Polish README for simple-mode HF deployment
Browse files
README.md
CHANGED
|
@@ -12,31 +12,52 @@ pinned: false
|
|
| 12 |
|
| 13 |
当前 Space:<https://ohmyapi-c2api.hf.space>
|
| 14 |
|
| 15 |
-
这是一个
|
| 16 |
|
| 17 |
-
- 让根路径 `/` 直接进入管理登录页 `/admin/login`
|
| 18 |
- 保持 `/admin`、`/health`、`/v1/*` 等能力继续由上游 `claude2api` 提供
|
| 19 |
-
-
|
| 20 |
|
| 21 |
-
## 当前
|
| 22 |
|
| 23 |
-
当前
|
| 24 |
|
| 25 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 26 |
|
| 27 |
-
-
|
| 28 |
-
|
| 29 |
-
|
| 30 |
-
|
|
|
|
| 31 |
|
| 32 |
当前线上已验证:
|
| 33 |
|
| 34 |
- `/` → `302 /admin/login`
|
| 35 |
- `/admin/login` 可正常打开
|
| 36 |
- `/health` 返回 `200`
|
| 37 |
-
- `/v1/models` 可正常访问
|
| 38 |
- `/v1/messages` 未带正确 token 时返回 `401 Invalid API key`
|
| 39 |
-
- 带正确 app token 时,`claude-sonnet-4-6` 已成功完成
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 40 |
|
| 41 |
## 为什么 Hugging Face 环境变量能直接生效
|
| 42 |
|
|
@@ -47,7 +68,7 @@ Hugging Face 对 Docker Space 的处理方式不是“把变量写进仓库文
|
|
| 47 |
- **Variables**
|
| 48 |
- **Secrets**
|
| 49 |
|
| 50 |
-
|
| 51 |
|
| 52 |
对这个仓库来说,等价于容器启动时直接拿到了例如:
|
| 53 |
|
|
@@ -59,7 +80,7 @@ ADMIN_PASS=...
|
|
| 59 |
CLAUDE_SESSION_KEYS=...
|
| 60 |
```
|
| 61 |
|
| 62 |
-
|
| 63 |
|
| 64 |
### 当前已确认的 Space Variables
|
| 65 |
|
|
@@ -72,9 +93,9 @@ ADMIN_USER=admin
|
|
| 72 |
|
| 73 |
Secrets 不会被 Hugging Face API 直接回显,但从线上行为可以确认至少存在并已生效:
|
| 74 |
|
| 75 |
-
- `CLAUDE_API_KEY`
|
| 76 |
-
- `CLAUDE_SESSION_KEYS`
|
| 77 |
-
- `ADMIN_PASS`
|
| 78 |
|
| 79 |
## 当前 wrapper 做了什么
|
| 80 |
|
|
@@ -92,73 +113,45 @@ Secrets 不会被 Hugging Face API 直接回显,但从线上行为可以确认
|
|
| 92 |
- 现在用户访问根路径时,会直接进入真实可用的登录入口
|
| 93 |
- 同时不需要去改上游镜像源码
|
| 94 |
|
| 95 |
-
## 当前
|
| 96 |
|
| 97 |
### 结论
|
| 98 |
|
| 99 |
**按当前已验证状态,不能认为这个 Space 已经配置并启用了 PostgreSQL 持久化存储。**
|
| 100 |
|
| 101 |
-
|
| 102 |
-
|
| 103 |
-
```text
|
| 104 |
-
postgresql://neondb_owner:npg_EhvAUwfT1Q0s@ep-late-sun-a4w4w406-pooler.us-east-1.aws.neon.tech/neondb?sslmode=require&channel_binding=require
|
| 105 |
-
```
|
| 106 |
-
|
| 107 |
-
但就目前线上可确认的信息来看,还不能据此得出“当前 Space 正在用 PostgreSQL 持久化”的结论。
|
| 108 |
|
| 109 |
### 原因
|
| 110 |
|
| 111 |
-
1. 当前
|
| 112 |
-
2. Hugging Face
|
| 113 |
-
3.
|
| 114 |
-
4. 当前线上已观察到的配置行为更像是:
|
| 115 |
-
- 上游成功读取了 `CLAUDE_SESSION_KEYS`
|
| 116 |
-
- 并使用 simple mode 就能完成调用
|
| 117 |
-
5. 之前的运行时验证还显示:
|
| 118 |
-
- admin UI 中修改的 `api_key` 只在当前进程有效
|
| 119 |
-
- 重启后回退到启动环境变量值
|
| 120 |
-
这也**不支持**“当前已经有稳定的持久化配置优先层”这一判断。
|
| 121 |
-
|
| 122 |
-
### 如果要真正启用 PostgreSQL
|
| 123 |
-
|
| 124 |
-
需要满足两个条件:
|
| 125 |
|
| 126 |
-
|
| 127 |
-
|
|
|
|
| 128 |
|
| 129 |
-
|
|
|
|
| 130 |
|
| 131 |
-
|
| 132 |
-
DB_HOST=ep-late-sun-a4w4w406-pooler.us-east-1.aws.neon.tech
|
| 133 |
-
DB_PORT=5432
|
| 134 |
-
DB_USER=neondb_owner
|
| 135 |
-
DB_PASS=...实际密码...
|
| 136 |
-
DB_NAME=neondb
|
| 137 |
-
```
|
| 138 |
|
| 139 |
-
|
| 140 |
|
| 141 |
-
|
| 142 |
-
- 当前 `.env.example` / README 的接口更偏向拆分字段,而不是单个 `DATABASE_URL`
|
| 143 |
-
- 如果上游源码实际上不支持 Neon 这种外部 PG 持久化路径,或者虽然支持 PG 但启动优先级仍是 env 覆盖 runtime state,那么依然达不到你想要的“persisted-first”语义
|
| 144 |
|
| 145 |
-
|
|
|
|
|
|
|
| 146 |
|
| 147 |
-
|
| 148 |
|
| 149 |
-
-
|
| 150 |
-
-
|
| 151 |
-
- `admin_pass` 目前看**不能**通过现有 settings 路径真正更新生效
|
| 152 |
-
|
| 153 |
-
所以当前更准确的理解是:
|
| 154 |
-
|
| 155 |
-
- Hugging Face Secrets / Variables = **启动配置源**
|
| 156 |
-
- 上游 admin UI 的部分设置 = **运行期状态修改**
|
| 157 |
-
- 两者目前**不是**一个可自动回写、可稳定持久继承的统一配置层
|
| 158 |
|
| 159 |
## 当前推荐的线上配置思路
|
| 160 |
|
| 161 |
-
如果你只是想把 Space 稳定跑起来:
|
| 162 |
|
| 163 |
### 必要 Secrets
|
| 164 |
|
|
@@ -173,22 +166,51 @@ LISTEN_ADDR=:7860
|
|
| 173 |
ADMIN_USER=admin
|
| 174 |
```
|
| 175 |
|
| 176 |
-
###
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 177 |
|
| 178 |
-
|
|
|
|
|
|
|
| 179 |
|
| 180 |
-
|
| 181 |
|
| 182 |
-
|
| 183 |
-
|
| 184 |
-
|
| 185 |
-
|
| 186 |
-
|
| 187 |
-
|
| 188 |
-
|
| 189 |
-
- 还是 HF Secrets / env
|
| 190 |
|
| 191 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 192 |
|
| 193 |
## 当前仓库文件职责
|
| 194 |
|
|
@@ -203,7 +225,9 @@ ADMIN_USER=admin
|
|
| 203 |
```bash
|
| 204 |
curl -I https://ohmyapi-c2api.hf.space/
|
| 205 |
curl https://ohmyapi-c2api.hf.space/health
|
| 206 |
-
|
|
|
|
|
|
|
| 207 |
|
| 208 |
curl https://ohmyapi-c2api.hf.space/v1/messages \
|
| 209 |
-H "Content-Type: application/json" \
|
|
@@ -215,4 +239,4 @@ curl https://ohmyapi-c2api.hf.space/v1/messages \
|
|
| 215 |
}'
|
| 216 |
```
|
| 217 |
|
| 218 |
-
如果最后一条返回正常消息体,就说明当前公开 Space、app token、以及 Claude session 这三层链路都已经打通。
|
|
|
|
| 12 |
|
| 13 |
当前 Space:<https://ohmyapi-c2api.hf.space>
|
| 14 |
|
| 15 |
+
这是一个围绕 `pushzx/claude2api:latest` 的 Hugging Face Docker Space 包装层。目标很克制:
|
| 16 |
|
| 17 |
+
- 让根路径 `/` 直接进入真实可用的管理登录页 `/admin/login`
|
| 18 |
- 保持 `/admin`、`/health`、`/v1/*` 等能力继续由上游 `claude2api` 提供
|
| 19 |
+
- wrapper 只处理入口体验与反代,不在外层伪造持久化配置语义
|
| 20 |
|
| 21 |
+
## 当前部署状态
|
| 22 |
|
| 23 |
+
当前线上状态已经收敛为 **public Space + simple mode**。
|
| 24 |
|
| 25 |
+
- Space 类型:**public Space**
|
| 26 |
+
- 运行模式:**simple mode**
|
| 27 |
+
- 当前不启用 DB-backed 持久化
|
| 28 |
+
- 当前已从 Space Secrets 中移除:`DB_HOST`、`DB_PORT`、`DB_USER`、`DB_PASS`、`DB_NAME`、`PGSSLMODE`
|
| 29 |
+
- 当前根路径 `/` 会直接 `302` 到 `/admin/login`
|
| 30 |
|
| 31 |
+
这样收敛的原因很明确:simple mode 已经稳定可用,而当前上游镜像的 DB-only 路径对 Neon / Supabase 这类强制 TLS 的托管 PostgreSQL 仍未验证通过,不能在这里把它写成现成功能。
|
| 32 |
+
|
| 33 |
+
## 当前访问行为
|
| 34 |
+
|
| 35 |
+
public Space 的含义是:**入口默认公开**,不是 **Secrets 自动公开**。
|
| 36 |
|
| 37 |
当前线上已验证:
|
| 38 |
|
| 39 |
- `/` → `302 /admin/login`
|
| 40 |
- `/admin/login` 可正常打开
|
| 41 |
- `/health` 返回 `200`
|
|
|
|
| 42 |
- `/v1/messages` 未带正确 token 时返回 `401 Invalid API key`
|
| 43 |
+
- 带正确 app token 时,`claude-sonnet-4-6` 已成功完成实际调用
|
| 44 |
+
- `/v1/models` 可在带 token 的情况下返回模型列表
|
| 45 |
+
|
| 46 |
+
## public Space 的风险边界
|
| 47 |
+
|
| 48 |
+
public Space 不会因为是 public 就把 Hugging Face Secrets 直接暴露出来,但它会让你的入口地址处于公网可探测状态。
|
| 49 |
+
|
| 50 |
+
这意味着:
|
| 51 |
+
|
| 52 |
+
- `https://ohmyapi-c2api.hf.space/` 这类地址任何人都能访问与探测
|
| 53 |
+
- Hugging Face Space Secrets **不会**被页面或公开 API 直接回显
|
| 54 |
+
- 真正更常见的泄露面是:把 token / session 写进仓库文件、前端页面、日志、导出的配置或本机历史文件
|
| 55 |
+
- public Space 是否安全,关键不在于“是否 public”,而在于:
|
| 56 |
+
- app 自身接口是否强制鉴权
|
| 57 |
+
- `CLAUDE_API_KEY` / `CLAUDE_SESSION_KEYS` 是否只保留在服务端运行时环境
|
| 58 |
+
- 仓库与页面输出里是否完全不出现真实 secret
|
| 59 |
+
|
| 60 |
+
换句话说,public Space **不会自动泄露 session**,但如果 app token 泄露、接口未加保护,别人就能直接消费你的服务。
|
| 61 |
|
| 62 |
## 为什么 Hugging Face 环境变量能直接生效
|
| 63 |
|
|
|
|
| 68 |
- **Variables**
|
| 69 |
- **Secrets**
|
| 70 |
|
| 71 |
+
直接注入成容器进程的真实运行时环境变量。
|
| 72 |
|
| 73 |
对这个仓库来说,等价于容器启动时直接拿到了例如:
|
| 74 |
|
|
|
|
| 80 |
CLAUDE_SESSION_KEYS=...
|
| 81 |
```
|
| 82 |
|
| 83 |
+
因此,只要上游 `claude2api` 在启动时通过 `os.Getenv(...)` 或等价方式读取配置,它就会直接生效,不需要额外写入 `.env`、`config.yaml` 或其它文件。
|
| 84 |
|
| 85 |
### 当前已确认的 Space Variables
|
| 86 |
|
|
|
|
| 93 |
|
| 94 |
Secrets 不会被 Hugging Face API 直接回显,但从线上行为可以确认至少存在并已生效:
|
| 95 |
|
| 96 |
+
- `CLAUDE_API_KEY`
|
| 97 |
+
- `CLAUDE_SESSION_KEYS`
|
| 98 |
+
- `ADMIN_PASS`
|
| 99 |
|
| 100 |
## 当前 wrapper 做了什么
|
| 101 |
|
|
|
|
| 113 |
- 现在用户访问根路径时,会直接进入真实可用的登录入口
|
| 114 |
- 同时不需要去改上游镜像源码
|
| 115 |
|
| 116 |
+
## 当前为什么不启用 PostgreSQL 持久化
|
| 117 |
|
| 118 |
### 结论
|
| 119 |
|
| 120 |
**按当前已验证状态,不能认为这个 Space 已经配置并启用了 PostgreSQL 持久化存储。**
|
| 121 |
|
| 122 |
+
更准确地说:当前线上已经明确收敛为 **simple mode only**,不是“正在尝试 DB-only 但尚未成功”。
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 123 |
|
| 124 |
### 原因
|
| 125 |
|
| 126 |
+
1. 只要存在 `CLAUDE_SESSION_KEYS`,上游就可以走 simple mode,并且当前已验证可稳定提供 API 能力。
|
| 127 |
+
2. 当前 Hugging Face Space runtime 已确认 `storage.current = None` 且 `storage.requested = None`,因此容器内本地 PostgreSQL 不能视为正式持久化层。
|
| 128 |
+
3. 对当前上游镜像的排查显示,DB-only 路径很可能会把 PostgreSQL DSN 拼成:
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 129 |
|
| 130 |
+
```text
|
| 131 |
+
host=%s port=%s user=%s password=%s dbname=%s sslmode=disable
|
| 132 |
+
```
|
| 133 |
|
| 134 |
+
这会与 Neon / Supabase 这类强制 TLS 的托管 PostgreSQL 冲突。
|
| 135 |
+
4. 因此,即使文档里存在“可连接外部数据库”的描述,也不能把它等同于“当前镜像已支持外部托管 PG 持久化”。
|
| 136 |
|
| 137 |
+
### 为什么 local PostgreSQL 不能当成 HF 持久化
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 138 |
|
| 139 |
+
如果你打算在 Hugging Face Space 容器里直接放一个“本地 PostgreSQL”,要先明确一件事:**默认情况下,这不等于可靠持久化。**
|
| 140 |
|
| 141 |
+
原因是:
|
|
|
|
|
|
|
| 142 |
|
| 143 |
+
1. Docker Space 默认使用的是容器自身的可写层,而不是天然持久卷。
|
| 144 |
+
2. 如果没有单独申请 Hugging Face persistent storage,并把数据库目录明确挂到持久路径,本地 PG 数据在 restart / rebuild / redeploy 后都可能丢失。
|
| 145 |
+
3. 当前这个 Space 没有启用 persistent storage,因此“容器内本地 PG”不能当成正式配置持久化方案。
|
| 146 |
|
| 147 |
+
因此:
|
| 148 |
|
| 149 |
+
- 本地 PG 更适合临时调试,不适合承担当前 Space 的正式配置持久化
|
| 150 |
+
- 真正需要稳定持久化时,应优先使用外部 PostgreSQL,或者先补齐 HF persistent storage,再验证上游是否支持对应的数据目录语义
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 151 |
|
| 152 |
## 当前推荐的线上配置思路
|
| 153 |
|
| 154 |
+
如果你只是想把 Space 稳定跑起来,当前推荐就是保持 simple mode:
|
| 155 |
|
| 156 |
### 必要 Secrets
|
| 157 |
|
|
|
|
| 166 |
ADMIN_USER=admin
|
| 167 |
```
|
| 168 |
|
| 169 |
+
### 当前不启用的配置
|
| 170 |
+
|
| 171 |
+
以下 DB 相关项当前视为**暂不启用**,不要再把它们当成线上必需配置:
|
| 172 |
+
|
| 173 |
+
- `DB_HOST`
|
| 174 |
+
- `DB_PORT`
|
| 175 |
+
- `DB_USER`
|
| 176 |
+
- `DB_PASS`
|
| 177 |
+
- `DB_NAME`
|
| 178 |
+
- `PGSSLMODE`
|
| 179 |
+
|
| 180 |
+
## 当前已验证可调用的模型
|
| 181 |
+
|
| 182 |
+
带正确 app token 时,以下模型已通过真实 `/v1/messages` 请求验证,可以正常返回结果:
|
| 183 |
+
|
| 184 |
+
- `claude-sonnet-4-5`
|
| 185 |
+
- `claude-haiku-4-5`
|
| 186 |
+
- `claude-sonnet-4-6`
|
| 187 |
+
- `claude-haiku-4-6`
|
| 188 |
+
- `claude-3-5-sonnet-20241022`
|
| 189 |
+
- `claude-3-5-haiku-20241022`
|
| 190 |
+
- `claude-3-sonnet-20240229`
|
| 191 |
+
- `claude-3-haiku-20240307`
|
| 192 |
+
|
| 193 |
+
以下模型虽然会出现在 `/v1/models` 列表里,但当前实测返回的是 `403 model_not_available`:
|
| 194 |
|
| 195 |
+
- `claude-opus-4-5`
|
| 196 |
+
- `claude-opus-4-6`
|
| 197 |
+
- `claude-3-opus-20240229`
|
| 198 |
|
| 199 |
+
这也说明一件事:**`/v1/models` 返回的是“当前镜像声明支持的模型列表”,真正能否调用仍然取决于当前 session / account 的实际可用性。**
|
| 200 |
|
| 201 |
+
## 关于 admin password / auth token 持久化的当前结论
|
| 202 |
+
|
| 203 |
+
目前已做过的验证结论是:
|
| 204 |
+
|
| 205 |
+
- `api_key` 可以在当前运行期通过管理接口更新,并立即影响鉴权结果
|
| 206 |
+
- 但容器重启后,会回退到启动时环境变量 / HF Secrets 的值
|
| 207 |
+
- `admin_pass` 目前看**不能**通过现有 settings 路径真正更新并持久生效
|
|
|
|
| 208 |
|
| 209 |
+
所以当前更准确的理解是:
|
| 210 |
+
|
| 211 |
+
- Hugging Face Secrets / Variables = **启动配置源**
|
| 212 |
+
- 上游 admin UI 的部分设置 = **运行期状态修改**
|
| 213 |
+
- 两者目前**不是**一个可自动回写、可稳定持久继承的统一配置层
|
| 214 |
|
| 215 |
## 当前仓库文件职责
|
| 216 |
|
|
|
|
| 225 |
```bash
|
| 226 |
curl -I https://ohmyapi-c2api.hf.space/
|
| 227 |
curl https://ohmyapi-c2api.hf.space/health
|
| 228 |
+
|
| 229 |
+
curl https://ohmyapi-c2api.hf.space/v1/models \
|
| 230 |
+
-H "Authorization: Bearer $CLAUDE_API_KEY"
|
| 231 |
|
| 232 |
curl https://ohmyapi-c2api.hf.space/v1/messages \
|
| 233 |
-H "Content-Type: application/json" \
|
|
|
|
| 239 |
}'
|
| 240 |
```
|
| 241 |
|
| 242 |
+
如果最后一条返回正常消息体,就说明当前公开 Space、app token、以及 Claude session 这三层链路都已经打通。
|