myshell-tools 2.3.0 → 2.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (60) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/README.md +26 -10
  3. package/dist/cli.js +43 -3
  4. package/dist/cli.js.map +1 -1
  5. package/dist/commands/cost.js +4 -1
  6. package/dist/commands/cost.js.map +1 -1
  7. package/dist/commands/doctor.js +2 -2
  8. package/dist/commands/doctor.js.map +1 -1
  9. package/dist/commands/install.d.ts +66 -0
  10. package/dist/commands/install.js +174 -0
  11. package/dist/commands/install.js.map +1 -0
  12. package/dist/commands/login.d.ts +41 -2
  13. package/dist/commands/login.js +116 -11
  14. package/dist/commands/login.js.map +1 -1
  15. package/dist/core/assess.js +2 -62
  16. package/dist/core/assess.js.map +1 -1
  17. package/dist/core/budget.d.ts +26 -0
  18. package/dist/core/budget.js +37 -0
  19. package/dist/core/budget.js.map +1 -0
  20. package/dist/core/history.d.ts +35 -0
  21. package/dist/core/history.js +116 -0
  22. package/dist/core/history.js.map +1 -0
  23. package/dist/core/json-envelope.d.ts +49 -0
  24. package/dist/core/json-envelope.js +117 -0
  25. package/dist/core/json-envelope.js.map +1 -0
  26. package/dist/core/orchestrate.js +107 -8
  27. package/dist/core/orchestrate.js.map +1 -1
  28. package/dist/core/policy.js +17 -9
  29. package/dist/core/policy.js.map +1 -1
  30. package/dist/core/prompt.d.ts +9 -4
  31. package/dist/core/prompt.js +14 -5
  32. package/dist/core/prompt.js.map +1 -1
  33. package/dist/core/review.js +2 -49
  34. package/dist/core/review.js.map +1 -1
  35. package/dist/core/route.d.ts +13 -5
  36. package/dist/core/route.js +20 -6
  37. package/dist/core/route.js.map +1 -1
  38. package/dist/core/types.d.ts +37 -0
  39. package/dist/infra/pricing.d.ts +17 -4
  40. package/dist/infra/pricing.js +73 -3
  41. package/dist/infra/pricing.js.map +1 -1
  42. package/dist/interface/menu.d.ts +12 -0
  43. package/dist/interface/menu.js +110 -25
  44. package/dist/interface/menu.js.map +1 -1
  45. package/dist/providers/detect.d.ts +17 -5
  46. package/dist/providers/detect.js +56 -4
  47. package/dist/providers/detect.js.map +1 -1
  48. package/dist/providers/install.js +1 -0
  49. package/dist/providers/install.js.map +1 -1
  50. package/dist/providers/opencode-parse.d.ts +49 -0
  51. package/dist/providers/opencode-parse.js +181 -0
  52. package/dist/providers/opencode-parse.js.map +1 -0
  53. package/dist/providers/opencode.d.ts +43 -0
  54. package/dist/providers/opencode.js +121 -0
  55. package/dist/providers/opencode.js.map +1 -0
  56. package/dist/providers/port.d.ts +1 -1
  57. package/dist/providers/registry.d.ts +2 -2
  58. package/dist/providers/registry.js +6 -2
  59. package/dist/providers/registry.js.map +1 -1
  60. package/package.json +2 -2
package/CHANGELOG.md CHANGED
@@ -11,6 +11,26 @@ and the project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.
11
11
  - Cross-OS CI execution (requires a public remote).
12
12
  - First npm publish.
13
13
 
