已关闭
auth: 环境变量 token 覆盖本地登录时,login 与 status 缺乏可复制的根治指引 #613
aflyingto创建于  9月30日关闭于  15 天前
aflyingto成员
9月30日 创建

背景

  • 认证优先级契约为 GC_TOKEN > GITCODE_TOKEN > 本地配置,环境变量始终覆盖(docs/AUTH.md)
  • 环境变量 token 失效时,gc auth login 仍成功写入本地配置,但运行时永远使用失效的环境变量 token;auth status 又建议 re-login,形成"登录成功但不生效、按提示重登也无效"的陷阱。且 unset 只对当前会话有效,若变量定义在 shell 配置文件中,新终端会复发——用户需要的是根治指引而非会话级缓解
  • 代码现状:
    • pkg/cmd/auth/login/login.go:177 成功路径末尾无条件打印静态提示,不检测环境变量是否设置、不区分变量名、不给处理命令
    • pkg/cmd/auth/status/status.go:168 已捕获 token_source(JSON 含该字段),但文本模式认证失败时硬编码建议 "To re-authenticate, run: gc auth login",环境变量场景下无效

改动建议

  1. gc auth login 成功路径:
    • 检测 GC_TOKEN/GITCODE_TOKEN 存在性(仅存在性,不读取值);未设置时不输出环境变量相关提示
    • 设置时输出醒目警告,并给出两条可直接复制执行的根治方案(见下方"指引输出要求")
    • 交互模式增加确认门:明确告知"本次登录配置不会生效"后询问是否仍保存;非交互模式警告后继续
    • 可选进阶(评审定夺):在常见 shell 配置文件中匹配变量名定位定义文件(仅输出路径,不读取值),使命令直达实际源头
    • 可选:对环境变量 token 做一次 VerifyToken,失效时在警告中明示
  2. gc auth status 认证失败路径:token_source 为环境变量时,输出与 login 相同风格的复制即执行建议;方案 A 在此路径包含完整 gc auth login 步骤并同样以验证命令收尾;为本地配置时维持现状
  3. 测试:表格驱动覆盖(env 设置与否 × token 有效/失效 × 交互/非交互 × bash/zsh 推断)

指引输出要求(验收锚点)

  • 每一步建议均为可直接复制执行的命令,不输出纯描述性文字
  • 命令按上下文定制:变量名、$SHELL 推断的配置文件路径、(如实现)检测到的实际定义文件
  • 修改配置文件的命令使用可逆形式(注释而非删除),并按平台适配语法(GNU/BSD sed -i 差异)
  • 方案 B 的会话级命令须避免 token 进入 shell history(如 read -rsp ... && export 形式)
  • 每条方案必须闭环到可验证的终态(以 gc auth status 收尾),不得停留在中间状态(如仅 unset)使用户误以为已完成
  • 按输出上下文区分步骤:auth login 成功路径的方案 A 标注"本次登录已保存",第 3 步仅需验证;auth status 失败路径的方案 A 须包含完整的 gc auth login 步骤(该上下文中本地配置可能未保存或已失效)
  • 打印的任何命令中不包含 token 值
  • 示例输出(措辞评审定稿):
⚠ 环境变量 GC_TOKEN 已设置,优先级高于本地登录配置;本次登录在该环境不会生效

  方案 A · 切换为本地登录(推荐,本次登录已保存,完成 1-2 后即生效):
    1. 停用配置文件中的旧定义(可逆,注释而非删除):
       sed -i 's/^\(export \)\{0,1\}GC_TOKEN=/# &/' ~/.bashrc
    2. 当前终端立即生效:
       unset GC_TOKEN
    3. 验证:
       gc auth status

  方案 B · 继续使用环境变量认证:
    1. 在 ~/.bashrc 中更新 GC_TOKEN 的值(GitCode「访问令牌」页生成)
    2. 当前终端立即生效(避免 token 进入 shell history):
       read -rsp "New token: " GC_TOKEN && export GC_TOKEN && echo
    3. 验证:
       gc auth status

(实际文件路径按 $SHELL/检测结果生成;sed 语法按 GNU/BSD 平台适配)

