1. 从一次真实的启动失败说起:Unable to connect 到底卡在哪
Claude Code 启动时抛出Unable to connect,很多人第一反应是网络问题,于是反复检查网络、重启终端,结果折腾半小时还是同样的报错。我试过在三个不同环境里复现这个问题,最后发现真正的原因往往藏在本地配置文件的读写状态里,而不是通道本身。
先把结论摆出来:Claude Code 在首次启动或配置变更后,会读取用户目录下的.claude.json。这个文件里有一个关键字段hasCompletedOnboarding,它标记的是「引导流程是否走完」。如果这个字段缺失、值为false,或者文件本身写入失败(权限、路径、JSON 语法错误),Claude Code 就会认为你还没完成初始化,于是尝试重新走引导流程。而引导流程里包含一次对服务端点的连通性探测,一旦探测目标不可达,就会直接报Unable to connect。
所以这个报错有两层含义:第一层是本地配置没就绪,第二层才是通道没就绪。排查顺序必须是先本地、后通道,否则你会在网络层面绕很久却找不到根因。
.claude.json的位置随系统不同而变化。macOS 和 Linux 通常在~/.claude.json,Windows 在C:\Users\<用户名>\.claude.json。你可以用一条命令确认它是否存在、内容是否合法:
# macOS / Linux ls -la ~/.claude.json && cat ~/.claude.json | python3 -m json.tool # Windows PowerShell Get-Content $env:USERPROFILE\.claude.json | ConvertFrom-Json如果python3 -m json.tool或ConvertFrom-Json报解析错误,说明文件已经损坏,这本身就是Unable to connect的常见诱因。JSON 里多一个逗号、少一个引号,Claude Code 读不到hasCompletedOnboarding,就会退回未完成状态。
还有一个容易被忽略的点:.claude.json是会被 Claude Code 频繁读写的文件。如果你在编辑器里手动改过它,同时 Claude Code 进程还在后台运行,就可能出现写入竞争,导致字段被覆盖回旧值。所以修改前先确认没有残留进程:
# 查看是否有 claude 相关进程 ps aux | grep -i claude # Windows tasklist | findstr /i claude这一步看起来简单,但它是后面所有操作的前提。配置文件状态不确定,后面改 endpoint、换 Key 都是白费功夫。接下来我会把.claude.json的字段结构、hasCompletedOnboarding的正确写法,以及如何把 endpoint 指向 TaoToken 的完整对照步骤拆开讲,每一步都给出可复制的片段和验证动作。
2. 读懂 .claude.json:hasCompletedOnboarding 与 endpoint 字段的读写逻辑
.claude.json本质上是一个状态文件,它记录的不只是「引导是否完成」,还包括你选择的模型、endpoint 地址、认证方式等。理解它的结构,才能判断Unable to connect是配置缺失还是通道问题。
一个健康的.claude.json大致长这样(字段会随版本增减,以下为常见结构):
{ "hasCompletedOnboarding": true, "lastOnboardingVersion": "1.0.0", "numStartups": 12, "theme": "dark", "env": { "ANTHROPIC_BASE_URL": "https://taotoken.net/api", "ANTHROPIC_AUTH_TOKEN": "sk-你的Key" } }这里有两个关键点。第一,hasCompletedOnboarding必须是布尔值true,不能是字符串"true",也不能是1。JSON 是强类型的,写成字符串 Claude Code 解析时会当成 falsy,照样报错。第二,env里的ANTHROPIC_BASE_URL决定了 Claude Code 往哪里发请求。如果你把 endpoint 指向了 TaoToken 的 API 地址,那么连通性探测的目标就是这个地址,通道是否就绪取决于这个地址能否正常响应。
为什么hasCompletedOnboarding会丢失?常见场景有三个:一是全新安装后引导流程中途退出,字段没写进去;二是手动编辑.claude.json时误删或格式错误;三是升级 Claude Code 版本后,旧配置文件结构不兼容,新版本读不到该字段。这三种情况都会让 Claude Code 认为你是「首次启动」,从而触发引导探测。
排查时我建议按这个顺序读文件:
# 1. 确认文件存在 test -f ~/.claude.json && echo "exists" || echo "missing" # 2. 提取关键字段,看是否可读 python3 -c " import json, os p = os.path.expanduser('~/.claude.json') with open(p) as f: d = json.load(f) print('hasCompletedOnboarding =', d.get('hasCompletedOnboarding')) print('base_url =', d.get('env', {}).get('ANTHROPIC_BASE_URL')) "如果第一步输出missing,说明文件根本没生成,Claude Code 每次启动都会当成首次运行。如果第二步抛异常,说明 JSON 损坏。如果hasCompletedOnboarding输出None,说明字段缺失。这三种结果对应三种修法,但核心动作都是补全字段并保证 JSON 合法。
关于 endpoint 的读写,还有一个细节:Claude Code 启动时会优先读环境变量,其次读.claude.json里的env。也就是说,如果你在 shell 里 export 了ANTHROPIC_BASE_URL,它会覆盖文件里的值。排查时要把两处都看一眼:
echo $ANTHROPIC_BASE_URL echo $ANTHROPIC_AUTH_TOKEN如果环境变量里是一个已经失效的地址,而文件里是正确的 TaoToken 地址,那么实际生效的是环境变量,报错依旧。这种情况在切换配置后特别常见,很多人改了文件却忘了清环境变量。
理解了读写优先级,你就能判断Unable to connect到底是「文件没写对」还是「环境变量在捣乱」。下一节给出可直接复制的配置片段,把hasCompletedOnboarding和 TaoToken endpoint 一次性配好。
3. 可复制配置:补全 hasCompletedOnboarding 并指向 TaoToken
这一节给的是可以直接粘贴的配置。操作前先备份原文件,避免改坏后无法回滚:
cp ~/.claude.json ~/.claude.json.bak然后写入下面这份完整配置。注意把sk-你的Key替换成你在 TaoToken 控制台创建的真实 Key,Key 的创建入口在 TaoToken API Keys。
{ "hasCompletedOnboarding": true, "lastOnboardingVersion": "1.0.0", "numStartups": 1, "theme": "dark", "env": { "ANTHROPIC_BASE_URL": "https://taotoken.net/api", "ANTHROPIC_AUTH_TOKEN": "sk-你的Key", "ANTHROPIC_MODEL": "claude-sonnet-4-20250514" } }这份配置里三件套齐全:Base URL 是https://taotoken.net/api,Key 放在ANTHROPIC_AUTH_TOKEN,Model ID 放在ANTHROPIC_MODEL。三者缺一不可,少任何一个都可能在启动或首次请求时报错。
如果你更习惯用环境变量而不是写进文件,可以在 shell 配置里加:
export ANTHROPIC_BASE_URL="https://taotoken.net/api" export ANTHROPIC_AUTH_TOKEN="sk-你的Key" export ANTHROPIC_MODEL="claude-sonnet-4-20250514"但要注意,环境变量和文件同时存在时,环境变量优先级更高。如果你两个地方都配了,确保值一致,否则会出现「文件里是对的、实际用的是错的」这种隐蔽问题。
对于使用 Claude Code 的 settings 文件(部分版本支持~/.claude/settings.json)的场景,可以写成:
{ "env": { "ANTHROPIC_BASE_URL": "https://taotoken.net/api", "ANTHROPIC_AUTH_TOKEN": "sk-你的Key", "ANTHROPIC_MODEL": "claude-sonnet-4-20250514" } }写完后做一次 JSON 合法性校验,这一步不能省:
python3 -m json.tool ~/.claude.json > /dev/null && echo "JSON OK"输出JSON OK才说明格式没问题。如果报错,根据提示的行号定位,通常是逗号或引号问题。
配置写好后,先别急着启动 Claude Code。把可能残留的进程清掉,再重新打开终端,让环境变量和文件都重新加载:
pkill -f claude # 然后新开一个终端窗口到这里,本地配置层面就绪了。hasCompletedOnboarding为true,endpoint 指向 TaoToken,三件套齐全。接下来要验证的是:这个配置能不能真正跑通一次请求。
4. 验证请求:从启动成功到首次对话的完整链路
配置改完,验证要分两步走:先确认 Claude Code 能正常启动不再报Unable to connect,再确认它能通过 TaoToken 完成一次真实对话。
第一步,启动 Claude Code:
claude如果配置正确,你会看到引导流程被跳过,直接进入交互界面。之前那个Unable to connect不再出现,说明hasCompletedOnboarding生效了,本地状态被识别为「已完成」。
第二步,发一条最简单的消息测试通道:
claude -p "用一句话说明什么是 JSON"-p是 print 模式,适合脚本化验证。如果通道正常,你会看到模型返回的内容。如果这一步报错,说明问题不在本地配置,而在 endpoint 或 Key。
为了更精确地定位,可以绕过 Claude Code,直接用 curl 打一次 TaoToken 的接口:
curl -s https://taotoken.net/api/v1/messages \ -H "Content-Type: application/json" \ -H "x-api-key: sk-你的Key" \ -H "anthropic-version: 2023-06-01" \ -d '{ "model": "claude-sonnet-4-20250514", "max_tokens": 64, "messages": [{"role": "user", "content": "ping"}] }'返回里如果包含content字段和模型输出,说明 Key 和 endpoint 都没问题,问题只可能在 Claude Code 的配置读取上。如果返回 401,说明 Key 无效或没带上;如果返回连接超时,说明通道层面有问题,需要检查网络出口。
实测下来,把这两步分开验证能省很多时间。很多人一看到Unable to connect就去查网络,其实先跑一遍 curl 就能判断通道是否就绪。通道没问题,就回到.claude.json找原因;通道有问题,再去看 endpoint 和 Key。
验证通过后,你可以正常使用 Claude Code 做代码补全、重构、解释。如果后续还要接入更多模型或做长期编码任务,可以了解 TaoToken Coding Plan,它针对持续性的编码场景做了额度优化。想先体验模型对话能力,可以从 模型对话 入口试起。
5. 常见报错对照排查:401、local proxy failed、reading choices、OAuth
即使配置写对了,实际使用中还是会遇到各种报错。这一节把几个高频错误和对应原因列出来,方便你对照定位。
401 Unauthorized:Key 无效、过期,或者请求头里没带上。Claude Code 用的是ANTHROPIC_AUTH_TOKEN,curl 测试用的是x-api-key,两者别搞混。如果 curl 能通但 Claude Code 报 401,检查.claude.json里的ANTHROPIC_AUTH_TOKEN是否和 curl 用的 Key 一致。另外注意 Key 前后不要有空格,复制时容易带上换行。
local proxy failed:这个报错通常出现在配置了本地代理地址的情况下。如果你之前把ANTHROPIC_BASE_URL指向过http://localhost:xxxx之类的本地地址,而那个服务没启动,就会报这个。解决方法是把 endpoint 改回https://taotoken.net/api,或者确认本地服务确实在运行。排查命令:
curl -s -o /dev/null -w "%{http_code}" https://taotoken.net/api返回 200 或 4xx 都说明地址可达,返回 000 说明连不上。
reading choices 相关报错:这类错误一般出现在响应解析阶段,说明请求发出去了、也收到了响应,但响应结构不符合预期。常见原因是 Model ID 写错,或者 endpoint 路径不对。确认ANTHROPIC_MODEL是有效值,ANTHROPIC_BASE_URL是https://taotoken.net/api而不是带多余路径的地址。
OAuth 相关报错:如果你之前用 OAuth 方式登录过,.claude.json里可能残留了旧的认证字段,和新的ANTHROPIC_AUTH_TOKEN冲突。处理方式是清掉旧字段,只保留 Token 认证。可以先备份,再手动删除oauthAccount之类的键,或者干脆用一份干净的配置覆盖。
排查时有一个通用动作:把.claude.json里的env和 shell 环境变量都打印出来对比,确保没有互相覆盖。前面提过环境变量优先级更高,这是最容易踩的坑。
echo "--- shell env ---" echo $ANTHROPIC_BASE_URL echo $ANTHROPIC_AUTH_TOKEN echo "--- file env ---" python3 -c " import json, os d = json.load(open(os.path.expanduser('~/.claude.json'))) print(d.get('env', {})) "两处输出一致,才说明配置没有冲突。不一致就以环境变量为准,或者把环境变量清掉让文件生效。
还有一个细节:Claude Code 不同版本对字段名的要求略有差异。如果你升级过版本后突然报错,先看官方文档确认当前版本支持的字段名。接入相关的完整说明在 TaoToken 接入文档,里面有各客户端的配置示例。
6. 把配置固化下来:让下次启动不再踩同样的坑
排查完一次,最好把配置固化,避免下次升级或换机器时重蹈覆辙。我的做法是维护一份最小可用的.claude.json模板,放在版本控制里(Key 用占位符,不提交真实值),换环境时复制过去改 Key 即可。
模板长这样:
{ "hasCompletedOnboarding": true, "env": { "ANTHROPIC_BASE_URL": "https://taotoken.net/api", "ANTHROPIC_AUTH_TOKEN": "__FILL_ME__", "ANTHROPIC_MODEL": "claude-sonnet-4-20250514" } }换机器时,把__FILL_ME__替换成真实 Key,再跑一次 JSON 校验和 curl 验证,基本一次就能通。
另外,养成「改配置前先备份、改完先校验」的习惯。.claude.json是会被程序读写的文件,手动编辑有风险,备份能让你随时回滚。校验用python3 -m json.tool一行命令就够,成本极低但能挡掉大部分低级错误。
如果你在多个项目间切换,需要不同的 endpoint 或模型,可以用环境变量在启动时临时覆盖,而不是反复改文件:
ANTHROPIC_MODEL="claude-sonnet-4-20250514" claude这样文件保持稳定,临时需求用环境变量解决,减少文件被写坏的概率。
最后提醒一点:Unable to connect这个报错本身不区分「本地配置问题」和「通道问题」,所以排查一定要有顺序。先确认.claude.json存在且 JSON 合法,再确认hasCompletedOnboarding为true,然后确认 endpoint 和 Key 正确,最后用 curl 验证通道。这个顺序走下来,绝大多数情况都能定位到具体环节。配置片段和验证命令都在上面,直接复制改 Key 就能用。