14
+ ## [2.6.0]
15
+
16
+ ### Added
17
+ - **opencode provider (experimental, auto-detected)**: third provider alongside claude/codex. Auto-detected when the `opencode` CLI is installed; works immediately via opencode's free hosted models (no keys required), with premium providers (Gemini/Claude/GPT/local/etc.) available through opencode's own `auth login` — myshell-tools never handles the keys. Streams via `opencode run --format json`, reports real per-step token usage AND cost to the ledger via step_finish events (no pricing-table dependency for billing), and appears in the control-panel header + raw-session picker only when installed (no nag otherwise). Cross-vendor review stays honest by comparing the effective vendor from the `provider/model` id.
18
+ - **Routing robustness**: `route()` now prefers a model the provider CLI actually advertises (from detection) and never selects a model the CLI lacks; falls back gracefully when the advertised set matches no pricing entry, never throws. Closes a latent crash where an opencode-only setup (or any escalation that reached manager tier with opencode as the sole available provider) would throw `No models available for tier "…" with providers [opencode]` because the pricing table only had an entry for the `ic` tier. All three tiers (worker/ic/manager) now have opencode pricing entries.
19
+
20
+ ## [2.5.0]
21
+
22
+ ### Added
23
+ - **Conversation context continuity**: multi-turn conversations now replay a bounded, compacted slice of prior history to the model on each turn — previously every turn was sent cold/stateless, so follow-up questions had no context. The history is token-bounded (most recent 12 turns, ~6 k chars) and assistant confidence-envelopes are stripped before replay to save tokens. Implemented via `src/core/history.ts` (`compactHistory`).
24
+ - **Efficiency engine**: cost-aware cross-vendor review gating via `reviewPolicy: auto | critical-only | off` — cost-saver mode now only runs the double-spend review pass on critical-risk tasks, not every IC invocation. An optional per-task cost budget cap (`Policy.maxCostUsd`) stops escalating/reviewing once spend reaches the cap and accepts the best result so far. Implemented via `src/core/budget.ts` (`budgetExceeded`, `remainingBudget`) and the `reviewPolicy` field in `src/core/policy.ts`.
25
+ - **Container / SSH-friendly sign-in ("code method")**: when the browser/localhost OAuth callback can't be reached (Replit, Codespaces, Gitpod, SSH, or a headless Linux box), `login` now uses a no-localhost flow automatically — `codex login --device-auth` (authorize with a one-time device code) for Codex, and `claude setup-token` (paste an authorization code from claude.ai) for Claude. The environment is auto-detected; force either flow with `myshell-tools login <provider> --code` / `--browser`. A failed browser sign-in now also points at the `--code` fallback.
26
+ - **Settings → "Set as default shell" toggle**: the control-panel Settings screen (`[s]`) now exposes `[2] Set as default shell` alongside the mode picker; toggling it installs/uninstalls the real shell startup hook (same mechanism as `myshell-tools install`/`uninstall`) and only flips the stored flag when the hook write succeeds.
27
+ - **JSON-envelope deduplication**: the brace-depth `{...}` scanner used to extract model confidence/verdict envelopes was duplicated across `assess.ts`, `review.ts`, and `history.ts`. Extracted into a shared pure module `src/core/json-envelope.ts` (`lastJsonObjectWithKey`, `lastJsonObjectBoundsWithKey`); all three consumers now delegate to it. Behaviour is identical; the shared module carries its own thorough test suite.
28
+
29
+ ## [2.4.0]
30
+
31
+ ### Added
32
+ - **Real `install` / "set as default"**: `myshell-tools install` writes a guarded, reversible hook to your shell rc (`~/.bashrc`/`~/.zshrc` or the PowerShell profile) so new interactive shells launch myshell-tools. The control panel's "set as default? Y" now actually does this (it was a no-op hint before). `myshell-tools uninstall` removes it; opt out per-shell with `MYSHELL_SKIP=1`.
33
+
14
34
  ## [2.3.0]
15
35
 
16
36
  ### Added
package/README.md CHANGED
@@ -4,7 +4,7 @@
4
4
 
5
5
  `myshell-tools` routes each task to the *cheapest* model likely to succeed, runs it on your real codebase, optionally has a **different vendor** review the result, and shows you exactly what it did and what it truly cost — with **no fabricated data, ever**.
6
6
 
7
- > **Status: `2.1.0` — honest, tested, and real.** Both the Claude and Codex paths work, and provider auth is detected for real.
7
+ > **Status: `2.6.0` — honest, tested, and real.** Claude, Codex, and opencode (experimental) all work, and provider auth is detected for real.
8
8
 
9
9
  ---
10
10
 
