Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

5 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

CodexBar.ts (TypeScript port)

A cross-platform port of the CodexBar CLI from Swift to TypeScript. It ships as a plain Node package — installed and run with npm/node — and is bundled at build time with Bun. It mirrors the original CLI's command/flag surface, its text and JSON output shapes, and the core usage / pace / cost logic. macOS-only mechanisms are replaced by cross-platform equivalents: secrets live in the OS keychain (via keytar — Windows Credential Manager, macOS Keychain, Linux libsecret) and WebKit browser scraping becomes a clean file-based stub, so it runs on Windows, Linux, and macOS.

The Swift original lives in CodexBar/ (reference only). The port lives under src/.

Requirements

  • Node ≥ 20.11 (developed against 22.x) — to run the CLI
  • Bun ≥ 1.1 (developed against 1.3.x) — only to build the bundle and run the tests
  • A system keychain for secret storage. macOS Keychain and Windows Credential Manager work out of the box; on Linux install libsecret and a Secret Service provider (e.g. libsecret-1-0 + gnome-keyring). To bypass the keychain and use a file instead, set CODEXBAR_SECRETS_FILE=<path>.

Install

npm install -g codexbar     # exposes the `codexbar` command globally

The only runtime dependency is keytar, a native Node-API addon for system-keychain access. It ships prebuilt binaries, but npm must be allowed to run its install script — on npm ≥ 11 approve it with npm approve-scripts keytar if prompted, otherwise keychain access fails with a clear error and you can fall back to CODEXBAR_SECRETS_FILE.

To install from a checkout instead:

npm install         # dependencies
bun run build       # bundle src/ -> dist/index.js
npm install -g .    # or: node dist/index.js <command>

Usage

codexbar <command> [flags]               # after a global install
node dist/index.js <command> [flags]     # from a checkout

Commands (mirrors CodexBar/docs/cli.md):

Command Description
usage (default) Provider usage windows, pace, credits, reset times (text or JSON)
cost Local token cost usage from Claude/Codex session logs
cards Terminal card grid (--brief for a compact table)
sessions list / sessions focus List local agent sessions (focus is a platform stub)
serve Localhost-only HTTP JSON server (/health, /usage, /cost)
config validate|dump|providers|enable|disable|set-api-key Config management
cache clear Clear cookie / cost caches
diagnose Safe, redacted JSON diagnostic export

Key flags: --provider <id\|both\|all>, --source auto\|web\|cli\|oauth\|api, --format text\|json, --pretty, --status, --no-credits, --account/--account-index/--all-accounts. Globals: -h/--help, -V/--version, -v/--verbose, --no-color, --log-level, --json-output, --json-only.

Exit codes: 0 success · 1 unexpected · 2 provider missing · 3 parse/format · 4 timeout.

Examples

codexbar --version
codexbar usage --provider claude --source oauth --format json --pretty
codexbar cost --days 30 --format json --pretty
codexbar cards --brief
codexbar serve --port 8080          # GET http://127.0.0.1:8080/health
codexbar diagnose

Providers

Three providers are implemented as the reference set:

  • Claude (reference) — reads ~/.claude/.credentials.json OAuth token and calls GET https://api.anthropic.com/api/oauth/usage. Exercises the full session/weekly/pace/identity model with no macOS dependency.
  • Codex~/.codex/auth.json OAuth file.
  • OpenRouter — API-key credits.

The provider registry accepts descriptors, so the remaining ~55 CodexBar providers can be added by implementing the ProviderDescriptor contract in src/core/contracts.ts.

Scope

In: full CLI command/flag surface, text + JSON output parity, UsagePace and UsageFormatter logic, config load/normalize/validate, local cost scanning + pricing, serve, and the 3 providers above.

Out (by design): the SwiftUI macOS app, the WidgetKit extension, and WebKit browser-cookie scraping. Secrets are stored in the OS keychain via keytar (Windows Credential Manager / macOS Keychain / Linux libsecret), with a file-backed fallback selected by CODEXBAR_SECRETS_FILE; browser-cookie import is a stub that still honors a manual cookieHeader from config. --source cli (PTY probes) returns a clean "unsupported" error.

Development

Bun is the dev toolchain (bundler + test runner); the shipped artifact targets Node only.

bun run typecheck     # tsc --noEmit (strict)
bun test              # bun's built-in test runner
bun run build         # bundle to dist/index.js (--target=node, keytar left external)
bun run src/cli.ts <command>   # run from source without building

Security notes

  • serve binds to 127.0.0.1 only, rejects non-loopback Host headers, and intentionally has no auth / TLS / CORS (loopback-only v1). Do not expose it to a network.
  • diagnose and logs never emit secret values — only booleans indicating presence.
  • Secrets are only ever sent in provider Authorization headers. They are stored in the OS keychain by default; the file-backed fallback (CODEXBAR_SECRETS_FILE) is written with restrictive 0600 permissions.

About

A cross-platform port of the CodexBar CLI from Swift to TypeScript

Topics

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages