Skip to content

feat(usage): add Pi-native provider quota inspection with /usage - #525

Merged
tt-a1i merged 3 commits into
openpi-dev:mainfrom
JS-banana:feat/provider-usage
Sep 9, 2026
Merged

feat(usage): add Pi-native provider quota inspection with /usage#525
tt-a1i merged 3 commits into
openpi-dev:mainfrom
JS-banana:feat/provider-usage

Conversation

@JS-banana

Copy link
Copy Markdown
Contributor

Problem

用户在开始长任务前缺少直接查看订阅额度的入口,往往直到请求被拒绝才发现某个时间窗口已经耗尽。额度信息还必须属于当前登录身份,不能混用旧账号缓存、遗漏附加额度池,或将未知数据表达为没有限制。

Closes #524

Value

通过 /usage 手动查看 Cursor、OpenAI Codex 和 Google Antigravity 的额度快照、剩余量、重置时间和采样年龄。失败按服务隔离,未知数据明确展示,账号标识可按需遮蔽。

Approach

  • 用 Pi modelRegistry.getProviderAuth() 解析当前身份并复用原生 OAuth 刷新;不读取 auth.json、不实现第二套刷新逻辑。
  • 使用固定的三个服务适配器,复用 Antigravity 现有凭据编解码与 User-Agent;保留 Codex 主池及附加池的两个窗口,按响应中的时长标注。
  • 保留无百分比分母的已知金额/剩余量,不用显示取整判断耗尽;未知和不完整快照不伪装成无限制。
  • 60 秒缓存限定于扩展实例和已解析身份;不缓存失败、不完整或空报告。
  • 每个服务最多等待 15 秒,单个 HTTP 尝试最多 4 秒;限制重定向,错误只展示受控描述。TUI 支持取消等待和滚动浮层,RPC/Web 使用原生通知通道,JSON 与文本投影基于同一份报告。

Validation

  • node --test --experimental-strip-types tests/extensions/usage/*.test.ts:30 passed。覆盖身份切换、Pi 原生过期凭据刷新、窗口完整性、未知/绝对剩余量、协议头、超时回退、取消、脱敏及输出模式。
  • bun run check:通过配置契约、discipline、Web 类型检查/构建、Biome 和 TypeScript。构建仍提示现有 bundle 大于 500 kB。
  • 默认 bun run test 有全套通过记录,也重复出现未改动的子代理生命周期测试 2 秒等待超时;最终默认并发一轮仍是该项失败。该文件单独复测 20/20 通过。没有修改该模块或放宽断言时限。
  • node --test --test-concurrency=4 --experimental-strip-types tests/**/*.test.ts:同一完整 Node 测试集 1495 passed / 1 skipped / 0 failed。node node_modules/vitest/vitest.mjs run tests/**/*.spec.ts:130 passed / 9 files。较低并发结果不代表默认高并发命令稳定通过。
  • 显式 --no-extensions -e ./extensions/usage/index.ts -e ./extensions/ai-providers/index.ts 加载源码,关闭启动网络发现、模型工具和 Session 持久化。真实 RPC 查询三个服务分别返回 2/4/2 个额度项,均无错误或不完整警告;仅产生 extension_ui_request 和命令 response,没有模型回合,stderr 为空。
  • 真实 TUI(70 列 × 20 行)验证浮层、Page Down 和 Esc;页码由 1-15/21 变为 7-21/21,无宽度/渲染错误,进程正常退出。该 UI 验收在最终 User-Agent 修正前完成;修正后的三服务成功结果由 RPC 验收。

Impact

  • User-visible behavior:新增 /usage [-f|--refresh] [-r|--redact] [-j|--json];订阅额度快照与 Session token/cost 统计明确分开。JSON 是报告格式,不绕过宿主输出协议;Pi print 模式将扩展日志转到 stderr。
  • Model-visible context/tools:无新增工具,不注入模型消息,不发起模型请求。
  • Runtime/lifecycle:用户触发查询、限时等待、可取消 TUI 输入监听、身份隔离的内存缓存。Pi 的鉴权兼容接口没有取消参数,停止等待不会中断已经启动的原生凭据刷新;晚到结果不缓存。
  • Persisted config/data:不新增配置或额度历史。正常 OAuth 刷新仍可能由 Pi 更新其现有凭据存储。
  • Compatibility/risk:依赖项目现有 Pi 0.85.1+ 接口。服务额度接口可能变更,无法识别的响应明确标为未知;不实现完整账单、充值、额度重置、账号轮换或任务预算保证。本机日常安装仍是 npm 版,验收显式加载当前源码,没有修改安装配置。

Adds an orthogonal, lightweight /usage command to inspect live subscription quotas and rate limits across Cursor, Google Antigravity, and OpenAI Codex.

Key highlights:
- Pure read-only observability with 60s in-memory TTL caching; failed requests are never cached.
- Wire-accurate parsing: Cursor sub/userId separation and auto/api pool distinction; Google Antigravity remainingFraction inversion and dual Gemini/3P pools; OpenAI Codex second-to-millisecond timestamp conversion, ChatGPT-Account-Id header injection, and Spark pool isolation.
- Privacy-aware formatting with ANSI progress bars, relative countdowns, and optional --redact masking.
- Includes 17 unit tests verifying wire headers, fallbacks, cache invalidation, and failure isolation.
…, and cache isolation

Incorporates review feedback from docs/research/2026-09-09-openpi-usage-review.md:
- Reuse Pi-native modelRegistry.getProviderAuth lifecycle and locking instead of direct auth.json reads
- Parse both primary and secondary windows for OpenAI Codex additional rate limits
- Key the in-memory cache by credential identity hash to prevent cross-account pollution
- Invert remainingFraction properly and handle empty groups/remainingAmount for Google Antigravity
- Route non-TUI output through ctx.ui.notify to preserve RPC channel contract
- Sanitize error messages to eliminate potential credential leakage
- Decouple status threshold calculation from display rounding
- Document /usage in README.md quick-reference table
Aligns Antigravity quota request User-Agent with the provider's existing getAntigravityUserAgent helper, asserting the wire header in provider tests.
@github-actions github-actions Bot added the documentation Improvements or additions to documentation label Sep 9, 2026

@tt-a1i tt-a1i left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Reviewed at exact head 2fb853e. Standards and Spec review found no P0/P1 blocker. The command is valuable, user-triggered, Pi-native, bounded, and does not add model-facing tools or context. Focused tests (30/30), repository checks, and hosted CI are green. Non-blocking follow-up: complete exhausted Codex reports currently carry a warning and therefore bypass the 60-second cache; completeness should eventually be represented separately from exhaustion/advisory state.

@tt-a1i
tt-a1i merged commit 36debe2 into openpi-dev:main Sep 9, 2026
7 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentation Improvements or additions to documentation

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat(usage): provide lightweight subscription quota and rate-limit snapshots (/usage)

2 participants