验收标准

  • 设置失效环境变量时:login 警告中每一步均为复制即执行命令且引用具体文件/变量名;status 不再对环境变量场景建议 re-login
  • 未设置环境变量时:login 输出保持安静
  • 不改变"环境变量始终覆盖本地配置"的优先级契约
  • 不自动修改任何用户 shell 配置文件;不读取、不打印任何 token 值

影响范围

pkg/cmd/auth/login/、pkg/cmd/auth/status/、相关测试

likedislike
Aaflyingto成员
9月30日 添加了label:scope/commands, status/triage,type/feature
aflyingto成员
15 天前 评论:

Issue Review(实现前置分析)

现状确认(代码级,main @ 5d2e0fb)

  • 优先级契约:GC_TOKEN > GITCODE_TOKEN > 本地配置(pkg/config/auth_config.go:35-44);消费侧仅默认主机 gitcode.com 走 ActiveToken(环境变量可覆盖),自定义主机一律 StoredToken(pkg/cmdutil/auth.go:38-41、pkg/cmd/auth/status/status.go:104)——因此 login 警告只应在目标主机为 gitcode.com 时触发,自定义主机登录不受环境变量影响,不应告警
  • pkg/cmd/auth/login/login.go:177:成功路径末尾无条件打印静态提示,不检测环境变量
  • pkg/cmd/auth/status/status.go:168:认证失败时硬编码 To re-authenticate, run: gc auth login,对环境变量场景无效;tokenSource 已在作用域内(取值 GC_TOKEN / GITCODE_TOKEN / config)
  • 既有先例:auth logout 已输出环境变量提示(logout.go:103-108,仅会话级 unset,无根治指引)

验收锚点(按 issue 复核后采用)

  1. login 成功路径:目标主机为 gitcode.com 且 GC_TOKEN/GITCODE_TOKEN 已设置(仅存在性检测,不读取值)→ stderr 输出醒目警告 + 两条可复制执行方案(变量名、$SHELL 推断配置文件、GNU/BSD sed -i 适配、方案 B 用 read -rsp 形式避免 history、均以 gc auth status 收尾);未设置时输出保持安静;自定义主机不再输出误导性环境变量提示
  2. login 交互确认门:token 验证通过后、写入本地配置前,交互模式询问是否仍保存;非交互模式警告后继续保存
  3. status 认证失败路径:token_source 为环境变量时输出同风格指引(方案 A 含完整 gc auth login 步骤);为 config 时维持现状;JSON 模式与退出码契约不变(stdout 仅 JSON、退出码 4)
  4. 不改变优先级契约;不自动修改任何 shell 配置文件;不读取、不打印 token 值

范围裁剪(评审定夺项,本 PR 不实现)

  • 在常见 shell 配置文件中扫描变量定义定位实际文件(可选进阶):不做,指引使用 $SHELL 推断路径
  • 对环境变量 token 做 VerifyToken 并在警告中明示失效(可选):不做,status 路径天然覆盖该场景;留待后续 issue 跟踪

风险与边界

  • 预判风险分级 risk/high(认证 + 确认逻辑),按规范需独立 AI 评审 + 人工最终确认后合并
  • 非交互路径不得新增任何阻塞式输入(--with-token/管道场景仅警告)
  • Windows 无 sed:按平台输出 PowerShell 形式命令(issue 未覆盖,属必要正确性补充)

验证记录

  • 当前验证版本: main @ 5d2e0fb(远端事实核验通过:issue open、无关联 PR)
  • 复现命令: GC_TOKEN=stub-invalid-token ./gc auth status(桩 token,未使用真实凭证)
  • 实际结果: 输出 To re-authenticate, run: gc auth login,退出码 4——按该提示重登后环境变量仍覆盖,提示无效,陷阱成立
  • login 路径证据: login.go:177 无条件静态提示(代码级;成功路径复现需有效 token,按安全规范不使用真实 token,该路径由单测覆盖)
  • 结论: 问题仍存在,进入修复
likedislike
Aaflyingto成员
15 天前 添加了label:risk/high, status/verified;删除了label:status/triage
Aaflyingto成员
15 天前 添加了label:status/in-progress
Aaflyingto成员
15 天前 关联了pull request:feat(auth): add copy-paste remediation guidance when env tokens override login
aflyingto成员
15 天前 评论:

