mirror of
https://gitcode.com/JianFeeeee/ModelRouter.git
synced 2026-11-07 09:47:23 +00:00
README 从 642 行降到 131 行,只保留简介、核心能力、最小快速开始、文档索引、 改名说明、目录结构与测试入口。其余内容迁到 docs/,中英文索引一一对应: docs/features.md 实现与完整特性清单(原 README 的"实现/特性") docs/configuration.md 配置文件、自动探测模型、多密钥与配额 docs/routing.md 模型路由、AUTO 链、冷却与半冷却、源/适配器、源模板 docs/performance.md 实测内存占用与调优、thinking 预算 docs/webui.md WebUI 使用 docs/adapters.md Lua 适配器协议与内置适配器清单 docs/gui.md 桌面端 Headless/Desktop 两种产物与构建 docs/development.md 目录职责、开发协作、测试 docs/deployment.md 部署、发行包、目录权限、llmsproxy 迁移与验证清单 中性化:README / README_EN / GUI 注释里的 `Clash Verge` 类比全部改为 「桌面壳 / desktop shell」,仓库内(源码与文档)已无该表述。
133 lines
6.5 KiB
Markdown
133 lines
6.5 KiB
Markdown
# ModelRouter
|
||
|
||
> **English**: [README_EN.md](./README_EN.md)
|
||
>
|
||
> **AI-assisted**: 本项目使用 AI 辅助编程(代码与文档由 AI 协作完成,经人工复核)。
|
||
|
||
面向多 LLM 订阅者的内网网关:一次配置,多个服务共用一组上游额度。支持指定模型或
|
||
`AUTO` 模式,按配置的优先级选择可用模型提供服务。
|
||
|
||
网关本体是单个 Go 二进制(约 10 MB,零运行时依赖)。新增或切换上游只需在
|
||
`config.yaml`(或 WebUI)加一个 `sources` 条目、或挂一个 `.lua` 适配器——**不改 Go、
|
||
不重编译**。源与适配器的改动经 WebUI 提交时即时生效(热更新);直接编辑
|
||
`config.yaml` 或 `adapter_dir` 下的 `.lua` 文件需要重启进程生效。
|
||
|
||
## 核心能力
|
||
|
||
- **统一接口**:对内暴露 OpenAI 兼容的 `/v1/chat/completions`、`/v1/models`、
|
||
`/v1/images/generations`;所有源对外都是同一套格式(含 `reasoning_content`、
|
||
`tool_calls`、`usage`)。
|
||
- **多源 + AUTO 链**:一个进程内任意多个上游源;`default_model: AUTO` 时按优先级页
|
||
保存的档位逐档调度,源故障自动降级并冷却,恢复后半冷却探测自愈。
|
||
- **协议适配在 Lua 层**:每个源挂一个 `.lua` 适配器,完成请求/响应/流式分片的双向
|
||
转换,并可用 `build_headers(meta)` 注入签名头。协议差异不进 Go 内核。
|
||
- **插件独立**:业务扩展(渠道接入、计费、额度巡检)是外置 Lua 插件,由插件目录加载,
|
||
不编进二进制、不随发行包分发;插件只通过 `modelrouter` SDK 与内核交互。
|
||
- **多租户密钥**:网关 key 与上游 key 相互独立,按 key 限定模型范围、AUTO 链与配额。
|
||
- **加密存储**:上游 key、自定义请求头、网关 key 均以 AES-256-GCM 落盘,
|
||
`master.key` 单独 0600 权限(或由 `MODELROUTER_MASTER_KEY` 注入)。
|
||
- **可观测**:状态页实时探测源可达性;HTTP 访问日志、配置变更审计、请求与用量 CSV 导出;
|
||
写操作不落在请求热路径上。
|
||
|
||
## 快速开始
|
||
|
||
```bash
|
||
# 需要 LuaJIT 开发库;-tags luajit 是必须的
|
||
GOMODCACHE=... GOPROXY=off go build -tags luajit -o modelrouter ./cmd/modelrouter
|
||
|
||
# 首次运行会生成默认配置,并在日志里打印随机 admin key
|
||
./modelrouter -config config.yaml
|
||
```
|
||
|
||
> 依赖 [golua](https://github.com/aarzilli/golua)(LuaJIT 绑定)。不带 `-tags luajit`
|
||
> 会走 gopher-lua 路径,行为略有差异。
|
||
|
||
> **配置不入库**:仓库不携带任何 config 文件(其中含密钥)。默认配置只绑定
|
||
> `127.0.0.1:8080`,首次登录后请在 WebUI「密钥」页更换管理员密钥。
|
||
|
||
```bash
|
||
# 无 key -> 401
|
||
curl http://127.0.0.1:8080/v1/models
|
||
|
||
# 单次($KEY 换成首次启动日志打印的 admin key)
|
||
curl -H "Authorization: Bearer $KEY" \
|
||
-d '{"model":"AUTO","messages":[{"role":"user","content":"hi"}]}' \
|
||
http://127.0.0.1:8080/v1/chat/completions
|
||
|
||
# 流式
|
||
curl -N -H "Authorization: Bearer $KEY" \
|
||
-d '{"model":"AUTO","stream":true,"messages":[{"role":"user","content":"hi"}]}' \
|
||
http://127.0.0.1:8080/v1/chat/completions
|
||
```
|
||
|
||
任何 OpenAI SDK 把 `base_url` 指向网关、`api_key` 换成任一已授权的网关 key 即可。
|
||
|
||
## 文档
|
||
|
||
| 主题 | 文档 |
|
||
|---|---|
|
||
| 实现与完整特性清单 | [docs/features.md](docs/features.md) |
|
||
| 配置:`config.yaml`、自动探测模型、多密钥 | [docs/configuration.md](docs/configuration.md) |
|
||
| 路由:模型路由、AUTO 链、冷却与半冷却、源与适配器、源模板 | [docs/routing.md](docs/routing.md) |
|
||
| 适配器:Lua 协议、内置适配器清单 | [docs/adapters.md](docs/adapters.md) · [docs/lua-adapters.md](docs/lua-adapters.md)([EN](docs/lua-adapters-en.md)) |
|
||
| 插件:SDK 契约、钩子、UI 扩展、HTTP 端点 | [docs/plugins.md](docs/plugins.md) |
|
||
| 桌面端:Headless / Desktop 两种产物、构建与运行 | [docs/gui.md](docs/gui.md) |
|
||
| 性能:实测内存占用与调优、thinking 预算 | [docs/performance.md](docs/performance.md) |
|
||
| WebUI 使用 | [docs/webui.md](docs/webui.md) |
|
||
| 开发:目录职责、测试、分支与发布纪律 | [docs/development.md](docs/development.md) · [docs/git-workflow.md](docs/git-workflow.md)([EN](docs/git-workflow-en.md)) |
|
||
| 部署与迁移 | [docs/deployment.md](docs/deployment.md) |
|
||
|
||
## 从 llmsproxy 改名
|
||
|
||
产品名早已是 ModelRouter,二进制、配置目录、服务名与环境变量现已统一为
|
||
`modelrouter`:
|
||
|
||
| 旧 | 新 |
|
||
|---|---|
|
||
| `llmsproxy`(二进制) | `modelrouter` |
|
||
| `/etc/llmsproxy/` | `/etc/modelrouter/` |
|
||
| `llmsproxy.service` | `modelrouter.service` |
|
||
| `LLMSPROXY_*` | `MODELROUTER_*` |
|
||
|
||
已部署的机器用迁移脚本升级(**默认 dry-run**,复制不移动,可回滚):
|
||
|
||
```bash
|
||
sudo ./packaging/migrate-to-modelrouter.sh # 预演
|
||
sudo ./packaging/migrate-to-modelrouter.sh --apply # 执行
|
||
sudo ./packaging/migrate-to-modelrouter.sh --rollback --apply
|
||
```
|
||
|
||
旧路径与旧环境变量在读取侧仍被接受,因此升级不会因为顺序问题立刻失效。
|
||
`deploy.sh` 在检测到旧 `/etc/llmsproxy` 而新配置不存在时会**中止**,避免部署出
|
||
一个「能启动但没有 key / 没有源」的空实例。
|
||
|
||
插件 SDK 同名调整:唯一公开入口是 `modelrouter`(`llmsproxy` 仅作兼容别名),
|
||
详见 [docs/plugins.md](docs/plugins.md)。
|
||
|
||
## 目录结构
|
||
|
||
```text
|
||
cmd/modelrouter # 入口(纯 Go 服务端)
|
||
cmd/gui # Electron 桌面壳(内嵌同一份核心)
|
||
internal/config # 配置解析、加密存储、运行时文件
|
||
internal/core # 调度、内核动作、状态与审计
|
||
internal/lua # LuaJIT VM + 弹性 worker 池 + 内置适配器 (embed)
|
||
internal/lua/plugins # 可选插件示例(不随二进制/发行包分发)
|
||
internal/provider # Provider(HTTP) + Registry(路由)
|
||
internal/gateway # OpenAI 兼容 HTTP 服务 + 鉴权 + 流式 + WebUI
|
||
internal/types # 统一格式 & OpenAI wire 类型
|
||
packaging/ # deb/rpm/tar 打包、systemd unit、迁移脚本
|
||
docs/ # 主题文档
|
||
```
|
||
|
||
## 开发与测试
|
||
|
||
```bash
|
||
go test -tags luajit ./... # 全量
|
||
go test -tags luajit ./internal/lua # 单包(LuaJIT 相关改动必跑)
|
||
```
|
||
|
||
- 分支与发布纪律见 [docs/git-workflow.md](docs/git-workflow.md)。
|
||
- 插件放置在 `plugin_dir`,网关启动时**不会**创建、覆盖或删除任何插件文件;
|
||
升级桌面端也不会动它们。
|