@@ -39,20 +39,29 @@ myshell-tools
39
39
  Using one frontier model for everything is wasteful (renaming a variable doesn't need Opus) and single‑model output has blind spots. `myshell-tools` addresses both, honestly:
40
40
 
41
41
  - **Cost‑aware routing** — trivial work goes to the cheap tier (Haiku / GPT‑5 mini), real implementation to the mid tier, hard calls to the flagship. You see the savings as a real number.
42
- - **Cross‑vendor adversarial review** — for high‑risk work, a *different vendor* checks the first model's output (Codex reviewing Claude, or vice‑versa). Different families, different blind spots.
43
- - **Subscription, not metering** it drives the **Claude Code** and **Codex** CLIs you already pay for. No API keys, no per‑token bill.
42
+ - **Efficiency modes** — three policy presets control the cost/quality trade-off:
43
+ - `cost-saver` routes to the cheapest capable model for each tier; only runs the cross-vendor review pass on *critical*-risk tasks (not every IC call). An optional `maxCostUsd` cap halts further escalation/review once spend reaches the limit.
44
+ - `balanced` — the default; routes intelligently and reviews high-risk work.
45
+ - `quality-first` — always reviews IC output for high/critical tasks, regardless of cost.
46
+ - **Cross‑vendor adversarial review** — a *different vendor* checks the first model's output (Codex reviewing Claude, or vice‑versa). Different families, different blind spots. Review gating depends on mode; see Efficiency modes above.
47
+ - **Multi-turn context continuity** — follow-up messages carry real context. Prior conversation turns are compacted into a bounded history block (~6 k chars, most recent 12 turns) and replayed to the model, so it actually knows what was said earlier. Confidence envelopes are stripped before replay to save tokens.
48
+ - **Container / SSH sign-in** — `myshell-tools login` auto-detects headless and cloud-IDE environments (Replit, Codespaces, Gitpod, SSH sessions) and switches to a no-localhost sign-in flow automatically. Force either flow with `--code` or `--browser`.
49
+ - **opencode provider (experimental)** — auto-detected; works instantly with free hosted models (no keys). Add premium providers through opencode's own `auth login`. Route to it explicitly or let the policy fall back to it automatically.
50
+ - **Routing prefers advertised models** — detection passes each provider's actual model list to `route()`, which picks the cheapest model the CLI *actually has*, not just the cheapest in the pricing table. Falls back gracefully if the advertised list doesn't match any pricing entry.
51
+ - **Subscription, not metering** — it drives the **Claude Code**, **Codex**, and **opencode** CLIs you already use. No API keys, no per‑token bill for the free path.
44
52
  - **Honest by construction** — every number on screen traces to a real measurement. A suite of *architecture tests* makes fabricated/mock output literally unmergeable.
45
53
 
46
54
  ---
47
55
 
48
56
  ## Requirements
49
57
 
50
- - **Node.js ≥ 20** (the CLI itself; tests require Node ≥ 22).
58
+ - **Node.js ≥ 20** for the compiled CLI (`dist/`). **Node ≥ 22** is required to run the test suite (see Development below).
51
59
  - At least one provider CLI. `npx myshell-tools` will **offer to install** them for you on first run — or you can install manually:
52
60
  - **Claude Code** — `npm install -g @anthropic-ai/claude-code`, then sign in when prompted.
53
61
  - **Codex** — `npm install -g @openai/codex`, then `codex login`.
62
+ - **opencode** *(experimental, optional)* — auto-detected when the `opencode` CLI is installed. Works immediately with free hosted models (no keys). Premium providers (Gemini, Claude, GPT, local models, etc.) are available through opencode's own `auth login` — myshell-tools never handles the keys. Appears in the control-panel header and session picker only when installed.
54
63
 
55
- You need **one** to start; install **both** to unlock cross‑vendor review.
64
+ You need **one** to start; install **both** claude and codex to unlock cross‑vendor review.
56
65
 
57
66
  ---
58
67
 
@@ -164,7 +173,7 @@ classify ─▶ route(cheapest tier) ─▶ run ─▶ assess
164
173
  This is a ground‑up rebuild whose first principle is: **the tool never shows fabricated, mocked, or randomized data as if it were real.** It's enforced, not promised:
165
174
 
166
175
  - **Architecture guard tests** fail the build if the UI/command layers contain hardcoded "AI responses", fake metrics, or a digit‑then‑`%` literal; if the orchestration core touches the filesystem, clock, or RNG directly; or if any module other than the entry point can terminate the process.
167
- - **513 unit/architecture tests + 42 contract tests** (parsers pinned to *recorded real transcripts*), with `tsc --strict`, ESLint, and a clean `npm pack` checked in CI across Windows / macOS / Linux.
176
+ - **1000+ unit/architecture tests + 42 contract tests** (parsers pinned to *recorded real transcripts*), with `tsc --strict`, ESLint, and a clean `npm pack` checked in CI across Windows / macOS / Linux.
168
177
 
169
178
  ---
170
179
 
@@ -184,12 +193,17 @@ Hexagonal / ports‑and‑adapters:
184
193
 
185
194
  ## Development
186
195
 
196
+ **Node ≥ 22 is required to run the test suite.** `npm test` uses
197
+ `node --experimental-strip-types` (native TypeScript stripping, available from
198
+ Node 22+). The compiled runtime (`dist/`) supports Node ≥ 20, so
199
+ `package.json` `engines` is left at `>=20`.
200
+
187
201
  ```bash
188
- npm run typecheck # tsc --strict, 0 errors
189
- npm run lint # ESLint (typescript-eslint strict)
190
- npm test # unit + architecture tests
202
+ npm run typecheck # tsc --strict, 0 errors
203
+ npm run lint # ESLint (typescript-eslint strict)
204
+ npm test # unit + architecture tests (requires Node ≥ 22)
191
205
  npm run test:contract # parser contract tests vs recorded transcripts
192
- npm run build # → dist/
206
+ npm run build # tsc → dist/
193
207
  ```
194
208
 
195
209
  ---
@@ -203,6 +217,8 @@ Honest snapshot of `2.0.0-alpha.0`:
203
217
  | Core routing + escalation + cross‑vendor review loop | ✅ implemented & unit‑proven |
204
218
  | Claude adapter | ✅ live, validated end‑to‑end on real models |
205
219
  | Codex adapter | ✅ built; auto‑activates once `codex` is installed + authed |
220
+ | opencode adapter (experimental) | ✅ auto-detected; free models work without keys |
221
+ | Routing prefers advertised models (never routes to unavailable model) | ✅ |
206
222
  | `doctor` / `cost` / REPL / streaming UI | ✅ |
207
223
  | Live cross‑vendor demonstration | ⏳ pending Codex auth |
208
224
  | Cross‑OS CI run | ⏳ pending a public remote |
package/dist/cli.js CHANGED
@@ -20,6 +20,7 @@ import { loadConfig } from './infra/config.js';
20
20
  import { runDoctor } from './commands/doctor.js';
21
21
  import { runCost } from './commands/cost.js';
22
22
  import { runLogin } from './commands/login.js';
23
+ import { runInstall } from './commands/install.js';
23
24
  import { banner } from './ui/banner.js';
24
25
  import { createSpinner } from './ui/spinner.js';
25
26
  import { dim } from './ui/theme.js';
@@ -39,28 +40,52 @@ Commands:
39
40
  (none) Open the interactive control panel (default)
40
41
  run <task...> Run a one-shot task and exit
41
42
  repl Start the plain line REPL (no menu)
42
- login [provider] Sign in to a provider (claude or codex) via its own OAuth
43
+ login [provider] Sign in to a provider (claude or codex) via its own OAuth.
44
+ Add --code to use the no-localhost flow (paste a code for
45
+ claude, device code for codex) — best inside containers /
46
+ over SSH. Add --browser to force the localhost flow.
43
47
  doctor Check provider installation, auth, and environment health
44
48
  cost Show real spend from the ledger with a per-model breakdown
49
+ install Write a guarded startup hook to your shell rc file so new
50
+ interactive shells launch myshell-tools automatically
51
+ uninstall Remove the startup hook written by "install"
45
52
 
46
53
  Examples:
47
54
  myshell-tools # open the control panel
48
55
  myshell-tools run "refactor the auth module"
49
56
  myshell-tools login
57
+ myshell-tools login codex --code # device-code sign-in (no localhost)
50
58
 
51
59
  Repository: https://github.com/hey-vera/myshell-tools
52
60
  `;
53
61
  /** Build the orchestration dependencies (includes provider detection). */
54
62
  async function buildDeps(cwd) {
63
+ const [providers, env] = await Promise.all([
64
+ buildProviders(cwd),
65
+ detectEnvironment(),
66
+ ]);
67
+ // Populate advertised model lists from detection so route() can prefer a
68
+ // model the provider CLI actually has. Only include installed providers.
69
+ const availableModels = {};
70
+ if (env.claude.installed && env.claude.availableModels.length > 0) {
71
+ availableModels['claude'] = env.claude.availableModels;
72
+ }
73
+ if (env.codex.installed && env.codex.availableModels.length > 0) {
74
+ availableModels['codex'] = env.codex.availableModels;
75
+ }
76
+ if (env.opencode.installed && env.opencode.availableModels.length > 0) {
77
+ availableModels['opencode'] = env.opencode.availableModels;
78
+ }
55
79
  return {
56
80
  clock: systemClock,
57
81
  session: createSessionWriter({ cwd, id: systemClock.uuid() }),
58
82
  ledger: createLedger({ cwd }),
59
83
  policy: DEFAULT_POLICY,
60
- providers: await buildProviders(cwd),
84
+ providers,
61
85
  cwd,
62
86
  sandbox: 'workspace-write',
63
87
  timeoutMs: 120000,
88
+ ...(Object.keys(availableModels).length > 0 ? { availableModels } : {}),
64
89
  };
65
90
  }
66
91
  /** Honest one-line welcome: which providers were actually detected. */
@@ -93,7 +118,16 @@ async function main() {
93
118
  };
94
119
  // ---- Commands that do NOT need provider detection --------------------------
95
120
  if (args[0] === 'login') {
96
- process.exit(await runLogin(out, args[1]));
121
+ const rest = args.slice(1);
122
+ // --code / --device → no-localhost paste/device flow; --browser → force the
123
+ // localhost flow. Omitted → auto-detect (headless envs default to code).
124
+ const method = rest.includes('--code') || rest.includes('--device')
125
+ ? 'code'
126
+ : rest.includes('--browser')
127
+ ? 'browser'
128
+ : undefined;
129
+ const provider = rest.find((a) => !a.startsWith('-'));
130
+ process.exit(await runLogin(out, provider, method !== undefined ? { method } : undefined));
97
131
  }
98
132
  if (args[0] === 'doctor') {
99
133
  process.exit(await runDoctor(out));
@@ -101,6 +135,12 @@ async function main() {
101
135
  if (args[0] === 'cost') {
102
136
  process.exit(await runCost(cwd, out));
103
137
  }
138
+ if (args[0] === 'install') {
139
+ process.exit(await runInstall(out));
140
+ }
141
+ if (args[0] === 'uninstall') {
142
+ process.exit(await runInstall(out, { uninstall: true }));
143
+ }
104
144
  // ---- One-shot run ----------------------------------------------------------
105
145
  if (args[0] === 'run') {
106
146
  const taskParts = args.slice(1);
package/dist/cli.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cli.js","sourceRoot":"","sources":["../src/cli.ts"],"names":[],"mappings":"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"}
@@ -35,7 +35,10 @@ export function formatCostReport(entries, color = false) {
35
35
  return ['No usage recorded yet — run a task first.'];
36
36
  }
37
37
  const summary = summarizeLedger(entries);
38
- const flagship = getCheapestForTier('manager');
38
+ // Counterfactual uses the flagship from paid providers only (claude/codex).
39
+ // opencode's zero-cost sentinel entries must not suppress the counterfactual
40
+ // by making the "flagship" appear free.
41
+ const flagship = getCheapestForTier('manager', ['claude', 'codex']);
39
42
  // Apples-to-apples: price BOTH the models actually used AND the flagship on the
40
43
  // SAME basis (list price × tokens). We do NOT compare the billed total (which
41
44
  // includes caching/discounts) against a list-price flagship estimate.
@@ -1 +1 @@
1
- {"version":3,"file":"cost.js","sourceRoot":"","sources":["../../src/commands/cost.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cost.js","sourceRoot":"","sources":["../../src/commands/cost.ts"],"names":[],"mappings":"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"}
@@ -45,7 +45,7 @@ export function buildDoctorReport(env, extras, color) {
45
45
  lines.push(divider(color));
46
46
  // ---- Providers -------------------------------------------------------------
47
47
  lines.push(bold('Providers', color));
48
- for (const ps of [env.claude, env.codex]) {
48
+ for (const ps of [env.claude, env.codex, env.opencode]) {
49
49
  if (ps.installed) {
50
50
  const versionStr = ps.version !== null ? ps.version : 'unknown';
51
51
  lines.push(` ${green('✓', color)} ${bold(ps.id, color)} — installed, version: ${versionStr}`);
@@ -69,7 +69,7 @@ export function buildDoctorReport(env, extras, color) {
69
69
  }
70
70
  else {
71
71
  lines.push(red('No providers found.', color) +
72
- ' Install claude or codex to use myshell-tools.');
72
+ ' Install claude, codex, or opencode to use myshell-tools.');
73
73
  }
74
74
  return lines;
75
75
  }
@@ -1 +1 @@
1
- {"version":3,"file":"doctor.js","sourceRoot":"","sources":["../../src/commands/doctor.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"doctor.js","sourceRoot":"","sources":["../../src/commands/doctor.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,66 @@
1
+ /**
2
+ * src/commands/install.ts — Shell startup hook installer / uninstaller.
3
+ *
4
+ * Appends (or removes) a guarded block to the user's shell rc file so that
5
+ * opening a new interactive shell automatically launches myshell-tools.
6
+ *
7
+ * The block is idempotent (install twice → one block) and fully reversible
8
+ * (`myshell-tools uninstall` removes it).
9
+ *
10
+ * Honesty contract:
11
+ * - Only writes when the caller explicitly consents.
12
+ * - Reports exactly what was written and where.
13
+ * - Never claims success when I/O failed.
14
+ * - No digit-% literals.
15
+ */
16
+ import type { OutputSink } from '../interface/render.js';
17
+ export type ShellKind = 'bash' | 'zsh' | 'powershell';
18
+ export declare const HOOK_BEGIN = "# >>> myshell-tools >>>";
19
+ export declare const HOOK_END = "# <<< myshell-tools <<<";
20
+ /**
21
+ * Determine which shell rc file to write.
22
+ *
23
+ * Pure function: takes env + platform, returns kind + absolute path.
24
+ *
25
+ * @param env - A `NodeJS.ProcessEnv`-shaped object (real or fake).
26
+ * @param platform - A `NodeJS.Platform`-shaped string (real or fake).
27
+ */
28
+ export declare function detectShellTarget(env: NodeJS.ProcessEnv, platform: NodeJS.Platform): {
29
+ kind: ShellKind;
30
+ path: string;
31
+ };
32
+ /**
33
+ * Build the guarded shell startup block for the given shell kind.
34
+ *
35
+ * For bash/zsh: uses POSIX `[ -t 1 ]` TTY guard and env-var opt-out.
36
+ * For powershell: uses `$Host.UI.RawUI` TTY check and equivalent env guards.
37
+ *
38
+ * Pure function — returns a string, never does I/O.
39
+ */
40
+ export declare function buildHookBlock(kind: ShellKind): string;
41
+ /**
42
+ * Insert or remove the hook block in `existing` rc file content.
43
+ *
44
+ * - If `enable` is true: remove any existing block, then append a fresh one.
45
+ * - If `enable` is false: remove any existing block (uninstall).
46
+ *
47
+ * Idempotent: calling with enable=true twice still yields exactly one block.
48
+ * Reversible: calling with enable=false removes all traces.
49
+ *
50
+ * Pure function — takes and returns strings, never does I/O.
51
+ */
52
+ export declare function upsertHook(existing: string, kind: ShellKind, enable: boolean): string;
53
+ /**
54
+ * Detect the shell target, read the rc file, upsert the hook, and write it back.
55
+ *
56
+ * Prints clearly:
57
+ * - On install: the rc file path, that new shells will launch myshell-tools,
58
+ * opt-out instructions, and how to reverse.
59
+ * - On uninstall: confirmation that the block was removed.
60
+ *
61
+ * Returns 0 on success, 1 on failure.
62
+ * Never calls process.exit — that is handled exclusively by src/cli.ts.
63
+ */
64
+ export declare function runInstall(out: OutputSink, opts?: {
65
+ uninstall?: boolean;
66
+ }): Promise<number>;
@@ -0,0 +1,174 @@
1
+ /**
2
+ * src/commands/install.ts — Shell startup hook installer / uninstaller.
3
+ *
4
+ * Appends (or removes) a guarded block to the user's shell rc file so that
5
+ * opening a new interactive shell automatically launches myshell-tools.
6
+ *
7
+ * The block is idempotent (install twice → one block) and fully reversible
8
+ * (`myshell-tools uninstall` removes it).
9
+ *
10
+ * Honesty contract:
11
+ * - Only writes when the caller explicitly consents.
12
+ * - Reports exactly what was written and where.
13
+ * - Never claims success when I/O failed.
14
+ * - No digit-% literals.
15
+ */
16
+ import { mkdir, readFile } from 'node:fs/promises';
17
+ import { dirname } from 'node:path';
18
+ import { atomicWrite } from '../infra/atomic.js';
19
+ // ---------------------------------------------------------------------------
20
+ // Hook markers
21
+ // ---------------------------------------------------------------------------
22
+ export const HOOK_BEGIN = '# >>> myshell-tools >>>';
23
+ export const HOOK_END = '# <<< myshell-tools <<<';
24
+ // ---------------------------------------------------------------------------
25
+ // detectShellTarget — PURE
26
+ // ---------------------------------------------------------------------------
27
+ /**
28
+ * Determine which shell rc file to write.
29
+ *
30
+ * Pure function: takes env + platform, returns kind + absolute path.
31
+ *
32
+ * @param env - A `NodeJS.ProcessEnv`-shaped object (real or fake).
33
+ * @param platform - A `NodeJS.Platform`-shaped string (real or fake).
34
+ */
35
+ export function detectShellTarget(env, platform) {
36
+ if (platform === 'win32') {
37
+ const userProfile = env['USERPROFILE'] ?? 'C:\\Users\\Default';
38
+ return {
39
+ kind: 'powershell',
40
+ path: `${userProfile}\\Documents\\WindowsPowerShell\\Microsoft.PowerShell_profile.ps1`,
41
+ };
42
+ }
43
+ const shell = env['SHELL'] ?? '';
44
+ const home = env['HOME'] ?? '/root';
45
+ if (shell.includes('zsh')) {
46
+ return { kind: 'zsh', path: `${home}/.zshrc` };
47
+ }
48
+ return { kind: 'bash', path: `${home}/.bashrc` };
49
+ }
50
+ // ---------------------------------------------------------------------------
51
+ // buildHookBlock — PURE
52
+ // ---------------------------------------------------------------------------
53
+ /**
54
+ * Build the guarded shell startup block for the given shell kind.
55
+ *
56
+ * For bash/zsh: uses POSIX `[ -t 1 ]` TTY guard and env-var opt-out.
57
+ * For powershell: uses `$Host.UI.RawUI` TTY check and equivalent env guards.
58
+ *
59
+ * Pure function — returns a string, never does I/O.
60
+ */
61
+ export function buildHookBlock(kind) {
62
+ if (kind === 'bash' || kind === 'zsh') {
63
+ return (`${HOOK_BEGIN}\n` +
64
+ `# Launch myshell-tools on new interactive shells. Opt out: export MYSHELL_SKIP=1\n` +
65
+ `if [ -t 1 ] && [ -z "$MYSHELL_LOADED" ] && [ -z "$MYSHELL_SKIP" ]; then\n` +
66
+ ` export MYSHELL_LOADED=1\n` +
67
+ ` command -v myshell-tools >/dev/null 2>&1 && myshell-tools\n` +
68
+ `fi\n` +
69
+ `${HOOK_END}`);
70
+ }
71
+ // powershell
72
+ return (`${HOOK_BEGIN}\n` +
73
+ `# Launch myshell-tools on new interactive shells. Opt out: $env:MYSHELL_SKIP = '1'\n` +
74
+ `if ($null -eq $env:MYSHELL_LOADED -and $null -eq $env:MYSHELL_SKIP) {\n` +
75
+ ` $env:MYSHELL_LOADED = '1'\n` +
76
+ ` if (Get-Command myshell-tools -ErrorAction SilentlyContinue) { myshell-tools }\n` +
77
+ `}\n` +
78
+ `${HOOK_END}`);
79
+ }
80
+ // ---------------------------------------------------------------------------
81
+ // upsertHook — PURE
82
+ // ---------------------------------------------------------------------------
83
+ /**
84
+ * Insert or remove the hook block in `existing` rc file content.
85
+ *
86
+ * - If `enable` is true: remove any existing block, then append a fresh one.
87
+ * - If `enable` is false: remove any existing block (uninstall).
88
+ *
89
+ * Idempotent: calling with enable=true twice still yields exactly one block.
90
+ * Reversible: calling with enable=false removes all traces.
91
+ *
92
+ * Pure function — takes and returns strings, never does I/O.
93
+ */
94
+ export function upsertHook(existing, kind, enable) {
95
+ // Strip any existing block (including surrounding blank lines we added).
96
+ // The pattern handles: optional leading \n, BEGIN marker, anything, END marker,
97
+ // optional trailing \n — all removed in one pass.
98
+ const stripped = existing
99
+ .replace(new RegExp(`\n?${escapeRegExp(HOOK_BEGIN)}[\\s\\S]*?${escapeRegExp(HOOK_END)}\n?`, 'g'), '')
100
+ .trimEnd();
101
+ if (!enable) {
102
+ // Return stripped content. Preserve trailing newline when content exists.
103
+ return stripped.length > 0 ? stripped + '\n' : '';
104
+ }
105
+ const block = buildHookBlock(kind);
106
+ // Separate from existing content with a blank line if there is any.
107
+ const separator = stripped.length > 0 ? '\n\n' : '';
108
+ return stripped + separator + block + '\n';
109
+ }
110
+ // ---------------------------------------------------------------------------
111
+ // Internal helper
112
+ // ---------------------------------------------------------------------------
113
+ function escapeRegExp(s) {
114
+ return s.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
115
+ }
116
+ // ---------------------------------------------------------------------------
117
+ // runInstall — I/O runner
118
+ // ---------------------------------------------------------------------------
119
+ /**
120
+ * Detect the shell target, read the rc file, upsert the hook, and write it back.
121
+ *
122
+ * Prints clearly:
123
+ * - On install: the rc file path, that new shells will launch myshell-tools,
124
+ * opt-out instructions, and how to reverse.
125
+ * - On uninstall: confirmation that the block was removed.
126
+ *
127
+ * Returns 0 on success, 1 on failure.
128
+ * Never calls process.exit — that is handled exclusively by src/cli.ts.
129
+ */
130
+ export async function runInstall(out, opts) {
131
+ const enable = !(opts?.uninstall ?? false);
132
+ const { kind, path: rcPath } = detectShellTarget(process.env, process.platform);
133
+ // Read existing content (treat missing file as empty).
134
+ let existing = '';
135
+ try {
136
+ existing = await readFile(rcPath, 'utf8');
137
+ }
138
+ catch (err) {
139
+ const nodeErr = err;
140
+ if (nodeErr.code !== 'ENOENT') {
141
+ out.write(`[error] Could not read ${rcPath}: ${nodeErr.message}\n`);
142
+ return 1;
143
+ }
144
+ // File doesn't exist yet — fine, we'll create it on write.
145
+ }
146
+ const updated = upsertHook(existing, kind, enable);
147
+ // If uninstalling and the block wasn't present, report and return cleanly.
148
+ if (!enable && updated === (existing.trimEnd().length > 0 ? existing.trimEnd() + '\n' : existing)) {
149
+ out.write(`[info] No myshell-tools hook found in ${rcPath} — nothing to remove.\n`);
150
+ return 0;
151
+ }
152
+ // Write atomically — create parent dir if needed.
153
+ try {
154
+ await mkdir(dirname(rcPath), { recursive: true });
155
+ await atomicWrite(rcPath, updated);
156
+ }
157
+ catch (err) {
158
+ const nodeErr = err;
159
+ out.write(`[error] Could not write ${rcPath}: ${nodeErr.message}\n`);
160
+ return 1;
161
+ }
162
+ if (enable) {
163
+ out.write(`[info] Shell hook installed in: ${rcPath}\n`);
164
+ out.write(`[info] New interactive shells will launch myshell-tools automatically.\n`);
165
+ out.write(`[info] Opt out any time: export MYSHELL_SKIP=1 (bash/zsh) or $env:MYSHELL_SKIP='1' (PowerShell)\n`);
166
+ out.write(`[info] To reverse: myshell-tools uninstall\n`);
167
+ }
168
+ else {
169
+ out.write(`[info] Shell hook removed from: ${rcPath}\n`);
170
+ out.write(`[info] myshell-tools will no longer auto-launch in new shells.\n`);
171
+ }
172
+ return 0;
173
+ }
174
+ //# sourceMappingURL=install.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"install.js","sourceRoot":"","sources":["../../src/commands/install.ts"],"names":[],"mappings":"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"}
@@ -1,20 +1,59 @@
1
1
  /**
2
- * src/commands/login.ts — `myshell-tools login [claude|codex]`.
2
+ * src/commands/login.ts — `myshell-tools login [claude|codex] [--code|--browser]`.
3
3
  *
4
4
  * Frictionless authentication: rather than make the user remember each vendor's
5
5
  * CLI auth command, we delegate to the provider's OWN OAuth flow and inherit the
6
6
  * terminal so the browser/device sign-in works in place.
7
7
  *
8
+ * Two sign-in methods:
9
+ * - 'browser': the provider's default flow, which spins up a localhost
10
+ * callback server and opens a browser. Great on a laptop; FAILS inside
11
+ * containers / over SSH (Replit, Codespaces, etc.) where localhost can't be
12
+ * reached from the user's browser.
13
+ * - 'code': a no-localhost flow that works anywhere.
14
+ * · claude → `claude setup-token`: prints a link; the user signs in at
15
+ * claude.ai, copies the authorization code, and pastes it back here.
16
+ * · codex → `codex login --device-auth`: prints a URL + one-time code;
17
+ * the user authorizes their ChatGPT account on any device.
18
+ *
19
+ * When no method is forced, we auto-detect: headless/remote environments default
20
+ * to 'code' (so the localhost trap is avoided), everything else to 'browser'.
21
+ *
8
22
  * Security: myshell-tools never sees, handles, or stores raw credentials. Each
9
23
  * CLI manages its own tokens; we only trigger its login. (This is what keeps the
10
24
  * "use your subscription, no API keys" model honest.)
11
25
  */
