Repository navigation
fix(web): Usage header controls fit beside the breadcrumb #24125
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
2e7b009
a1e254e
e06f27a
b26c26e
dd03e05
74e42f1
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,73 @@ | ||
| import * as NodeFSP from "node:fs/promises"; | ||
| import * as NodeOS from "node:os"; | ||
| import * as NodePath from "node:path"; | ||
|
|
||
| // Public screenshot fixtures must never scan a contributor's provider homes. | ||
| // A worktree's .t3 holds the developer's dev settings, so default to a fresh temp home. | ||
| const sandbox = NodePath.resolve( | ||
| process.argv[2] ?? (await NodeFSP.mkdtemp(NodePath.join(NodeOS.tmpdir(), "t3-usage-fixture-"))), | ||
| ); | ||
| if (sandbox === NodePath.resolve(process.env.HOME, ".t3")) throw new Error("Refusing live T3 home"); | ||
| const homes = NodePath.join(sandbox, "usage-fixtures"); | ||
| await NodeFSP.mkdir(NodePath.join(sandbox, "userdata"), { recursive: true }); | ||
| // Claim settings.json exclusively before writing anything, so an existing home is left untouched. | ||
| const settings = await NodeFSP.open(NodePath.join(sandbox, "userdata", "settings.json"), "wx"); | ||
| await NodeFSP.mkdir(NodePath.join(homes, "claude", "projects", "fixture"), { recursive: true }); | ||
| await NodeFSP.mkdir(NodePath.join(homes, "codex"), { recursive: true }); | ||
| await NodeFSP.mkdir(NodePath.join(homes, "config"), { recursive: true }); | ||
| await NodeFSP.mkdir(NodePath.join(homes, "opencode"), { recursive: true }); | ||
| const now = new Date(process.argv[3] ?? "2026-10-23T12:00:00Z"); | ||
| const records = [0, 1, 5, 12, 25, 60].map((days, i) => | ||
| JSON.stringify({ | ||
| type: "assistant", | ||
| timestamp: new Date(+now - days * 86400000 - i * 3600000).toISOString(), | ||
| requestId: `fixture-request-${i}`, | ||
| sessionId: "fixture-session", | ||
| message: { | ||
| id: `fixture-message-${i}`, | ||
| model: "claude-sonnet-4-5", | ||
| usage: { input_tokens: 10000 * (i + 1), output_tokens: 2000 * (i + 1) }, | ||
| }, | ||
| }), | ||
| ); | ||
| await NodeFSP.writeFile( | ||
| NodePath.join(homes, "claude", "projects", "fixture", "session.jsonl"), | ||
| records.join("\n") + "\n", | ||
| ); | ||
| await settings.writeFile( | ||
| JSON.stringify( | ||
| { | ||
| providerInstances: { | ||
| claudeAgent: { | ||
| driver: "claudeAgent", | ||
| config: { homePath: NodePath.join(homes, "claude") }, | ||
| }, | ||
| codex: { driver: "codex", config: { homePath: NodePath.join(homes, "codex") } }, | ||
| cursor: { | ||
| driver: "cursor", | ||
| enabled: false, | ||
| config: { homePath: NodePath.join(homes, "cursor") }, | ||
| }, | ||
| grok: { driver: "grok", enabled: false }, | ||
| opencode: { | ||
| driver: "opencode", | ||
| enabled: false, | ||
| environment: [{ name: "OPENCODE_DATA_DIR", value: NodePath.join(homes, "opencode") }], | ||
| }, | ||
| antigravity: { driver: "antigravity", enabled: false }, | ||
| }, | ||
| usageLimitSources: {}, | ||
| cursorKeychainUsageEnabled: false, | ||
| }, | ||
| null, | ||
| 2, | ||
| ) + "\n", | ||
| ); | ||
| await settings.close(); | ||
| console.log("Seeded synthetic usage in", sandbox); | ||
|
|
||
| // Some usage readers ignore enabled and resolve history from host env overrides | ||
| // (CODEX_HOME, GROK_HOME, PI_CODING_AGENT_DIR, ...), so start from an empty env. | ||
| console.log( | ||
| `Start the verifier server under: env -i PATH="$PATH" HOME=${homes} XDG_CONFIG_HOME=${NodePath.join(homes, "config")} XDG_DATA_HOME=${NodePath.join(homes, "data")} XDG_STATE_HOME=${NodePath.join(homes, "state")} AGENT_CLI_CREDENTIAL_STORE=memory`, | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win Shell-quote the paths in the verifier command. If the sandbox path contains a space, the shell splits 🤖 Prompt for AI Agents
|
||
| ); | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win
Resolve sandbox links before protecting the live T3 home.
NodePath.resolvedoes not follow symlinks. If the supplied sandbox is a symlink to$HOME/.t3, this check passes. The later write then replaces the liveuserdata/settings.jsonwith fixture settings. Compare real paths before creating directories or writing files.🤖 Prompt for AI Agents