@@ -59,7 +59,7 @@ npx claude-code-model-router init --global # 写入 ~/.ccmr,全目录共享
5959# 启动网关(前台运行;models.yaml / .env 修改后自动热重载,无需重启)
6060npx claude-code-model-router start
6161npx claude-code-model-router start --port 9000 # 指定端口
62- npx claude-code-model-router start --host 0.0.0.0 # 监听所有网卡(见下方安全提示)
62+ npx claude-code-model-router start --host 0.0.0.0 # 需设置入站鉴权令牌
6363
6464# 查看本机正在运行的网关(端口 / PID / 版本 / 配置来源 / Key 状态)
6565npx claude-code-model-router status
@@ -91,7 +91,7 @@ npx claude-code-model-router claude --gateway-port 9000 # 自定义网关端口
9191claude
9292```
9393
94- > ** 配置发现顺序** :` -c 指定路径 ` > ` ./models.yaml ` > ` ./config/models.yaml ` > ` ./.claude-router.yaml ` > ` ~/.ccmr/models.yaml ` 。` .env ` 同理: ` ./. env` 优先, ` ~/.ccmr/.env ` 兜底(环境变量 ` CCMR_HOME ` 可改写全局目录位置,日志 ` gateway.log ` 也随之移动 )。
94+ > ** 配置发现顺序** :` -c 指定路径 ` > ` ./models.yaml ` > ` ./config/models.yaml ` > ` ./.claude-router.yaml ` > ` ~/.ccmr/models.yaml ` 。显式 ` -c ` 不存在或配置非法时会直接报错,不会回退到另一份配置。 ` . env` 按 ` ~/.ccmr/.env ` < ` ./.env ` < 配置文件相邻 ` .env ` 的优先级加载,父进程环境变量优先级最高( ` CCMR_HOME ` 可改写全局目录位置,日志也随之移动 )。
9595
9696### 网关的生命周期
9797
@@ -102,10 +102,12 @@ claude
102102
103103自动拉起的网关是 detached 进程(自成进程组、` PPID=1 ` ),收不到终端的 ` SIGHUP ` ——这是有意设计:多个 Claude Code 会话可以共用同一个网关,关掉其中一个窗口不该打断其他会话。代价是它不会自己消失,用 ` ccmr status ` 查看、` ccmr stop ` 收掉。
104104
105- > ` ccmr stop ` 只会停止通过 ` /health ` 自证身份的 ccmr 网关。如果端口被其他程序占用,它会明确报错并拒绝操作,绝不会误杀你的其他进程。
105+ 复用网关前会比较配置路径、路由内容、` .env ` 来源及 API Key 的不可逆摘要。若端口上的网关来自另一个项目,` ccmr claude ` 会拒绝复用并提示换端口或先停止旧网关,避免提示词发往错误的供应商账号。
106+
107+ > ` ccmr stop ` 会同时校验 ` /health ` 身份和 ` ~/.ccmr/gateway-<port>.identity.json ` 中的本机随机身份记录,匹配后才会发送信号。只伪造 HTTP 响应不能诱导它停止任意 PID。
106108
107109> ** 安全提示** :网关默认绑定到 ` 127.0.0.1 ` (仅本机可访问)。网关会用你本地配置的各厂商 API Key 代理上游请求,因此任何能访问该端口的人都能消耗你的额度。
108- > 若确需通过 ` --host 0.0.0.0 ` 暴露到局域网,请务必设置环境变量 ` CCMR_REQUIRED_AUTH_TOKEN ` ,此时调用方必须在 ` x-api-key ` 或 ` Authorization: Bearer <token> ` 中携带该令牌。未设置时绑定非回环地址会打印警告 。
110+ > 若确需通过 ` --host 0.0.0.0 ` 暴露到局域网,必须设置环境变量 ` CCMR_REQUIRED_AUTH_TOKEN ` ,此时调用方需在 ` x-api-key ` 或 ` Authorization: Bearer <token> ` 中携带该令牌。未设置时网关默认拒绝启动;仅在已隔离且明确接受风险时使用 ` --allow-insecure-network ` 。远程未认证的 ` /health ` 只返回基础存活信息,不暴露 PID、路径或 Key 状态 。
109111
110112### Claude Code 原生参数支持
111113
@@ -244,15 +246,23 @@ MIMO_API_KEY=tp-xxx # MiMo Token Plan,默认 SGP 集群
244246MIMO_TOKEN_CN_API_KEY=tp-xxx # MiMo Token Plan CN 集群
245247MIMO_TOKEN_AMS_API_KEY=tp-xxx # MiMo Token Plan AMS 集群
246248MIMO_PAYG_API_KEY=sk-xxx # MiMo Pay-as-you-go: https://platform.xiaomimimo.com/
249+
250+ # 可选网关设置
251+ GATEWAY_PORT=8080
252+ REQUEST_TIMEOUT=300
253+ LOG_LEVEL=INFO # DEBUG / INFO / WARN / ERROR / SILENT
254+ CCMR_REQUIRED_AUTH_TOKEN= # 非回环监听时必须设置
247255```
248256
257+ ` ccmr claude ` 与 ` ccmr stats ` 会自动使用 ` CCMR_REQUIRED_AUTH_TOKEN ` 。如客户端与服务端使用不同环境,可在客户端单独设置 ` CCMR_AUTH_TOKEN ` 覆盖发送令牌。
258+
249259MiMo Token Plan 的 Base URL 与购买套餐所在集群绑定。默认 ` mimo ` 使用 SGP 集群;如果订阅页显示 CN 或 AMS 集群,请分别配置 ` MIMO_TOKEN_CN_API_KEY ` / ` MIMO_TOKEN_AMS_API_KEY ` ,并使用 ` mimo-token-cn ` 或 ` mimo-token-ams ` 。` tp-* ` Token Plan Key 不能用于按量付费接口,` sk-* ` 按量付费 Key 也不能用于 Token Plan 接口。
250260
251261### 配置文件 (models.yaml)
252262
253263可以自定义供应商、模型变体、别名等。运行 ` init ` 命令会生成 ` providers -> variants ` 结构的模板;旧版平铺 ` models ` 配置仍然兼容。
254264
255- 网关运行中修改 ` models.yaml ` 或 ` .env ` 会** 自动热重载** (轮询检测,约 1 秒生效),加模型、换 Key 都不用重启。 ** 即使网关启动时这些文件还不存在 ** ,之后创建也会被捕获(v1.8.1 起) 。注意:` gateway.host ` / ` gateway.port ` 变更仍需重启才能重新绑定。
265+ 网关运行中修改 ` models.yaml ` 或 ` .env ` 会** 自动热重载** (轮询检测,约 1 秒生效),新增、轮换或删除 Key 都会生效;入站鉴权令牌也可热轮换。即使文件启动时不存在 ,之后创建也会被捕获。注意:` gateway.host ` / ` gateway.port ` 变更仍需重启才能重新绑定。
256266
257267排查某个网关到底在用哪份配置:
258268
@@ -399,9 +409,10 @@ npx claude-code-model-router claude
399409| 端点 | 方法 | 说明 |
400410| ------| ------| ------|
401411| ` /v1/messages ` | POST | Anthropic Messages API |
412+ | ` /v1/messages/count_tokens ` | POST | 转发到所选供应商的兼容 token counting 端点 |
402413| ` /v1/models ` | GET | 列出可用模型 |
403414| ` /usage ` | GET | 按模型的用量统计(请求数 / 错误数 / tokens,网关重启后清零) |
404- | ` /health ` | GET | 健康检查(含网关版本号、 ` pid ` 、 ` config_file ` 配置来源、 ` ccmr_home ` 、各模型 Key 状态) |
415+ | ` /health ` | GET | 健康检查;本机或已认证请求额外返回 PID、配置来源和模型状态 |
405416
406417## 开发
407418
@@ -419,6 +430,9 @@ npm run dev
419430# 构建
420431npm run build
421432
433+ # 类型检查、测试、冒烟测试与依赖审计
434+ npm run check
435+
422436# 本地测试
423437npm link
424438ccmr start
@@ -458,6 +472,17 @@ DeepSeek Anthropic 兼容接口会忽略 `metadata` 字段,但某些 Claude Co
458472
459473## 更新日志
460474
475+ ### v1.8.3
476+
477+ - 阻止 detached 网关跨项目复用错误的配置、端点或 API Key
478+ - 流式转发改用增量 UTF-8 解码,兼容 CRLF SSE;客户端断开会取消上游请求并处理背压
479+ - ` .env ` 删除 Key 后会真正撤销,入站鉴权支持热轮换;内置客户端统一使用相同令牌
480+ - 非回环无鉴权监听改为默认拒绝,远程 ` /health ` 隐藏本机路径、PID 与 Key 状态
481+ - ` ccmr stop ` 增加本机随机身份记录校验,不再只信任 HTTP 自报 PID
482+ - 显式配置路径、YAML、端口、超时和 CLI 数值参数改为严格校验;YAML/env/CLI 优先级保持一致
483+ - 实现兼容 ` /v1/messages/count_tokens ` 转发,并执行 streaming/tools 能力声明
484+ - 修复流式断连继续计费、生产依赖漏洞和缺失 LICENSE;CI/发布前新增依赖审计
485+
461486### v1.8.2
462487
463488- ** 新增 ` ccmr status ` ** :列出本机正在运行的 ccmr 网关及其端口、PID、版本、配置来源、可用模型数。` ccmr claude ` 自动拉起的网关是 detached 进程(关掉终端后继续运行),此前只能靠 ` lsof ` 才能找到它
@@ -497,7 +522,7 @@ DeepSeek Anthropic 兼容接口会忽略 `metadata` 字段,但某些 Claude Co
497522- 配置热重载遇到损坏的 YAML 时保留旧配置继续运行,不再静默退化为默认配置
498523
499524** 工程化**
500- - 引入 vitest 测试体系(69 个测试) :路由解析 / URL 构建 / SSE 转发 / 鉴权 / 热重载 / failover / 用量统计,以及 DEFAULT_CONFIG 与 YAML 模板的一致性测试(当场修复了模板中 ` default_variant: 5.2 ` 未加引号、缺失 ` kimi-k2.6 ` 别名两处漂移)
525+ - 引入 vitest 测试体系:路由解析 / URL 构建 / SSE 转发 / 鉴权 / 热重载 / failover / 用量统计,以及 DEFAULT_CONFIG 与 YAML 模板的一致性测试
501526- 新增 GitHub Actions CI:Node 18/20/24 矩阵构建 + 测试 + dist 一致性校验
502527
503528### v1.7.1
@@ -557,4 +582,4 @@ DeepSeek Anthropic 兼容接口会忽略 `metadata` 字段,但某些 Claude Co
557582
558583## License
559584
560- MIT
585+ [ MIT] ( LICENSE )
0 commit comments