12
26
  import type { OutputSink } from '../interface/render.js';
13
27
  import type { ProviderId } from '../providers/port.js';
28
+ /** Which sign-in flow to run. See module docstring. */
29
+ export type LoginMethod = 'browser' | 'code';
14
30
  export declare function isProviderId(value: string): value is ProviderId;
31
+ /**
32
+ * Decide whether the current environment can actually reach a localhost OAuth
33
+ * callback / open a browser. Pure (env + platform in, boolean out) so it is
34
+ * hermetically testable.
35
+ *
36
+ * Returns true for environments where the browser/localhost flow typically
37
+ * fails and the code method should be preferred:
38
+ * - Known cloud IDEs / containers (Replit, Codespaces, Gitpod).
39
+ * - SSH sessions (no local browser).
40
+ * - Linux with no X11/Wayland display (headless box — nothing to open).
41
+ */
42
+ export declare function isHeadlessEnv(env: NodeJS.ProcessEnv, platform: NodeJS.Platform): boolean;
43
+ /**
44
+ * Resolve the sign-in method to use. An explicit choice always wins; otherwise
45
+ * fall back to environment auto-detection (headless → 'code', else 'browser').
46
+ * Pure / testable.
47
+ */
48
+ export declare function resolveLoginMethod(explicit: LoginMethod | undefined, env: NodeJS.ProcessEnv, platform: NodeJS.Platform): LoginMethod;
15
49
  /**
16
50
  * Run the interactive sign-in flow for one provider (or all installed providers
17
51
  * when no argument is given). Returns 0 on success, 1 only for an invalid
18
52
  * argument — individual sign-in failures are reported but do not fail the command.
53
+ *
54
+ * @param opts.method - Force 'browser' or 'code'. When omitted, the method is
55
+ * auto-detected from the environment via {@link resolveLoginMethod}.
19
56
  */
20
- export declare function runLogin(out: OutputSink, providerArg?: string): Promise<number>;
57
+ export declare function runLogin(out: OutputSink, providerArg?: string, opts?: {
58
+ method?: LoginMethod;
59
+ }): Promise<number>;