开发进度

  • 当前状态: in-progress(本地门禁完成,PR 已建,CI 与多角色评审进行中)
  • 根因: 环境变量 token 优先级契约下,auth login 成功写入的本地配置被环境变量永久遮蔽;auth status 又建议 re-login,形成"登录成功但不生效、按提示重做也无效"的陷阱;unset 仅会话级有效
  • 主要修改: 新增 pkg/cmd/auth/envtoken 渲染器($SHELL 推断 + GNU/BSD sed/PowerShell 适配 + 双方案可复制指引);auth login 增加交互确认门与非交互警告指引;auth status 环境变量来源失败路径输出同风格指引(方案 A 含完整登录步骤)
  • 影响范围: 仅 auth login/status 文本输出路径;优先级契约、JSON 输出、退出码、凭证落盘逻辑均不变
  • 单元测试: go test ./... 163 包全绿;新增 envtoken/login/status 共 27 个场景(env×有效性×交互性×shell×平台×多变量×JSON×--hostname)
  • 构建: go build -o ./gc ./cmd/gc 通过
  • 实际命令验证: 环境变量桩 token 的 status 指引输出与退出码 4、env 未设置基线不变、--json 纯 JSON、login --with-token 错误路径不变、生成 sed 命令 scratch 实测、regression-core.sh exit 0、go test -tags=system ./tests/system 通过
  • 安全影响: 仅存在性检测不读值;CLI 不修改 shell 配置文件;警告走 stderr;gitleaks 通过;风险分级脚本判定 risk/high
  • 文档同步: docs/AUTH.md、docs/COMMANDS.md 已更新
  • 风险或未覆盖项: login 成功路径与确认门需有效 token 才能真实命令验证(按安全规范不使用真实 token,由单测覆盖);zsh/PowerShell 命令形态按文档语法生成,本机未实测
  • 关联 PR: !593(feature/issue-613)
likedislike
Aaflyingto成员
15 天前 添加了label:status/ready-for-review
aflyingto成员
15 天前 评论:

开发进度

  • 当前状态: ready-for-review(PR !593 已完成自检、四角色独立评审三轮全部 approved、双端 CI 全绿,等待人工最终确认与合并)
  • 根因: 环境变量优先级契约下 login 写入的本地配置被永久遮蔽、status 又建议无效的 re-login(详见前两条进度记录与 PR 自检)
  • 主要修改: envtoken 渲染器新包 + login 确认门/共享 reader/persistLogin 拆分 + status 失败路径指引分流 + 测试与文档同步;62d74eb 为 main 既有 factory 测试 CI 缺陷的独立修复提交
  • 影响范围: 仅 auth login/status 文本输出路径;优先级契约、JSON 输出、退出码、凭证落盘逻辑不变
  • 单元测试: go test ./... 163 包全绿(多轮 -count=1 复核);覆盖率 envtoken 100% / login 80.5% / status 90.1% / cmdutil 94.0%(评审员复测)
  • 构建: go build -o ./gc ./cmd/gc 通过;./gc version 正常
  • 实际命令验证: 环境变量桩 token 的 status 指引(含新开终端验证步骤)与退出码 4、env 未设置基线不变、--json 纯 JSON、login --with-token 错误路径不变、sed 命令 scratch 实测、regression-core.sh exit 0、系统测试通过(终态复跑)
  • 安全影响: 无 token 值外泄路径(status 集成测试负断言钉住);无 shell 注入面(白名单过滤);CLI 不修改 shell 配置;gitleaks 通过;独立安全评审三轮 approved
  • 文档同步: docs/AUTH.md、docs/COMMANDS.md 已更新并经文档评审实测逐条核对;README/AGENTS/CLAUDE/spec/AI-GUIDE/REGRESSION/skills 全量核查无失效(记录于 PR 正文)
  • 风险或未覆盖项: risk/high,按规范合并前需人工最终确认(逐 PR 显式合并指令);login 成功路径与交互门的真实命令验证需有效 token,由单测 + CI 覆盖;累计 21 项评审发现全部闭环(16 项本 PR 修复、4 项登记 #621-#624、1 项可选对称项经两位评审员判定非缺口未采纳)
  • 关联 PR: !593
likedislike
Aaflyingto成员
15 天前 关闭了 issue
Aaflyingto成员
15 天前 添加了label:status/merged