From af75ed508277506ded375089171c0320951f123f Mon Sep 17 00:00:00 2001 From: fylorn <249551762+fylorn@users.noreply.github.com> Date: Fri, 9 Oct 2026 11:55:13 +0800 Subject: [PATCH 1/3] Docs for Lite 2026.10.10: models added by hand, a hidden menu bar item, scan alerts MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - features.md (en, zh-CN): an upstream's models are the ones it lists plus any added by hand with "Add models…" in its model list; the Manual tag, the rules for an ID, removal with Undo, and that routing, failover, aliases, rules, key scopes, the clients' model list, the dry run and the speed test treat them like listed models. The Menu bar setting's fourth choice, Hidden. Editing a scanned file reports only new findings. - import-links.md (en, zh-CN): the models parameter adds models by hand, next to those the service lists. - failover-and-load-balancing.md (en, zh-CN): a member that leaves a model out of its list can be given it by hand; the guide follows 2026.10.10. Co-Authored-By: Claude Opus 5.5 --- src/content/docs-lite/en/failover-and-load-balancing.md | 4 ++-- src/content/docs-lite/en/features.md | 8 +++++--- src/content/docs-lite/en/import-links.md | 2 +- .../docs-lite/zh-CN/failover-and-load-balancing.md | 4 ++-- src/content/docs-lite/zh-CN/features.md | 8 +++++--- src/content/docs-lite/zh-CN/import-links.md | 2 +- 6 files changed, 16 insertions(+), 12 deletions(-) diff --git a/src/content/docs-lite/en/failover-and-load-balancing.md b/src/content/docs-lite/en/failover-and-load-balancing.md index 47d93aa..8d1c5c6 100644 --- a/src/content/docs-lite/en/failover-and-load-balancing.md +++ b/src/content/docs-lite/en/failover-and-load-balancing.md @@ -4,7 +4,7 @@ ThinkWatch Lite turns each relay key into an upstream and puts several upstreams ## Before you start -- ThinkWatch Lite, [installed](/lite/#install), with a client connected on the Clients page. This guide follows version 2026.10.6. +- ThinkWatch Lite, [installed](/lite/#install), with a client connected on the Clients page. This guide follows version 2026.10.10. - The base URL and API keys of each relay. ## Steps @@ -32,7 +32,7 @@ A strategy only sets the order; every member remains available for failover. - **Concurrency limits.** An upstream with a **Concurrency limit** takes at most that many requests at once. When it is full, a conversation that stays on it waits for a free slot and then moves on, and other requests go straight to the next member; when every member is full, a request waits for the first free slot for up to **Wait for a free slot at most** in Settings › Failover, 30 seconds by default, and then receives a 429 with `Retry-After`, or the error of an earlier attempt when one was sent. The same wait covers a key's per-minute and per-hour usage limits, and the Traffic page shows each skip and the time queued. - **Pauses.** A failing upstream is paused for as long as Settings › Failover sets: by default 60 seconds after 3 **Consecutive failures**, doubling up to 600; 30 minutes for **Insufficient balance**; until the reset time, or 60 minutes, for **Quota used up**; the wait a rate-limited upstream asks for, up to 60 minutes. A rule with a single upstream is never held back, and when every member is paused they are tried anyway. - **Sessions and prompt cache.** Within a turn, while the client sends tool results back, requests keep the rule chosen at the start of the turn and the upstream that answered. Across turns, a conversation stays with the upstream that answered last if that answer read or wrote at least 1,024 cached tokens within the last five minutes; moving would rebuild the cache at full price. Otherwise, or when that upstream is paused, the strategy orders the members again, which is when **Round robin** moves on. The **Conversation** line on a request's **Routing** tab shows when a request stayed. -- **Same model name.** Every member is asked for the model the client sent, or the name a rule rewrote it to. A member whose model list lacks it is skipped; one without a list is tried, and its 404 moves the request on. +- **Same model name.** Every member is asked for the model the client sent, or the name a rule rewrote it to. A member whose model list lacks it is skipped; one without a list is tried, and its 404 moves the request on. A model that a member serves but leaves out of its list can be added with **Add models…** in the member's model list on the Upstreams page. - **Falling back to another model.** Add a rule with the condition **Selected upstream** set to the backup upstream, **On match** set to **Continue matching**, and its model in **Change model to** under **Parameter rewrites**. Such a rule is evaluated for each upstream as it is tried, failover included. The changed model no longer hits the cached prompt, and the request is priced by the name sent. Related: [Switch relays, upstreams or models without restarting Claude Code or Codex](/docs/lite/switch-upstreams-without-restart/), [Features](/docs/lite/features/#routing-and-failover), [Install and update](/docs/lite/install/). diff --git a/src/content/docs-lite/en/features.md b/src/content/docs-lite/en/features.md index 510cb58..4166789 100644 --- a/src/content/docs-lite/en/features.md +++ b/src/content/docs-lite/en/features.md @@ -41,6 +41,8 @@ Usage limits keep one client from using up a budget: each caps the key at a numb Upstreams are the services requests are forwarded to: API keys for Anthropic, OpenAI, Google Gemini, DeepSeek or any compatible endpoint, Amazon Bedrock (with an API key, access keys or an AWS profile), a ChatGPT account or a Z.ai / BigModel account signed in from the app, relays such as OpenRouter, and local models such as Ollama. A ChatGPT account shows its usage limits and reset times. So does an upstream on a GLM Coding Plan, that is, one whose address is on `api.z.ai` or `open.bigmodel.cn`, whether it was signed in from the app or added with a key: its 5-hour and weekly limits and, on a plan billed in credits, the credits left (“1,976 / 2,000 credits left”). When a client and an upstream use different API formats, requests are converted between Anthropic Messages, OpenAI Chat Completions, OpenAI Responses and Gemini, and the fields that cannot be carried over are listed on the request. Upstreams can be reached through an outbound proxy and priced with a price sheet of their own; aliases, proxies and price sheets have tabs on the same page. An optional **Concurrency limit** suits relays and accounts that allow only so many requests at once: when the upstream is full, a conversation that stays on it waits for a free slot, other requests go to the next upstream, and when every upstream is full a request waits and then receives a busy error. **Specs…** in an upstream's model list sets by hand a model's context window, maximum output, and whether it reasons and takes images, for a model the price table lacks or gets wrong; the values set there are used in place of the price table's. A connection test times the DNS lookup and the TCP, TLS and proxy handshakes without incurring any cost; an inference test measures the time to first token and estimates its cost before it runs. +An upstream's models are the ones it lists plus any added by hand. Upstreams often leave out models they serve: an account backend hides newer models, a relay lists only some. **Add models…** in an upstream's model list adds such models by their exact IDs, several at a time. An ID cannot contain `*` or `?` or have spaces around it, is at most 256 characters, and is added once; the dialog points out an ID that breaks these rules, or one the upstream already lists, before saving. A model added by hand is marked **Manual**, and routing and failover, aliases, routing rules that name a model, a key's allowed models, the model list clients see, the dry run and the speed test all treat it like a listed model. The summary at the top of the list counts the models the upstream lists apart from those added by hand. Hovering over a manual model shows **Remove**, which takes effect at once, with **Undo** in the message that follows. For an upstream that lists no models, the same dialog replaces the manual model list, and the models added there are its whole list. + The Aliases tab gives a model the name clients use for it. An alias lists the names the same model has on different upstreams, such as `claude-sonnet-5` on Anthropic and `us.anthropic.claude-sonnet-5-v1:0` on Bedrock; every upstream that offers one of them serves the alias under its own name, and they back each other up. Clients see aliases in their model lists, and answers carry the name the client asked for, while the request log shows the model each upstream was sent. When the same Claude model has different names on the official API, Bedrock, Vertex or OpenRouter, the tab and the new-alias dialog suggest grouping them. An alias can also be created from an upstream's model list. The dialog shows which upstream receives which name and warns when the name would take over another upstream's model of the same name. A key whose model scope allows an upstream model can also use the aliases that list it. Each upstream is also compared over the last 7 days with the others serving the same model, and a deviation is marked next to its name in the list: **Model name differs** when answers name a model other than the one sent, **Input reported high** or **Input reported low** when the input tokens it reports, as a multiple of the gateway's own estimate, are well off the other upstreams', and **Low cache reads** when follow-up turns read a smaller share of their input from the prompt cache. Hovering over a mark shows the evidence and the sample sizes, and a deviation is marked only when both sides have enough samples. @@ -77,7 +79,7 @@ The MCP page covers what clients load from their own configuration files, which - **Skills and hooks:** the installed skills and configured hooks, with the client each belongs to; skills in the shared `~/.agents/skills` folder are listed as such. - **Findings:** client configuration, skills, hooks, slash commands, subagents and project instruction files are scanned for hidden characters, prompt injection, dangerous commands and overly broad permissions, and each finding is graded high, medium or low. The scan only reports; it never changes a file. -The app watches these files while it runs, and a new finding raises a system notification. +The app watches these files while it runs, and a new finding raises a system notification. After a file is edited, only the findings that are new are reported; those already in it are not reported again, even when they moved to another line. ## Plugins @@ -85,11 +87,11 @@ Plugins are short JavaScript files that change requests before they go to an ups ## Settings -Settings has seven sections. Connection lists the local core and the saved remote cores, described in [Connecting to a remote core](/docs/lite/remote-core). General sets the language, the appearance, what the menu bar item shows on macOS, launch at login, whether notices arrive as system notifications, in the app only or not at all, and shows hidden guidance hints again. Listening sets who can reach the gateway (this machine only, the local network of a chosen interface, or every interface), its port and the allowed address ranges. Failover sets how long a failing upstream is paused before requests go to the next one: after how many consecutive failures, for how long, and separate pauses for an insufficient balance, a used-up quota and rate limits. It also sets how long to wait for a streamed answer to start, whether a stream that has not started by then moves to the next upstream (off by default), and how long in total a request may wait for a free slot on a full upstream or for a key's per-minute or per-hour limit, 30 seconds by default. Log retention sets how long request payloads and request records are kept, and a size cap for payloads. About shows the version, checks for updates and produces a diagnostics bundle with keys and addresses masked. Uninstall restores every connected client and removes the autostart entry, and is meant to be run before the app is deleted. +Settings has seven sections. Connection lists the local core and the saved remote cores, described in [Connecting to a remote core](/docs/lite/remote-core). General sets the language, the appearance, what the menu bar item shows on macOS (or that it is hidden), launch at login, whether notices arrive as system notifications, in the app only or not at all, and shows hidden guidance hints again. Listening sets who can reach the gateway (this machine only, the local network of a chosen interface, or every interface), its port and the allowed address ranges. Failover sets how long a failing upstream is paused before requests go to the next one: after how many consecutive failures, for how long, and separate pauses for an insufficient balance, a used-up quota and rate limits. It also sets how long to wait for a streamed answer to start, whether a stream that has not started by then moves to the next upstream (off by default), and how long in total a request may wait for a free slot on a full upstream or for a key's per-minute or per-hour limit, 30 seconds by default. Log retention sets how long request payloads and request records are kept, and a size cap for payloads. About shows the version, checks for updates and produces a diagnostics bundle with keys and addresses masked. Uninstall restores every connected client and removes the autostart entry, and is meant to be run before the app is deleted. ## Menu bar, system tray and notifications -On macOS the menu bar shows today's tokens above today's cost; the numbers turn orange when a subscription quota is nearly used up and red when it is, and Settings can reduce the item to the icon or to the numbers. +On macOS the menu bar shows today's tokens above today's cost; the numbers turn orange when a subscription quota is nearly used up and red when it is. **Menu bar** in Settings › General can reduce the item to the icon or to the numbers, or set it to **Hidden**, which takes it off the menu bar: the gateway keeps running in the background, after a launch at login as well, and opening ThinkWatch Lite again from Finder or Spotlight shows the main window. Clicking it opens a native menu. **Open ThinkWatch Lite** always comes first, followed by unread notices and a **Today** block: today's tokens in large type, with requests, failures and cost on the line below and a small chart of tokens per hour beside them. The block's top line gives the gateway's state, the server's name when connected to a remote core, and the generation speed over the last minute. Below it, each quota window an upstream reports has a row with how much is used and when it resets (subscription accounts and GLM Coding Plan upstreams; a plan billed in credits shows the credits left under the bar), followed by the requests in progress. The actions come last: choosing the upstream of a manually selected group, copying the gateway address, which is shown beside the item, or the default key, installing a new version when one is available, settings, switching connections and checking for updates, all without opening the main window. diff --git a/src/content/docs-lite/en/import-links.md b/src/content/docs-lite/en/import-links.md index 1e9ded5..6fd8e92 100644 --- a/src/content/docs-lite/en/import-links.md +++ b/src/content/docs-lite/en/import-links.md @@ -23,7 +23,7 @@ The web form suits emails and dashboards whose users may not have the app yet. T | `name` | No | The upstream's name in the app. When omitted, the app derives one from the address. | | `protocol` | No | `anthropic`, `openai-chat`, `openai-responses` or `gemini`. When omitted, the app detects the protocol from the address. | | `key` | No | The API key, stored as given. Letters, digits and `- _ . ~ + / = :` only. | -| `models` | No | Comma-separated model IDs. The app uses this list when the service does not list its models itself. | +| `models` | No | Comma-separated model IDs, added to the upstream by hand. The app offers them next to the models the service lists, so a service that lists only some of its models can name the rest here; when the service lists none, they are its whole list. | Encoding rules: diff --git a/src/content/docs-lite/zh-CN/failover-and-load-balancing.md b/src/content/docs-lite/zh-CN/failover-and-load-balancing.md index 431d7a5..dd08cf0 100644 --- a/src/content/docs-lite/zh-CN/failover-and-load-balancing.md +++ b/src/content/docs-lite/zh-CN/failover-and-load-balancing.md @@ -4,7 +4,7 @@ ThinkWatch Lite 把每个中转站的每把密钥建成一个上游,再把多 ## 准备 -- 已[安装](/zh-CN/lite/#install) ThinkWatch Lite,并已在客户端页接管客户端。本文按 2026.10.6 版编写。 +- 已[安装](/zh-CN/lite/#install) ThinkWatch Lite,并已在客户端页接管客户端。本文按 2026.10.10 版编写。 - 各中转站的接口地址和 API 密钥。 ## 步骤 @@ -32,7 +32,7 @@ ThinkWatch Lite 把每个中转站的每把密钥建成一个上游,再把多 - **并发上限。**设置了「并发上限」的上游同时最多接收这么多请求。上游已满时,留在它上面的对话等待空位,等不到再换下一个,其他请求直接交给下一个成员;所有成员都满时,请求等待最先空出的位置,最长为「设置 › 故障转移」中的「最多等待空位」(默认 30 秒),仍无空位则返回 429 并带 `Retry-After`;此前已有尝试发出时,返回那次尝试的错误。密钥的分钟、小时用量上限共用这段等待;流量页会标出每一次跳过和排队时间。 - **暂停。**失败的上游按「设置 › 故障转移」暂停使用,默认值为:「连续失败」3 次后暂停 60 秒,此后每次加倍,最长 600 秒;「余额不足」暂停 30 分钟;「额度用完」暂停到重置时刻,未给出时暂停 60 分钟;「限流」按上游要求的等待时间暂停,最长 60 分钟。只有一个上游的规则不受暂停影响;所有成员都在暂停时,网关仍会逐个尝试。 - **会话与提示缓存。**同一轮之内(客户端回传工具结果期间),请求沿用这一轮开头确定的规则和回答它的上游。跨轮时,如果上次回答在五分钟以内、且读写了至少 1,024 个缓存 token,对话继续使用该上游,因为换到别处要按全价重建缓存;否则,或者该上游正在暂停时,由策略重新排序,「轮询」正是在这时轮到下一个成员。请求「路由」标签中的「对话延续」一行说明请求是否因此留在原上游。 -- **模型名相同。**每个成员收到的都是客户端请求的模型名,或者规则改写之后的模型名。模型列表中没有该模型的成员会被跳过;没有模型列表的成员照常尝试,它返回 404 时请求换到下一个。 +- **模型名相同。**每个成员收到的都是客户端请求的模型名,或者规则改写之后的模型名。模型列表中没有该模型的成员会被跳过;没有模型列表的成员照常尝试,它返回 404 时请求换到下一个。成员能服务、却没有列进模型列表的模型,可以在上游页该成员的模型列表中选择「添加模型…」加上。 - **回退到另一个模型。**添加一条规则:条件「选定上游」选择后备上游,「命中后」选择「继续匹配」,在「改写参数」的「模型改为」中填写它的模型。这样的规则在每次选定上游之后判断,故障转移之后同样适用。更换模型后已缓存的 prompt 不再命中,费用按发出的模型名计算。 相关文档:[切换中转站、上游或模型,无需重启 Claude Code 与 Codex](/zh-CN/docs/lite/switch-upstreams-without-restart/)、[功能详解](/zh-CN/docs/lite/features/#路由与故障转移)、[安装与更新](/zh-CN/docs/lite/install/)。 diff --git a/src/content/docs-lite/zh-CN/features.md b/src/content/docs-lite/zh-CN/features.md index eb4669e..fccaad7 100644 --- a/src/content/docs-lite/zh-CN/features.md +++ b/src/content/docs-lite/zh-CN/features.md @@ -41,6 +41,8 @@ WSL 2 默认使用 NAT 网络,此时 Windows 上的网关无法从 WSL 内访 上游是网关转发请求的目标:Anthropic、OpenAI、Google Gemini、DeepSeek 或任何兼容接口的 API 密钥,Amazon Bedrock(API 密钥、访问密钥或 AWS 配置文件),在应用内登录的 ChatGPT 账号或 Z.ai / BigModel 账号,OpenRouter 等中转服务,以及 Ollama 等本机模型。ChatGPT 账号显示订阅额度与重置时间;GLM Coding Plan 的上游(地址在 `api.z.ai` 或 `open.bigmodel.cn` 上,在应用内登录或手动填写密钥均可)同样显示:5 小时与每周额度,积分制套餐另外显示剩余积分(「剩余 1,976 / 2,000 积分」)。客户端与上游的 API 格式不同时,请求在 Anthropic Messages、OpenAI Chat Completions、OpenAI Responses 与 Gemini 之间自动转换,无法转换的字段会在请求上逐一列出。上游可以经出站代理访问,也可以使用单独的价目表计价,别名、代理与价目表在同一页的标签中管理。可选的「并发上限」适用于限制并发的中转站或账号:上游已满时,留在它上面的对话等待空位,其他请求交给下一个上游;所有上游都满时,请求先等待,仍无空位则返回繁忙错误。在上游的模型列表中选择「规格…」,可以手动设置模型的上下文窗口、输出上限,以及是否支持推理与图片输入,适用于价目表中没有或数值有误的模型,手动设置的值优先于价目表。链路测速测量 DNS 解析以及 TCP、TLS、代理握手的耗时,不产生费用;推理测速测量首个 token 的时间,运行前先给出费用预估。 +一家上游的模型,是它自己列出的模型加上手动添加的模型。上游常常没有列全它能服务的模型:账号类的后端会隐藏较新的模型,中转站只列出一部分。在上游的模型列表中选择「添加模型…」,可以按确切的模型 ID 添加这类模型,一次可以添加多个。模型 ID 不能含 `*` 或 `?`,前后不能有空格,最多 256 个字符,且不能重复;不符合要求的,以及上游已经列出的,对话框在保存之前当场指出。手动添加的模型标有「手动」,路由与故障转移、别名、指定模型的路由规则、密钥的可用模型、客户端看到的模型列表、试算与推理测速都把它当作列出的模型。列表顶部的摘要把上游列出的模型与手动添加的模型分开计数。悬停在手动添加的模型上会出现「移除」,立即生效,随后的提示中可以「撤销」。上游不提供模型列表时,同一个对话框取代原来的手动清单,手动添加的模型就是它的全部模型。 + 别名标签为模型设定客户端使用的名称。一个别名列出同一个模型在各家上游的名称,例如 Anthropic 上的 `claude-sonnet-5` 和 Bedrock 上的 `us.anthropic.claude-sonnet-5-v1:0`;提供其中任一名称的上游都能以自己的名称服务这个别名,并互为备用。客户端的模型列表里能看到别名,回答里的模型名写成客户端请求的名称,请求记录则保留每家上游实际收到的模型。同一个 Claude 模型在官方 API、Bedrock、Vertex 或 OpenRouter 上名称不同时,别名标签和新建别名对话框会建议合并。也可以在上游的模型列表里直接起别名。对话框列出每家上游将收到的名称,名称会接管另一家上游的同名模型时给出提示。密钥的可见模型允许某个上游模型时,列有它的别名也可以使用。 每个上游还会与服务同一模型的其他上游对照最近 7 天的数据,偏差直接标在上游列表中它的名称旁:回答中的模型名与发出的不同,标为「模型名不符」;上游报告的输入 token 相对网关本地估算的倍数明显高于或低于其他上游,标为「输入 token 偏多」或「输入 token 偏少」;后续轮次中从提示缓存读取的输入比例偏低,标为「缓存读取偏低」。悬停可以查看依据与样本数,两边样本都足够时才标出偏差。 @@ -77,7 +79,7 @@ MCP 页管理客户端从自己的配置文件中加载的内容,这些内容 - **技能与钩子**:列出已安装的技能和配置的钩子,以及各自所属的客户端;共用的 `~/.agents/skills` 目录中的技能单独标为共用目录。 - **发现**:扫描客户端配置、技能、钩子、斜杠命令、subagent 与项目指令文件,检查隐藏字符、提示注入、危险命令与过宽权限四类问题,每项发现按高、中、低分级。扫描只报告,不修改任何文件。 -应用运行期间会监视这些文件,出现新的发现时发送系统通知。 +应用运行期间会监视这些文件,出现新的发现时发送系统通知。文件被编辑后只报告新出现的发现,原有的发现即使换了行号也不再重复报告。 ## 插件 @@ -85,11 +87,11 @@ MCP 页管理客户端从自己的配置文件中加载的内容,这些内容 ## 设置 -设置页分为七节。「连接」列出本机 core 和已保存的远程 core,详见[连接远程 core](/zh-CN/docs/lite/remote-core)。「通用」设置语言、外观、菜单栏显示的内容(仅 macOS)、开机启动、提醒以系统通知发送、仅在应用内显示还是关闭,并可让设为不再显示的引导提示重新显示。「网关监听」设置网关的访问范围(仅本机、所选网卡所在的局域网或所有网卡)、端口和放行网段。「故障转移」设置上游失败后暂停多久、请求交给下一个上游:连续失败几次后暂停、暂停多长,以及余额不足、额度用完和限流时各自的暂停时长;还设置流式回答等待开头的时长、开头超时时是否转到下一个上游(默认关闭),以及上游并发已满或密钥的分钟、小时上限用满时请求合计最多等待的时长(默认 30 秒)。「日志保留」分别设置请求报文与请求记录的保留天数,以及报文的空间上限。「关于」显示版本、检查更新,并可生成诊断包,其中的密钥与地址均已脱敏。「卸载」还原所有已接管的客户端并取消开机启动,应在删除应用之前执行。 +设置页分为七节。「连接」列出本机 core 和已保存的远程 core,详见[连接远程 core](/zh-CN/docs/lite/remote-core)。「通用」设置语言、外观、菜单栏显示的内容(仅 macOS,也可设为不显示)、开机启动、提醒以系统通知发送、仅在应用内显示还是关闭,并可让设为不再显示的引导提示重新显示。「网关监听」设置网关的访问范围(仅本机、所选网卡所在的局域网或所有网卡)、端口和放行网段。「故障转移」设置上游失败后暂停多久、请求交给下一个上游:连续失败几次后暂停、暂停多长,以及余额不足、额度用完和限流时各自的暂停时长;还设置流式回答等待开头的时长、开头超时时是否转到下一个上游(默认关闭),以及上游并发已满或密钥的分钟、小时上限用满时请求合计最多等待的时长(默认 30 秒)。「日志保留」分别设置请求报文与请求记录的保留天数,以及报文的空间上限。「关于」显示版本、检查更新,并可生成诊断包,其中的密钥与地址均已脱敏。「卸载」还原所有已接管的客户端并取消开机启动,应在删除应用之前执行。 ## 菜单栏、系统托盘与通知 -macOS 菜单栏显示今日 token 与今日费用,订阅额度紧张时数字变橙、用完变红;设置里可以改为仅标识或仅数值。 +macOS 菜单栏显示今日 token 与今日费用,订阅额度紧张时数字变橙、用完变红。「设置 › 通用」中的「菜单栏」可以改为仅标识或仅数值,也可以选「不显示」,菜单栏中不再出现该项:网关照常在后台运行,开机启动时也是如此;从访达或聚焦搜索再次打开 ThinkWatch Lite,即显示主窗口。 点开是原生菜单。第一项始终是「打开主界面」,其后是未读的提醒和「今日」一栏:今日 token 以大字显示,下方一行为请求数、失败数与费用,旁边是按小时统计 token 的小图。这一栏的顶行显示网关状态、连接远程 core 时的服务器名称,以及最近一分钟的生成速度。再往下,上游报告的每个额度窗口各占一行,显示已用比例与重置时间(订阅账号与 GLM Coding Plan 上游;积分制套餐在额度条下方显示剩余积分),然后是进行中的请求。最后是常用操作:切换手动选择策略组中的上游、复制网关地址(菜单项右侧显示该地址)和默认密钥、有新版本时安装新版本、设置、切换连接、检查更新,不必先打开主界面。 diff --git a/src/content/docs-lite/zh-CN/import-links.md b/src/content/docs-lite/zh-CN/import-links.md index 6e11898..b86a6d9 100644 --- a/src/content/docs-lite/zh-CN/import-links.md +++ b/src/content/docs-lite/zh-CN/import-links.md @@ -23,7 +23,7 @@ ThinkWatch Lite 支持通过链接预填一个新的上游。中转站或模型 | `name` | 否 | 上游在应用中的名称。省略时由应用按地址生成。 | | `protocol` | 否 | `anthropic`、`openai-chat`、`openai-responses` 或 `gemini`。省略时由应用按地址识别。 | | `key` | 否 | API 密钥,按原样保存。只能包含字母、数字与 `- _ . ~ + / = :`。 | -| `models` | 否 | 以逗号分隔的模型 ID。服务本身不提供模型列表时,应用使用这份清单。 | +| `models` | 否 | 以逗号分隔的模型 ID,作为手动添加的模型写入上游。应用把它们与服务自己列出的模型一起使用,只列出部分模型的服务可以在这里写上其余的模型;服务不提供模型列表时,它们就是全部模型。 | 编码规则: From 740fd3162bc5eb641a262baeec62ce898deeddec Mon Sep 17 00:00:00 2001 From: fylorn <249551762+fylorn@users.noreply.github.com> Date: Fri, 9 Oct 2026 12:02:05 +0800 Subject: [PATCH 2/3] Core docs from v0.66.0 `CORE_DOCS_REF=v0.66.0 pnpm core-docs`: the configuration reference describes providers[].models as models added by hand and explains which models an upstream has. Co-Authored-By: Claude Opus 5.5 --- src/data/core-docs/config.md | 12 +++++++++++- src/data/core-docs/config.zh-CN.md | 4 +++- src/data/core-docs/manifest.json | 6 +++--- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src/data/core-docs/config.md b/src/data/core-docs/config.md index 01c9386..fae4f75 100644 --- a/src/data/core-docs/config.md +++ b/src/data/core-docs/config.md @@ -398,7 +398,7 @@ Upstreams: the APIs requests are forwarded to. | `forward_client_identity` | bool | `false` | Also send the client's own identity: its `User-Agent`, identity headers such as `x-app` and `originator`, and identity fields in the request body such as `metadata.user_id`. Values are the client's, never made up. Off: requests carry ThinkWatch's `User-Agent` and no client identity. For upstreams that admit only certain clients (Kimi For Coding, Bailian Coding Plan, relays restricted to official clients). Not available for `chatgpt`. | | `proxy` | string | `direct` | `direct`; `system`, the proxy in the core process's `HTTPS_PROXY`, `HTTP_PROXY` or `ALL_PROXY` environment variables; or the name of an entry in `proxies`. | | `on_proxy_fail` | `fail` \| `direct` | `fail` | When the proxy cannot be reached: `fail` the request, or go `direct`. | -| `models` | list of strings | `[]` | Models to assume when the upstream does not answer `/v1/models`. | +| `models` | list of strings | `[]` | Models added by hand, by exact id, for those the upstream serves but leaves out of its list. They count as offered together with the models the upstream lists, or are the whole list when it lists none: they appear in `/v1/models` and requests for them are routed here. `models_only` still applies. No wildcards, no duplicates, at most 256 characters each. | | `models_only` | list of strings | — | Use only these of the upstream's models, as ids or globs. Others are not listed and are not routed here. Unset: all of them. Empty is refused; use `disabled`. | | `billing` | `per-token` \| `free` | `per-token` | `per-token`: cost is usage times the price in the upstream's price sheet, subscription accounts included. `free`: cost is recorded as 0. | | `pricing` | string | — | Name of a price sheet under `pricing.sheets`. Unset: the default price table. | @@ -435,6 +435,16 @@ providers: billing: free ``` +An upstream's models are the ones it lists on `/v1/models` (for Bedrock, the +region's model list) and the ones written in `models`. Upstreams often leave +models out of their list: a relay lists only some of what it serves, an +account backend hides new models from older clients. A model added in `models` +is listed in `/v1/models`, can be named by an alias, pinned in a rule and +allowed for a key, and is routed to this upstream like a listed one; +`models_only` applies to both. An upstream that lists nothing has exactly the +models in `models`; one with neither lists no model and is still sent requests +for any model. + A request carries the request itself and the headers its upstream needs, and nothing else from the client: the credential and the headers written in `headers`; ThinkWatch's own `User-Agent`; and, from the client's request, only diff --git a/src/data/core-docs/config.zh-CN.md b/src/data/core-docs/config.zh-CN.md index 8279e36..6e5f3e3 100644 --- a/src/data/core-docs/config.zh-CN.md +++ b/src/data/core-docs/config.zh-CN.md @@ -296,7 +296,7 @@ clients: | `forward_client_identity` | 布尔 | `false` | 同时发送客户端自己的身份:它的 `User-Agent`、`x-app` 和 `originator` 等身份请求头,以及请求体中的身份字段(如 `metadata.user_id`)。发送的都是客户端的原值,不做伪造。关闭时请求使用 ThinkWatch 的 `User-Agent`,不带客户端身份。用于只接受特定客户端的上游(Kimi For Coding、百炼 Coding Plan、只允许官方客户端的中转站)。`chatgpt` 不可用。 | | `proxy` | 字符串 | `direct` | `direct`;`system`,即 core 进程环境变量 `HTTPS_PROXY`、`HTTP_PROXY`、`ALL_PROXY` 中的代理;或 `proxies` 中某一项的名字。 | | `on_proxy_fail` | `fail` \| `direct` | `fail` | 代理不可用时:请求失败(`fail`),或改为直连(`direct`)。 | -| `models` | 字符串列表 | `[]` | 上游不支持 `/v1/models` 时,按这份清单认定它提供的模型。 | +| `models` | 字符串列表 | `[]` | 手动添加的模型,写确切的 ID:上游能服务、却没有列进清单的模型。它们和上游列出的模型一起算作这家提供的模型,上游不提供清单时就是全部:出现在 `/v1/models` 里,相应的请求也会路由到这家。`models_only` 照样适用。不支持通配,不能重复,每项最多 256 个字符。 | | `models_only` | 字符串列表 | — | 只使用这家的这些模型,写 ID 或通配。范围外的模型不出现在模型列表里,也不会路由到这家。不写:全部。写空列表会被拒绝,暂停使用请用 `disabled`。 | | `billing` | `per-token` \| `free` | `per-token` | `per-token`:费用为用量乘以所选价目表中的单价,订阅账号同样如此。`free`:费用记为 0。 | | `pricing` | 字符串 | — | `pricing.sheets` 中某张价目表的名字。不写:默认价目表。 | @@ -329,6 +329,8 @@ providers: billing: free ``` +一家上游提供的模型,是它在 `/v1/models` 列出的模型(Bedrock 为所在区域的模型清单),加上 `models` 中手动添加的模型。上游的清单常常不全:中转站只列出一部分,账号类的后端对旧版本客户端隐藏新模型。写进 `models` 的模型出现在 `/v1/models` 里,可以写进别名、在规则中指定、在密钥的 `allow` 中放行,也和列出的模型一样路由到这家;`models_only` 对两者同样适用。上游不提供清单时,`models` 就是它的全部模型;两者都没有时,它不列出任何模型,但任何模型的请求仍可能路由到这家。 + 每个请求只带请求本身和上游需要的请求头,客户端的其他信息一律不发:凭据和 `headers` 中写的请求头、ThinkWatch 自己的 `User-Agent`,以及客户端请求中该上游协议使用的请求头(Anthropic 为 `anthropic-*`,OpenAI 为 `Idempotency-Key` 和 `X-Client-Request-Id`,Gemini 没有)。客户端自动填写的身份字段(如 Claude Code 的 `metadata.user_id`)从请求体中去掉。只接受特定客户端的上游,打开 `forward_client_identity`。 ChatGPT 账号上游(`protocol: chatgpt`)只接受桌面应用登录得到的凭据,不能手写。不支持 Claude 和 Google 的订阅登录,请使用 API 密钥。 diff --git a/src/data/core-docs/manifest.json b/src/data/core-docs/manifest.json index b9d72d4..3e81802 100644 --- a/src/data/core-docs/manifest.json +++ b/src/data/core-docs/manifest.json @@ -1,9 +1,9 @@ { "repository": "ThinkWatchProject/ThinkWatch-Core", - "ref": "v0.65.0", + "ref": "v0.66.0", "files": { - "docs/config.md": "09b2e4d1fa3fb07b53b450ebba3293d78a579ef26488e00ad5f29e2a9cfe4431", - "docs/config.zh-CN.md": "e1b5a952b3b57210201ea4af749ada20e3758db9e28da0edf6d0617fcf1cbbe4", + "docs/config.md": "91818dc4be92174ddcae4c41c8fdd5d514d80a0913dea84b4dcdc656380752f0", + "docs/config.zh-CN.md": "9550dd8d65a69b3096dc53337d8ee439f239ddc8185f4faa7b1171373876aad0", "docs/server.md": "5e1e9b901bef2b46d417aea057a1db24c78457d3c1938b8540ecb4766515b68f", "docs/server.zh-CN.md": "1f508e7c39b8ded28653773ca4d8701e6bdc2247bcd359c3a8fd00fd1401a6ff" } From 4fc0749dcaf7c00d02eb8d0e345392f336f80898 Mon Sep 17 00:00:00 2001 From: fylorn <249551762+fylorn@users.noreply.github.com> Date: Fri, 9 Oct 2026 12:04:12 +0800 Subject: [PATCH 3/3] Import page and link builder: "Models added by hand", as in the app MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The app's import dialog now labels the models field "Models added by hand" («手动添加的模型») like the rest of the app. The site's import page, the link builder and their field errors, and the dialog description in import-links.md (en, zh-CN) follow. Co-Authored-By: Claude Opus 5.5 --- src/components/ImportLinkBuilder.astro | 8 ++++---- src/components/pages/ImportPage.astro | 8 ++++---- src/content/docs-lite/en/import-links.md | 2 +- src/content/docs-lite/zh-CN/import-links.md | 2 +- 4 files changed, 10 insertions(+), 10 deletions(-) diff --git a/src/components/ImportLinkBuilder.astro b/src/components/ImportLinkBuilder.astro index df35847..956ce09 100644 --- a/src/components/ImportLinkBuilder.astro +++ b/src/components/ImportLinkBuilder.astro @@ -18,7 +18,7 @@ const t = zh protocol: "接口协议", auto: "自动识别(不写入链接)", key: "API 密钥(可选)", - models: "手动模型清单(可选,逗号分隔)", + models: "手动添加的模型(可选,逗号分隔)", appLink: "应用链接", webLink: "网页链接", copy: "复制", @@ -35,7 +35,7 @@ const t = zh url: "接口地址不符合要求:须为 https 地址(http 仅限 localhost、127.0.0.1、[::1]),不含账号、查询串、片段、空白与 % $ { } 等字符。", protocol: "接口协议不受支持。", key: "API 密钥只能包含字母、数字与 - _ . ~ + / = :,最长 512 个字符。", - models: "模型清单不符合要求:以逗号分隔,每项只含字母、数字与 - _ . : / @ +,最多 64 项。", + models: "手动添加的模型不符合要求:以逗号分隔,每项只含字母、数字与 - _ . : / @ +,最多 64 项。", }, } : { @@ -46,7 +46,7 @@ const t = zh protocol: "Protocol", auto: "Auto-detect (left out of the link)", key: "API key (optional)", - models: "Manual model list (optional, comma-separated)", + models: "Models added by hand (optional, comma-separated)", appLink: "App link", webLink: "Web link", copy: "Copy", @@ -63,7 +63,7 @@ const t = zh url: "The base URL is not accepted: it must be an https address (http only for localhost, 127.0.0.1 and [::1]) without credentials, a query, a fragment, spaces or characters such as % $ { }.", protocol: "The protocol is not supported.", key: "The API key may contain only letters, digits and - _ . ~ + / = :, up to 512 characters.", - models: "The model list is not accepted: comma-separated, each entry only letters, digits and - _ . : / @ +, at most 64 entries.", + models: "The models added by hand are not accepted: comma-separated, each entry only letters, digits and - _ . : / @ +, at most 64 entries.", }, }; diff --git a/src/components/pages/ImportPage.astro b/src/components/pages/ImportPage.astro index 417c40f..7d7d9b0 100644 --- a/src/components/pages/ImportPage.astro +++ b/src/components/pages/ImportPage.astro @@ -36,7 +36,7 @@ const t = zh noKey: "未提供", show: "显示", hide: "隐藏", - models: "手动模型清单", + models: "手动添加的模型", open: "在 ThinkWatch Lite 中打开", notInstalled: "尚未安装 ThinkWatch Lite 时,先下载并安装,再回到此页面。", invalidTitle: "此导入链接无效", @@ -54,7 +54,7 @@ const t = zh url: "接口地址不符合要求:须为 https 地址(http 仅限本机),且不含账号、查询串或片段。", protocol: "接口协议不受支持。", key: "API 密钥包含不支持的字符。", - models: "模型清单不符合要求。", + models: "手动添加的模型不符合要求。", }, } : { @@ -73,7 +73,7 @@ const t = zh noKey: "Not provided", show: "Show", hide: "Hide", - models: "Manual model list", + models: "Models added by hand", open: "Open in ThinkWatch Lite", notInstalled: "If ThinkWatch Lite is not installed yet, download and install it, then return to this page.", invalidTitle: "This import link is not valid", @@ -92,7 +92,7 @@ const t = zh url: "The base URL is not accepted: it must be an https address (http only for this computer) without credentials, a query or a fragment.", protocol: "The protocol is not supported.", key: "The API key contains unsupported characters.", - models: "The model list is not accepted.", + models: "The models added by hand are not accepted.", }, }; diff --git a/src/content/docs-lite/en/import-links.md b/src/content/docs-lite/en/import-links.md index 6fd8e92..94dc25e 100644 --- a/src/content/docs-lite/en/import-links.md +++ b/src/content/docs-lite/en/import-links.md @@ -44,7 +44,7 @@ Limits: ## What the app does with a link 1. **Checks the link.** Every rule above is applied in the app, whatever the page that produced the link has checked. -2. **Shows a confirmation dialog.** The dialog states the host that will receive request content and the API key, in ASCII: an internationalized domain name is shown as punycode (`xn--…`), so a look-alike domain cannot pass for a familiar one. It also shows the base URL, the protocol, the key (hidden until revealed) and the model list. Only the name can be changed. Values are displayed as plain text. +2. **Shows a confirmation dialog.** The dialog states the host that will receive request content and the API key, in ASCII: an internationalized domain name is shown as punycode (`xn--…`), so a look-alike domain cannot pass for a familiar one. It also shows the base URL, the protocol, the key (hidden until revealed) and the models added by hand. Only the name can be changed. Values are displayed as plain text. 3. **Saves nothing before confirmation.** Until **Create** is chosen, the configuration is not written and the app makes no network request to the address: no connection test and no model listing. 4. **Creates one new upstream.** An import never changes, replaces or deletes an existing upstream. When the name is already in use, a different name must be entered; there is no option to overwrite. The new upstream is not made the default and is not added to any route. After creation it behaves like an upstream added by hand, including fetching its model list. 5. **Handles one link at a time.** Links that arrive while the dialog is open, or within a few seconds after it closes, are ignored and do not bring the window to the front. diff --git a/src/content/docs-lite/zh-CN/import-links.md b/src/content/docs-lite/zh-CN/import-links.md index b86a6d9..525fb63 100644 --- a/src/content/docs-lite/zh-CN/import-links.md +++ b/src/content/docs-lite/zh-CN/import-links.md @@ -44,7 +44,7 @@ ThinkWatch Lite 支持通过链接预填一个新的上游。中转站或模型 ## 应用如何处理链接 1. **校验链接。**上述规则全部在应用中执行,与生成链接的页面做过哪些校验无关。 -2. **显示确认对话框。**对话框写明接收请求内容与 API 密钥的主机,以 ASCII 显示:国际化域名显示为 punycode(`xn--…`),外形相近的域名无法冒充熟悉的域名。对话框同时显示 Base URL、接口协议、密钥(默认隐藏,可切换显示)与模型清单,其中只有名称可以修改。所有值都按纯文本显示。 +2. **显示确认对话框。**对话框写明接收请求内容与 API 密钥的主机,以 ASCII 显示:国际化域名显示为 punycode(`xn--…`),外形相近的域名无法冒充熟悉的域名。对话框同时显示 Base URL、接口协议、密钥(默认隐藏,可切换显示)与手动添加的模型,其中只有名称可以修改。所有值都按纯文本显示。 3. **确认之前不保存任何内容。**选择「创建」之前,应用不写入配置,也不向该地址发出任何网络请求:不检测连接,不获取模型列表。 4. **只创建一个新的上游。**导入不会修改、替换或删除已有的上游。名称已被使用时须改用其他名称,不提供覆盖选项。新上游不会被设为默认,也不会加入任何路由。创建之后,它与手动添加的上游相同,包括获取模型列表。 5. **一次只处理一条链接。**对话框打开期间,以及关闭后的几秒内到达的链接会被忽略,也不会把窗口调到前台。