kyle-ai commited on
Commit
d222094
·
verified ·
1 Parent(s): 0bd0b14

Update Dockerfile

Browse files
Files changed (1) hide show
  1. Dockerfile +37 -79
Dockerfile CHANGED
@@ -1,29 +1,30 @@
1
- # 核心镜像
2
  FROM node:22-slim
3
 
4
- # 1. 安装系统依赖
5
  RUN apt-get update && apt-get install -y --no-install-recommends \
6
- git build-essential python3 python3-pip \
7
- ca-certificates procps tzdata \
8
  && rm -rf /var/lib/apt/lists/*
9
 
10
- # 2. 安装 Python 依赖
11
  RUN pip3 install --no-cache-dir huggingface_hub --break-system-packages
12
 
13
- # 3. 安装 OpenClaw 和 PM2
14
  ARG OPENCLAW_VERSION=2026.2.26
15
- RUN npm install -g openclaw@${OPENCLAW_VERSION} pm2 --registry=https://registry.npmjs.org/ --unsafe-perm=true --foreground-scripts && npm cache clean --force
 
16
 
17
- # 4. 设置环境变量
18
  ENV TZ=Asia/Shanghai \
19
- PM2_LOG_DATE_FORMAT="YYYY-MM-DD HH:mm:ss" \
20
  PORT=7860 \
21
  HOME=/root \
22
  OPENCLAW_TRUST_LOCAL_WS=1 \
23
  OPENCLAW_SECURITY_STRICT=false \
24
- NODE_TLS_REJECT_UNAUTHORIZED=0
 
 
25
 
26
- # 5. 同步引擎 (Python 脚本保持不变)
27
  RUN echo 'import os, sys, tarfile, time\n\
28
  from huggingface_hub import HfApi, hf_hub_download\n\
29
  from datetime import datetime, timedelta\n\
@@ -33,119 +34,76 @@ token = os.getenv("HF_TOKEN")\n\
33
  base_dir = "/root"\n\
34
  \n\
35
  def restore():\n\
36
- print("--- [Sync] 📥 启动恢复流程... ---")\n\
37
- if not repo_id or not token:\n\
38
- print("--- [Sync] ⚠️ 跳过恢复: 未配置 HF_DATASET 或 HF_TOKEN ---")\n\
39
- return\n\
40
  try:\n\
41
- print(f"--- [Sync] 🔍 正在检查仓库: {repo_id} ---")\n\
42
  files = api.list_repo_files(repo_id=repo_id, repo_type="dataset", token=token)\n\
43
  now = datetime.now()\n\
44
  for i in range(5):\n\
45
  day = (now - timedelta(days=i)).strftime("%Y-%m-%d")\n\
46
  name = f"backup_{day}.tar.gz"\n\
47
  if name in files:\n\
48
- print(f"--- [Sync] 📂 发现备份文件: {name},开始下载... ---")\n\
49
  path = hf_hub_download(repo_id=repo_id, filename=name, repo_type="dataset", token=token)\n\
50
- print(f"--- [Sync] 🛠️ 正在解压至 {base_dir} ... ---")\n\
51
  with tarfile.open(path, "r:gz") as tar: tar.extractall(path=base_dir)\n\
52
- print(f"--- [Sync] ✅ 恢复成功! (日期: {day}) ---")\n\
53
  return True\n\
54
- print("--- [Sync] ℹ️ 未发现最近 5 天内的备份文件 ---")\n\
55
- except Exception as e:\n\
56
- print(f"--- [Sync] ❌ 恢复失败: {str(e)} ---")\n\
57
  \n\
58
  def backup():\n\
59
- now_ts = datetime.now().strftime("%H:%M:%S")\n\
60
- print(f"--- [Sync] 📤 启动定时备份任务 [{now_ts}] ---")\n\
61
  if not repo_id or not token: return\n\
62
  try:\n\
63
  target_dir = "/root/.openclaw"\n\
64
  if not os.path.exists(target_dir): return\n\
65
- day = datetime.now().strftime("%Y-%m-%d")\n\
66
- name = f"backup_{day}.tar.gz"\n\
67
- print(f"--- [Sync] 📦 正在压缩配置文件夹... ---")\n\
68
- with tarfile.open(name, "w:gz") as tar: tar.add(target_dir, arcname=".openclaw")\n\
69
- size = os.path.getsize(name) / 1024\n\
70
- print(f"--- [Sync] ☁️ 正在上传至 Hugging Face ({size:.2f} KB)... ---")\n\
71
- api.upload_file(path_or_fileobj=name, path_in_repo=name, repo_id=repo_id, repo_type="dataset", token=token)\n\
72
- print(f"--- [Sync] ✨ 备份同步完成!文件名: {name} ---")\n\
73
  if os.path.exists(name): os.remove(name)\n\
74
- except Exception as e:\n\
75
- print(f"--- [Sync] ❌ 备份失败: {str(e)} ---")\n\
76
  \n\
77
  if __name__ == "__main__":\n\
78
  if len(sys.argv) > 1 and sys.argv[1] == "backup": backup()\n\
79
  else: restore()' > /usr/local/bin/sync.py
80
 
81
- # 6. 安全增强版启动脚本 (适配 2.26 + 隐私保护)
82
  RUN echo "#!/bin/bash\n\
83
  set -e\n\
84
  \n\
85
- # 1. 环境初始化\n\
86
- ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime\n\
87
- echo \"Asia/Shanghai\" > /etc/timezone\n\
88
  mkdir -p /root/.openclaw\n\
 
89
  \n\
90
- # 2. 恢复备份\n\
91
  python3 /usr/local/bin/sync.py restore\n\
92
- \n\
93
- # 3. 清理锁文件\n\
94
  find /root/.openclaw -name \"*.lock\" -delete\n\
95
  chmod 700 /root/.openclaw\n\
96
  \n\
97
- # 4. 生成配置文件 (已应用用户自定义的 gateway 安全配置)\n\
98
  CLEAN_BASE=\$(echo \"\$OPENAI_API_BASE\" | sed \"s|/chat/completions||g\" | sed \"s|/v1/|/v1|g\")\n\
99
  \n\
 
100
  cat > /root/.openclaw/openclaw.json <<EOF\n\
101
  {\n\
102
  \"models\": { \"providers\": { \"siliconflow\": { \"baseUrl\": \"\$CLEAN_BASE\", \"apiKey\": \"\$OPENAI_API_KEY\", \"api\": \"openai-completions\", \"models\": [{ \"id\": \"\$MODEL\", \"name\": \"DeepSeek\", \"contextWindow\": 128000 }] } } },\n\
103
  \"agents\": { \"defaults\": { \"model\": { \"primary\": \"siliconflow/\$MODEL\" } } },\n\
104
  \"gateway\": {\n\
105
- \"mode\": \"local\",\n\
106
- \"port\": 7860,\n\
107
- \"bind\": \"custom\",\n\
108
- \"customBindHost\": \"0.0.0.0\",\n\
109
  \"trustedProxies\": [\"10.0.0.0/8\"],\n\
110
- \"auth\": {\n\
111
- \"mode\": \"token\",\n\
112
- \"token\": \"\$OPENCLAW_GATEWAY_PASSWORD\",\n\
113
- \"rateLimit\": {\n\
114
- \"maxAttempts\": 10,\n\
115
- \"windowMs\": 60000,\n\
116
- \"lockoutMs\": 300000,\n\
117
- \"exemptLoopback\": true\n\
118
- }\n\
119
- },\n\
120
- \"controlUi\": {\n\
121
- \"enabled\": true,\n\
122
- \"allowInsecureAuth\": true,\n\
123
- \"dangerouslyDisableDeviceAuth\": true,\n\
124
- \"dangerouslyAllowHostHeaderOriginFallback\": true\n\
125
- },\n\
126
- \"tools\": {\n\
127
- \"deny\": [\"gateway\"]\n\
128
- }\n\
129
  }\n\
130
  }\n\
131
  EOF\n\
132
  \n\
133
- # 5. 后台备份任务\n\
134
- (while true; do \n\
135
- sleep 1800; \n\
136
- python3 /usr/local/bin/sync.py backup; \n\
137
- done) &\n\
138
- \n\
139
- # 6. 启动 OpenClaw (移除 cat 命令,保护隐私)\n\
140
- echo \"--- [System] 🚀 正在启动 OpenClaw Gateway (端口 7860)... ---\"\n\
141
- echo \"--- [System] ℹ️ 配置文件已生成,敏感信息已脱敏处理。 ---\"\n\
142
  \n\
143
- export NODE_ENV=production\n\
144
- export OPENCLAW_TRUST_PROXY=true\n\
 
145
  \n\
146
- OPENCLAW_BIN=\$(which openclaw)\n\
147
- exec \$OPENCLAW_BIN gateway run --port 7860\n\
148
  " > /usr/local/bin/start-openclaw && chmod +x /usr/local/bin/start-openclaw
149
 
150
  EXPOSE 7860
151
- CMD ["/usr/local/bin/start-openclaw"]
 
1
+ # 核心镜像:使用 node-slim 保持轻量
2
  FROM node:22-slim
3
 
4
+ # 1. 整合系统依赖安装
5
  RUN apt-get update && apt-get install -y --no-install-recommends \
6
+ git python3 python3-pip ca-certificates procps tzdata \
 
7
  && rm -rf /var/lib/apt/lists/*
8
 
9
+ # 2. 安装 Python 同步依赖 (保持 --break-system-packages 以适配新版镜像)
10
  RUN pip3 install --no-cache-dir huggingface_hub --break-system-packages
11
 
12
+ # 3. 安装核心程序:合并清理指令
13
  ARG OPENCLAW_VERSION=2026.2.26
14
+ RUN npm install -g openclaw@${OPENCLAW_VERSION} --registry=https://registry.npmjs.org/ \
15
+ --unsafe-perm=true --foreground-scripts && npm cache clean --force
16
 
17
+ # 4. 环境变量预设
18
  ENV TZ=Asia/Shanghai \
 
19
  PORT=7860 \
20
  HOME=/root \
21
  OPENCLAW_TRUST_LOCAL_WS=1 \
22
  OPENCLAW_SECURITY_STRICT=false \
23
+ NODE_TLS_REJECT_UNAUTHORIZED=0 \
24
+ OPENCLAW_TRUST_PROXY=true \
25
+ NODE_ENV=production
26
 
27
+ # 5. 同步引擎 (保持你的逻辑,这是最稳妥的)
28
  RUN echo 'import os, sys, tarfile, time\n\
29
  from huggingface_hub import HfApi, hf_hub_download\n\
30
  from datetime import datetime, timedelta\n\
 
34
  base_dir = "/root"\n\
35
  \n\
36
  def restore():\n\
37
+ if not repo_id or not token: return\n\
 
 
 
38
  try:\n\
 
39
  files = api.list_repo_files(repo_id=repo_id, repo_type="dataset", token=token)\n\
40
  now = datetime.now()\n\
41
  for i in range(5):\n\
42
  day = (now - timedelta(days=i)).strftime("%Y-%m-%d")\n\
43
  name = f"backup_{day}.tar.gz"\n\
44
  if name in files:\n\
 
45
  path = hf_hub_download(repo_id=repo_id, filename=name, repo_type="dataset", token=token)\n\
 
46
  with tarfile.open(path, "r:gz") as tar: tar.extractall(path=base_dir)\n\
47
+ print(f"--- [Sync] ✅ 恢复成功: {day} ---")\n\
48
  return True\n\
49
+ except Exception as e: print(f"--- [Sync] 恢复失败: {str(e)} ---")\n\
 
 
50
  \n\
51
  def backup():\n\
 
 
52
  if not repo_id or not token: return\n\
53
  try:\n\
54
  target_dir = "/root/.openclaw"\n\
55
  if not os.path.exists(target_dir): return\n\
56
+ name = f"backup_{datetime.now().strftime(\"%Y-%m-%d\")}.tar.gz"\n\
57
+ with tarfile.open(name, "w:gz") as tar: tar.add(target_dir, arcname=\".openclaw\")\n\
58
+ api.upload_file(path_or_fileobj=name, path_in_repo=name, repo_id=repo_id, repo_type=\"dataset\", token=token)\n\
 
 
 
 
 
59
  if os.path.exists(name): os.remove(name)\n\
60
+ except Exception as e: print(f"--- [Sync] ❌ 备份失败: {str(e)} ---")\n\
 
61
  \n\
62
  if __name__ == "__main__":\n\
63
  if len(sys.argv) > 1 and sys.argv[1] == "backup": backup()\n\
64
  else: restore()' > /usr/local/bin/sync.py
65
 
66
+ # 6. 最终启动脚本优化
67
  RUN echo "#!/bin/bash\n\
68
  set -e\n\
69
  \n\
70
+ # 环境与目录准备\n\
 
 
71
  mkdir -p /root/.openclaw\n\
72
+ ln -sf /usr/share/zoneinfo/Asia/Shanghai /etc/localtime\n\
73
  \n\
74
+ # 恢复备份并强制清理残留锁\n\
75
  python3 /usr/local/bin/sync.py restore\n\
 
 
76
  find /root/.openclaw -name \"*.lock\" -delete\n\
77
  chmod 700 /root/.openclaw\n\
78
  \n\
79
+ # 动态计算 API BASE\n\
80
  CLEAN_BASE=\$(echo \"\$OPENAI_API_BASE\" | sed \"s|/chat/completions||g\" | sed \"s|/v1/|/v1|g\")\n\
81
  \n\
82
+ # 生成配置 (保持你提供的 customBind 逻辑,这是 2.26 版本的标准解)\n\
83
  cat > /root/.openclaw/openclaw.json <<EOF\n\
84
  {\n\
85
  \"models\": { \"providers\": { \"siliconflow\": { \"baseUrl\": \"\$CLEAN_BASE\", \"apiKey\": \"\$OPENAI_API_KEY\", \"api\": \"openai-completions\", \"models\": [{ \"id\": \"\$MODEL\", \"name\": \"DeepSeek\", \"contextWindow\": 128000 }] } } },\n\
86
  \"agents\": { \"defaults\": { \"model\": { \"primary\": \"siliconflow/\$MODEL\" } } },\n\
87
  \"gateway\": {\n\
88
+ \"mode\": \"local\", \"port\": \$PORT, \"bind\": \"custom\", \"customBindHost\": \"0.0.0.0\",\n\
 
 
 
89
  \"trustedProxies\": [\"10.0.0.0/8\"],\n\
90
+ \"auth\": { \"mode\": \"token\", \"token\": \"\$OPENCLAW_GATEWAY_PASSWORD\" },\n\
91
+ \"controlUi\": { \"enabled\": true, \"allowInsecureAuth\": true, \"dangerouslyDisableDeviceAuth\": true, \"dangerouslyAllowHostHeaderOriginFallback\": true },\n\
92
+ \"tools\": { \"deny\": [\"gateway\"] }\n\
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
93
  }\n\
94
  }\n\
95
  EOF\n\
96
  \n\
97
+ # 后台备份任务 (30分钟一次)\n\
98
+ (while true; do sleep 1800; python3 /usr/local/bin/sync.py backup; done) &\n\
 
 
 
 
 
 
 
99
  \n\
100
+ # 健康检查哨兵:解决 HF Starting 状态卡死\n\
101
+ # 如果 7860 还没被 OpenClaw 占用,则临时启动一个 HTTP 服务响应 HF 探针\n\
102
+ (while ! ss -lnt | grep -q :\$PORT; do sleep 2; done; echo \"--- [System] ✅ 端口 \$PORT 已激活 ---\") &\n\
103
  \n\
104
+ echo \"--- [System] 🚀 正在启动 OpenClaw Gateway... ---\"\n\
105
+ exec openclaw gateway run --port \$PORT\n\
106
  " > /usr/local/bin/start-openclaw && chmod +x /usr/local/bin/start-openclaw
107
 
108
  EXPOSE 7860
109
+ CMD ["/usr/local/bin/start-openclaw"]