@kodycodes/cli 1.7.0 → 1.8.1

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.
package/README.md CHANGED
@@ -60,8 +60,9 @@ Or run via `npx @kodycodes/cli` without a global install.
60
60
  | `kody install` | Detect running local MCP clients, write their config, and start host OAuth. **Recommended long-term path.** |
61
61
  | `kody skill install` | Copies the getting-started skill into Claude Code / Cursor / Agents. |
62
62
  | `kody login` | Browser OAuth (CIMD + PKCE) for the CLI itself. Stores access and refresh tokens. |
63
- | `kody logout` | Deletes stored CLI credentials. |
64
- | `kody status` | Shows CLI login state without printing secrets. |
63
+ | `kody logout` | Deletes stored CLI OAuth credentials and any stored bootstrap/API token. |
64
+ | `kody status` | Shows CLI login / stored API token state without printing secrets. |
65
+ | `kody auth bootstrap --code` | Redeems a one-shot `kody_bc_…` from MCP `cliCredentialBootstrap` and stores the resulting `kody_at_…` for `execute --local` (never prints the token). |
65
66
  | `kody whoami` | Confirms the CLI MCP connection and lists tools. With a scoped API token (and no login), shows token identity via the Open API. |
66
67
  | `kody search [query]` | Calls Kody `search` from the CLI (prefer the host MCP tool). Token-only auth uses Open API `GET /v1/search`. |
67
68
  | `kody execute` | Calls Kody `execute` from the CLI (`--invoke`, `--code`, `--file`, or stdin via `--file -`). With a scoped API token and no login (or with `--token`), cloud execute goes through CapabilityProxy → `kody.execute` — no `kody login`. Add `--local` to run the module (and static `kody:@…` package modules) on this machine instead. |
@@ -70,13 +71,21 @@ Or run via `npx @kodycodes/cli` without a global install.
70
71
 
71
72
  ## Token-authenticated execute (no `kody login`)
72
73
 
73
- Scoped API tokens (`kody_at_…`, from the MCP `api` tool `tokenCreate` or
74
- `POST /v1/tokens`) authenticate the Open API and CapabilityProxy. They never
75
- replace MCP OAuth on `/mcp`. The CLI uses that token path when you pass
76
- `--token` / `KODY_API_TOKEN` and are not logged in (or when you pass `--token`
77
- explicitly):
74
+ Agents already on Kody MCP should prefer `cliCredentialBootstrap` →
75
+ `kody auth bootstrap --code …` (ADR 0056) so a one-shot `kody_bc_…` seeds the
76
+ CLI store without pasting `kody_at_…` into chat. Interactive humans can use
77
+ `kody login`. Scoped API tokens (`kody_at_…`, from bootstrap redeem,
78
+ `tokenCreate`, or `POST /v1/tokens`) authenticate the Open API and
79
+ CapabilityProxy. They never replace MCP OAuth on `/mcp`. The CLI uses that
80
+ token path when you pass `--token` / `KODY_API_TOKEN` and are not logged in
81
+ (or when you pass `--token` explicitly):
78
82
 
79
83
  ```bash
84
+ # Preferred for agents on MCP (no tokenCreate, no second OAuth):
85
+ # 1. MCP api / kody.cliCredentialBootstrap → { bootstrap_code, cli_command }
86
+ npx @kodycodes/cli auth bootstrap --code 'kody_bc_…'
87
+ npx @kodycodes/cli execute --local --file ./task.js
88
+
80
89
  export KODY_API_TOKEN=… # scopes: local-execute (+ search:read for search)
81
90
  # Cloud execute — module runs in Kody's sandbox via CapabilityProxy → kody.execute
82
91
  npx @kodycodes/cli execute --code 'export default async () => ({ ok: true })'
@@ -86,16 +95,16 @@ npx @kodycodes/cli search "what can you do"
86
95
  npx @kodycodes/cli whoami
87
96
  ```
88
97
 
89
- - Neither `kody login` nor a token → the error tells you to mint one with the
90
- MCP `api` tool `tokenCreate` (scopes: `local-execute` plus the capability
91
- scopes the module will call) and pass `--token` / `KODY_API_TOKEN`, or run
92
- `kody login` (for cloud MCP commands and for login-backed `execute --local`).
98
+ - Neither bootstrap store, `kody login`, nor a token → the error prefers
99
+ `cliCredentialBootstrap` → `auth bootstrap`, then `kody login`, then
100
+ `tokenCreate` for CI/headless (`--token` / `KODY_API_TOKEN`).
93
101
  - For `execute --local` specifically: `--token` / `KODY_API_TOKEN` wins when
94
- set; otherwise the CLI uses the stored `kody login` OAuth access token as
95
- the Bearer (no under-the-hood `tokenCreate`). The Open API must accept that
96
- OAuth bearer on CapabilityProxy / package-graph
102
+ set; else a stored bootstrap/API token from `auth bootstrap`; else the
103
+ stored `kody login` OAuth access token as Bearer (no under-the-hood
104
+ `tokenCreate`). The Open API must accept that OAuth bearer on
105
+ CapabilityProxy / package-graph
97
106
  ([kentcdodds/kody#2812](https://github.com/kentcdodds/kody/issues/2812));
98
- until then mint a scoped `kody_at_…` token.
107
+ until then use bootstrap or a scoped `kody_at_…` token.
99
108
  - Wrong/expired token → 401 with a mint-fresh-token message (or the OAuth
100
109
  platform-gap message when the bearer is login OAuth).
101
110
  - Wrong scopes → the error includes `insufficient_scope` and the required
@@ -103,6 +112,7 @@ npx @kodycodes/cli whoami
103
112
  - Account flag off → the error includes `feature_disabled` and the
104
113
  `local-execute` feature flag. Another token does not bypass that flag.
105
114
  - Prefer the env var so the token stays out of shell history and `ps`.
115
+ - Never scavenge host MCP OAuth tokens from disk (ADR 0053).
106
116
 
107
117
  ## Local execute
108
118
 
@@ -121,19 +131,24 @@ CapabilityProxy → `kody.execute` defer). There is no author-facing
121
131
  npx @kodycodes/cli login
122
132
  npx @kodycodes/cli execute --local --file ./task.js --params '{"to":"me@example.com"}'
123
133
 
124
- # Or a scoped API token (still wins over login when set):
134
+ # Agents on MCP: bootstrap code → store (no tokenCreate, no second OAuth):
135
+ npx @kodycodes/cli auth bootstrap --code 'kody_bc_…'
136
+ npx @kodycodes/cli execute --local --file ./task.js --params '{"to":"me@example.com"}'
137
+
138
+ # Or a scoped API token (still wins over login / bootstrap store when set):
125
139
  export KODY_API_TOKEN=… # minted through the Kody `api` tool
126
140
  npx @kodycodes/cli execute --local --file ./task.js --params '{"to":"me@example.com"}'
127
141
  ```
128
142
 
129
- - **Auth:** `--token` / `KODY_API_TOKEN` when set; else a valid `kody login`
130
- session (OAuth access token as Bearer — never printed, never exchanged via
131
- `tokenCreate`). Prefer the env var for API tokens so they stay out of shell
132
- history and `ps`. The bearer stays in the CLI process; the sandbox only
133
- talks to a loopback bridge. Host MCP OAuth from other clients is never
134
- read. Until [kentcdodds/kody#2812](https://github.com/kentcdodds/kody/issues/2812)
135
- ships, login-only Bearer is rejected by the Open API — use a `kody_at_…`
136
- token in that case.
143
+ - **Auth:** `--token` / `KODY_API_TOKEN` when set; else stored `auth bootstrap`
144
+ API token; else a valid `kody login` session (OAuth access token as Bearer —
145
+ never printed, never exchanged via `tokenCreate`). Prefer the env var for
146
+ API tokens so they stay out of shell history and `ps`. The bearer stays in
147
+ the CLI process; the sandbox only talks to a loopback bridge. Host MCP OAuth
148
+ from other clients is never read. Until
149
+ [kentcdodds/kody#2812](https://github.com/kentcdodds/kody/issues/2812)
150
+ ships, login-only Bearer is rejected by the Open API — use bootstrap or a
151
+ `kody_at_…` token in that case.
137
152
  - **Node.js:** 22 or newer (`package.json` `engines` is `>=22`). Older Node
138
153
  fails immediately with that requirement, before workerd is downloaded or
139
154
  started.
@@ -0,0 +1,29 @@
1
+ import { type SecretBackend, type StoreResolution } from './store.js';
2
+ /**
3
+ * Scoped API token stored by `auth bootstrap` (ADR 0056) for
4
+ * `execute --local`, Open API search/whoami, and token-auth cloud execute.
5
+ * Separate from `kody login` OAuth credentials.
6
+ */
7
+ export type StoredApiToken = {
8
+ version: 1;
9
+ apiUrl: string;
10
+ token: string;
11
+ tokenId: string;
12
+ name?: string;
13
+ scopes?: Array<string>;
14
+ expiresAt?: string | null;
15
+ maxExpiresAt?: string | null;
16
+ createdVia?: string;
17
+ };
18
+ export declare function accountForApiUrl(apiUrl: string): string;
19
+ export declare function apiTokenFileStorePath(apiUrl: string, home?: string): string;
20
+ export declare function createApiTokenKeyringBackend(apiUrl: string): SecretBackend;
21
+ export declare function parseStoredApiToken(raw: string): StoredApiToken;
22
+ export declare function loadStoredApiToken(apiUrl?: string, backend?: SecretBackend, resolution?: StoreResolution): StoredApiToken | null;
23
+ export declare function saveStoredApiToken(credentials: StoredApiToken, backend?: SecretBackend, resolution?: StoreResolution): {
24
+ backend: SecretBackend;
25
+ };
26
+ export declare function deleteStoredApiToken(apiUrl?: string, backend?: SecretBackend, resolution?: StoreResolution): {
27
+ deleted: boolean;
28
+ backend: SecretBackend;
29
+ };
@@ -0,0 +1,120 @@
1
+ import { Entry } from '@napi-rs/keyring';
2
+ import { homedir } from 'node:os';
3
+ import { join } from 'node:path';
4
+ import { defaultApiUrl, keyringService } from './defaults.js';
5
+ import { createFileBackend, secretServiceKeyringOptions, } from './store.js';
6
+ export function accountForApiUrl(apiUrl) {
7
+ return `cli-api-token:${new URL(apiUrl).origin}`;
8
+ }
9
+ export function apiTokenFileStorePath(apiUrl, home = homedir()) {
10
+ const origin = new URL(apiUrl).host.replace(/[^a-zA-Z0-9.-]/g, '_');
11
+ const base = process.platform === 'win32'
12
+ ? join(process.env.APPDATA || join(home, 'AppData', 'Roaming'), 'kody')
13
+ : process.platform === 'darwin'
14
+ ? join(home, 'Library', 'Application Support', 'kody')
15
+ : join(process.env.XDG_CONFIG_HOME || join(home, '.config'), 'kody');
16
+ return join(base, `api-token-${origin}.json`);
17
+ }
18
+ export function createApiTokenKeyringBackend(apiUrl) {
19
+ const entry = new Entry(keyringService, accountForApiUrl(apiUrl), secretServiceKeyringOptions);
20
+ return {
21
+ kind: 'keyring',
22
+ get() {
23
+ try {
24
+ return entry.getPassword();
25
+ }
26
+ catch {
27
+ return null;
28
+ }
29
+ },
30
+ set(value) {
31
+ entry.setPassword(value);
32
+ },
33
+ delete() {
34
+ try {
35
+ return entry.deleteCredential();
36
+ }
37
+ catch {
38
+ return false;
39
+ }
40
+ },
41
+ };
42
+ }
43
+ function fileBackendFor(apiUrl, resolution) {
44
+ const path = resolution?.fileStorePath?.(apiUrl) ?? apiTokenFileStorePath(apiUrl);
45
+ return createFileBackend(path);
46
+ }
47
+ function resolveApiTokenBackend(apiUrl, preferred, resolution) {
48
+ if (preferred)
49
+ return preferred;
50
+ try {
51
+ return (resolution?.createKeyring ?? createApiTokenKeyringBackend)(apiUrl);
52
+ }
53
+ catch {
54
+ return fileBackendFor(apiUrl, resolution);
55
+ }
56
+ }
57
+ export function parseStoredApiToken(raw) {
58
+ const parsed = JSON.parse(raw);
59
+ if (parsed.version !== 1 ||
60
+ typeof parsed.token !== 'string' ||
61
+ !parsed.token.startsWith('kody_at_') ||
62
+ typeof parsed.apiUrl !== 'string' ||
63
+ typeof parsed.tokenId !== 'string') {
64
+ throw new Error('Stored Kody API token is invalid. Run `kody auth bootstrap --code …` again.');
65
+ }
66
+ return parsed;
67
+ }
68
+ function readParsed(store) {
69
+ const raw = store.get();
70
+ if (!raw)
71
+ return null;
72
+ return parseStoredApiToken(raw);
73
+ }
74
+ export function loadStoredApiToken(apiUrl = defaultApiUrl, backend, resolution) {
75
+ const store = resolveApiTokenBackend(apiUrl, backend, resolution);
76
+ try {
77
+ const loaded = readParsed(store);
78
+ if (loaded)
79
+ return loaded;
80
+ }
81
+ catch (error) {
82
+ if (!(store.kind === 'keyring' && !backend))
83
+ throw error;
84
+ }
85
+ if (store.kind === 'keyring' && !backend) {
86
+ return readParsed(fileBackendFor(apiUrl, resolution));
87
+ }
88
+ return null;
89
+ }
90
+ export function saveStoredApiToken(credentials, backend, resolution) {
91
+ const store = resolveApiTokenBackend(credentials.apiUrl, backend, resolution);
92
+ try {
93
+ store.set(JSON.stringify(credentials));
94
+ return { backend: store };
95
+ }
96
+ catch (error) {
97
+ if (store.kind === 'keyring' && !backend) {
98
+ const fallback = fileBackendFor(credentials.apiUrl, resolution);
99
+ fallback.set(JSON.stringify(credentials));
100
+ return { backend: fallback };
101
+ }
102
+ throw error;
103
+ }
104
+ }
105
+ export function deleteStoredApiToken(apiUrl = defaultApiUrl, backend, resolution) {
106
+ const store = resolveApiTokenBackend(apiUrl, backend, resolution);
107
+ let deleted = false;
108
+ try {
109
+ deleted = store.delete();
110
+ }
111
+ catch {
112
+ deleted = false;
113
+ }
114
+ if (store.kind === 'keyring' && !backend) {
115
+ const file = fileBackendFor(apiUrl, resolution);
116
+ deleted = file.delete() || deleted;
117
+ }
118
+ return { deleted, backend: store };
119
+ }
120
+ //# sourceMappingURL=api-token-store.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"api-token-store.js","sourceRoot":"","sources":["../src/api-token-store.ts"],"names":[],"mappings":"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"}
@@ -1,5 +1,18 @@
1
+ import { loadStoredApiToken } from './api-token-store.js';
2
+ import type { SecretBackend, StoreResolution } from './store.js';
1
3
  /** Platform tracking for login OAuth as CapabilityProxy / package-graph Bearer. */
2
4
  export declare const localExecuteOauthPlatformIssueUrl = "https://github.com/kentcdodds/kody/issues/2812";
5
+ export type ResolveScopedApiTokenInput = {
6
+ tokenValues?: {
7
+ token?: string;
8
+ };
9
+ env?: NodeJS.ProcessEnv;
10
+ apiUrl?: string;
11
+ apiTokenBackend?: SecretBackend;
12
+ apiTokenResolution?: StoreResolution;
13
+ /** Test seam. */
14
+ loadApiToken?: typeof loadStoredApiToken;
15
+ };
3
16
  /**
4
17
  * Scoped Open API / CapabilityProxy token (`kody_at_…`). Same source for
5
18
  * `execute --local`, token-only cloud execute, and Open API search/whoami.
@@ -7,17 +20,25 @@ export declare const localExecuteOauthPlatformIssueUrl = "https://github.com/ken
7
20
  export declare function readApiToken(values?: {
8
21
  token?: string;
9
22
  }, env?: NodeJS.ProcessEnv): string | null;
23
+ /**
24
+ * Resolve a scoped API token without falling back to `kody login` OAuth.
25
+ * Priority: `--token` / `KODY_API_TOKEN` → stored bootstrap/API token.
26
+ */
27
+ export declare function resolveScopedApiToken(input?: ResolveScopedApiTokenInput): string | null;
10
28
  /** True when the bearer looks like a minted Open API token (not MCP OAuth). */
11
29
  export declare function isScopedApiToken(token: string): boolean;
12
30
  /**
13
- * How to mint the scoped token this CLI already accepts. There is no second
14
- * auth flow here — callers use the MCP `api` tool they already have.
31
+ * How to mint a scoped token for CI/headless. Interactive agents on MCP should
32
+ * prefer `cliCredentialBootstrap` → `auth bootstrap` instead.
15
33
  */
16
34
  export declare function apiTokenMintInstructions(): string;
35
+ /** Preferred interactive path for agents already on Kody MCP (ADR 0056). */
36
+ export declare function cliBootstrapInstructions(): string;
17
37
  /** Token-only Open API paths (search / whoami / cloud token execute) with no token. */
18
38
  export declare function missingApiTokenMessage(purpose: string): string;
19
39
  /**
20
- * `execute --local` with neither `--token` / `KODY_API_TOKEN` nor `kody login`.
40
+ * `execute --local` with neither env/`--token`, stored bootstrap token, nor
41
+ * `kody login`. Prefer bootstrap (MCP) → login → tokenCreate (CI).
21
42
  */
22
43
  export declare function missingLocalExecuteAuthMessage(purpose?: string): string;
23
44
  /** Cloud search / whoami / execute when the process has neither a session nor a token. */
@@ -32,7 +53,7 @@ export declare function insufficientScopeMessage(input: {
32
53
  export declare function featureDisabledMessage(): string;
33
54
  export declare function requireApiToken(values?: {
34
55
  token?: string;
35
- }, env?: NodeJS.ProcessEnv, purpose?: string): string;
56
+ }, env?: NodeJS.ProcessEnv, purpose?: string, options?: Omit<ResolveScopedApiTokenInput, 'tokenValues' | 'env'>): string;
36
57
  /** True when the user passed `--token` (not only the env var). */
37
58
  export declare function hasExplicitTokenFlag(values: {
38
59
  token?: string;
package/dist/api-token.js CHANGED
@@ -1,4 +1,5 @@
1
- import { apiTokenEnvVar } from './defaults.js';
1
+ import { loadStoredApiToken } from './api-token-store.js';
2
+ import { apiTokenEnvVar, defaultApiUrl } from './defaults.js';
2
3
  /** Platform tracking for login OAuth as CapabilityProxy / package-graph Bearer. */
3
4
  export const localExecuteOauthPlatformIssueUrl = 'https://github.com/kentcdodds/kody/issues/2812';
4
5
  /**
@@ -9,30 +10,47 @@ export function readApiToken(values = {}, env = process.env) {
9
10
  const token = (values.token ?? env[apiTokenEnvVar] ?? '').trim();
10
11
  return token.length > 0 ? token : null;
11
12
  }
13
+ /**
14
+ * Resolve a scoped API token without falling back to `kody login` OAuth.
15
+ * Priority: `--token` / `KODY_API_TOKEN` → stored bootstrap/API token.
16
+ */
17
+ export function resolveScopedApiToken(input = {}) {
18
+ const token = readApiToken(input.tokenValues, input.env);
19
+ if (token)
20
+ return token;
21
+ const apiUrl = input.apiUrl || defaultApiUrl;
22
+ const loadApi = input.loadApiToken ?? loadStoredApiToken;
23
+ return loadApi(apiUrl, input.apiTokenBackend, input.apiTokenResolution)?.token ?? null;
24
+ }
12
25
  /** True when the bearer looks like a minted Open API token (not MCP OAuth). */
13
26
  export function isScopedApiToken(token) {
14
27
  return token.startsWith('kody_at_');
15
28
  }
16
29
  /**
17
- * How to mint the scoped token this CLI already accepts. There is no second
18
- * auth flow here — callers use the MCP `api` tool they already have.
30
+ * How to mint a scoped token for CI/headless. Interactive agents on MCP should
31
+ * prefer `cliCredentialBootstrap` → `auth bootstrap` instead.
19
32
  */
20
33
  export function apiTokenMintInstructions() {
21
34
  return `Mint one with the Kody MCP \`api\` tool \`tokenCreate\` (include the \`local-execute\` scope plus the capability scopes this command needs) and pass --token or set ${apiTokenEnvVar}.`;
22
35
  }
36
+ /** Preferred interactive path for agents already on Kody MCP (ADR 0056). */
37
+ export function cliBootstrapInstructions() {
38
+ return `From MCP, call \`cliCredentialBootstrap\` (MCP \`api\` / \`kody.cliCredentialBootstrap\`), then run \`npx @kodycodes/cli auth bootstrap --code <kody_bc_…>\``;
39
+ }
23
40
  /** Token-only Open API paths (search / whoami / cloud token execute) with no token. */
24
41
  export function missingApiTokenMessage(purpose) {
25
- return `${purpose} needs a scoped Kody API token. ${apiTokenMintInstructions()}`;
42
+ return `${purpose} needs a scoped Kody API token. ${cliBootstrapInstructions()}, or ${apiTokenMintInstructions()}`;
26
43
  }
27
44
  /**
28
- * `execute --local` with neither `--token` / `KODY_API_TOKEN` nor `kody login`.
45
+ * `execute --local` with neither env/`--token`, stored bootstrap token, nor
46
+ * `kody login`. Prefer bootstrap (MCP) → login → tokenCreate (CI).
29
47
  */
30
48
  export function missingLocalExecuteAuthMessage(purpose = 'execute --local') {
31
- return `${purpose} needs auth. Run \`kody login\`, or ${apiTokenMintInstructions()}`;
49
+ return `${purpose} needs auth. ${cliBootstrapInstructions()}; or run \`kody login\`; or for CI/headless, ${apiTokenMintInstructions()}`;
32
50
  }
33
51
  /** Cloud search / whoami / execute when the process has neither a session nor a token. */
34
52
  export function missingCliAuthMessage() {
35
- return `Not logged in, and no API token is set. ${apiTokenMintInstructions()} Or run \`kody login\` for browser OAuth (search, whoami, cloud execute, and login-backed \`execute --local\`).`;
53
+ return `Not logged in, and no API token is set. ${cliBootstrapInstructions()}; or run \`kody login\` for browser OAuth (search, whoami, cloud execute, and login-backed \`execute --local\`); or for CI/headless, ${apiTokenMintInstructions()}`;
36
54
  }
37
55
  /** 401 when CapabilityProxy rejected a non-`kody_at_` bearer (typically CLI OAuth). */
38
56
  export function rejectedOauthBearerMessage() {
@@ -50,8 +68,12 @@ export function insufficientScopeMessage(input) {
50
68
  export function featureDisabledMessage() {
51
69
  return 'Kody returned feature_disabled: CapabilityProxy is not enabled for this Kody account (feature flag `local-execute`). `execute --local` and token-auth cloud execute both stop here; minting another token does not bypass the flag. Browser `kody login` can still run cloud execute over MCP.';
52
70
  }
53
- export function requireApiToken(values = {}, env = process.env, purpose = 'this command') {
54
- const token = readApiToken(values, env);
71
+ export function requireApiToken(values = {}, env = process.env, purpose = 'this command', options = {}) {
72
+ const token = resolveScopedApiToken({
73
+ tokenValues: values,
74
+ env,
75
+ ...options,
76
+ });
55
77
  if (!token)
56
78
  throw new Error(missingApiTokenMessage(purpose));
57
79
  return token;
@@ -1 +1 @@
1
- {"version":3,"file":"api-token.js","sourceRoot":"","sources":["../src/api-token.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,eAAe,CAAA;AAE9C,mFAAmF;AACnF,MAAM,CAAC,MAAM,iCAAiC,GAC7C,gDAAgD,CAAA;AAEjD;;;GAGG;AACH,MAAM,UAAU,YAAY,CAC3B,SAA6B,EAAE,EAC/B,MAAyB,OAAO,CAAC,GAAG;IAEpC,MAAM,KAAK,GAAG,CAAC,MAAM,CAAC,KAAK,IAAI,GAAG,CAAC,cAAc,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAA;IAChE,OAAO,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,CAAA;AACvC,CAAC;AAED,+EAA+E;AAC/E,MAAM,UAAU,gBAAgB,CAAC,KAAa;IAC7C,OAAO,KAAK,CAAC,UAAU,CAAC,UAAU,CAAC,CAAA;AACpC,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,wBAAwB;IACvC,OAAO,uKAAuK,cAAc,GAAG,CAAA;AAChM,CAAC;AAED,uFAAuF;AACvF,MAAM,UAAU,sBAAsB,CAAC,OAAe;IACrD,OAAO,GAAG,OAAO,mCAAmC,wBAAwB,EAAE,EAAE,CAAA;AACjF,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,8BAA8B,CAC7C,UAAkB,iBAAiB;IAEnC,OAAO,GAAG,OAAO,uCAAuC,wBAAwB,EAAE,EAAE,CAAA;AACrF,CAAC;AAED,0FAA0F;AAC1F,MAAM,UAAU,qBAAqB;IACpC,OAAO,2CAA2C,wBAAwB,EAAE,iHAAiH,CAAA;AAC9L,CAAC;AAED,uFAAuF;AACvF,MAAM,UAAU,0BAA0B;IACzC,OAAO,yKAAyK,iCAAiC,uBAAuB,wBAAwB,EAAE,EAAE,CAAA;AACrQ,CAAC;AAED,MAAM,UAAU,wBAAwB,CAAC,KAIxC;IACA,MAAM,QAAQ,GAAG,KAAK,CAAC,aAAa,CAAC,CAAC,CAAC,yBAAyB,KAAK,CAAC,aAAa,IAAI,CAAC,CAAC,CAAC,EAAE,CAAA;IAC5F,MAAM,IAAI,GAAG,KAAK,CAAC,mBAAmB;QACrC,CAAC,CAAC,wBAAwB,EAAE;QAC5B,CAAC,CAAC,8DACA,KAAK,CAAC,aAAa;YAClB,CAAC,CAAC,mBAAmB,KAAK,CAAC,aAAa,GAAG;YAC3C,CAAC,CAAC,mCACJ,8BAA8B,cAAc,GAAG,CAAA;IACjD,OAAO,oCAAoC,QAAQ,IAAI,IAAI,EAAE,CAAA;AAC9D,CAAC;AAED,MAAM,UAAU,sBAAsB;IACrC,OAAO,gSAAgS,CAAA;AACxS,CAAC;AAED,MAAM,UAAU,eAAe,CAC9B,SAA6B,EAAE,EAC/B,MAAyB,OAAO,CAAC,GAAG,EACpC,UAAkB,cAAc;IAEhC,MAAM,KAAK,GAAG,YAAY,CAAC,MAAM,EAAE,GAAG,CAAC,CAAA;IACvC,IAAI,CAAC,KAAK;QAAE,MAAM,IAAI,KAAK,CAAC,sBAAsB,CAAC,OAAO,CAAC,CAAC,CAAA;IAC5D,OAAO,KAAK,CAAA;AACb,CAAC;AAED,kEAAkE;AAClE,MAAM,UAAU,oBAAoB,CAAC,MAA0B;IAC9D,OAAO,OAAO,MAAM,CAAC,KAAK,KAAK,QAAQ,IAAI,MAAM,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC,CAAA;AAC1E,CAAC"}
1
+ {"version":3,"file":"api-token.js","sourceRoot":"","sources":["../src/api-token.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,51 @@
1
+ import { type StoredApiToken } from './api-token-store.js';
2
+ import type { SecretBackend, StoreResolution } from './store.js';
3
+ /** ADR 0056 one-shot bootstrap code prefix (`kody_bc_…`). */
4
+ export declare const cliBootstrapCodePrefix = "kody_bc_";
5
+ export declare const bootstrapRedeemPath = "v1/tokens/bootstrap/redeem";
6
+ export type BootstrapRedeemResponse = {
7
+ token: string;
8
+ token_type?: string;
9
+ id: string;
10
+ name?: string | null;
11
+ scopes?: Array<string>;
12
+ status?: string;
13
+ idle_ttl_seconds?: number;
14
+ expires_at?: string | null;
15
+ max_expires_at?: string | null;
16
+ created_via?: string;
17
+ };
18
+ export declare function parseCliBootstrapCode(value: string): {
19
+ codeId: string;
20
+ secret: string;
21
+ } | null;
22
+ export declare function assertCliBootstrapCode(code: string): string;
23
+ /**
24
+ * POST /v1/tokens/bootstrap/redeem with JSON `{ code }` and **no** Authorization
25
+ * header (ADR 0056). Returns the minted `kody_at_…` once.
26
+ */
27
+ export declare function redeemBootstrapCode(input: {
28
+ code: string;
29
+ apiUrl?: string;
30
+ fetchFn?: typeof fetch;
31
+ }): Promise<BootstrapRedeemResponse>;
32
+ export declare function storedApiTokenFromRedeem(input: {
33
+ apiUrl: string;
34
+ redeemed: BootstrapRedeemResponse;
35
+ }): StoredApiToken;
36
+ /**
37
+ * Redeem a one-shot `kody_bc_…` and persist the resulting API token for
38
+ * `execute --local`. Never returns the token string to callers that print
39
+ * success output — use `stored.tokenId` / backend kind only.
40
+ */
41
+ export declare function authBootstrap(input: {
42
+ code: string;
43
+ apiUrl?: string;
44
+ fetchFn?: typeof fetch;
45
+ backend?: SecretBackend;
46
+ resolution?: StoreResolution;
47
+ }): Promise<{
48
+ stored: StoredApiToken;
49
+ backendKind: SecretBackend['kind'];
50
+ backendPath?: string;
51
+ }>;
@@ -0,0 +1,157 @@
1
+ import { assertTokenSafeApiUrl, capabilityProxyUrl } from './capability-proxy.js';
2
+ import { cliName, defaultApiUrl } from './defaults.js';
3
+ import { describeNetworkError } from './network-error.js';
4
+ import { readPackageVersion } from './package-info.js';
5
+ import { saveStoredApiToken, } from './api-token-store.js';
6
+ /** ADR 0056 one-shot bootstrap code prefix (`kody_bc_…`). */
7
+ export const cliBootstrapCodePrefix = 'kody_bc_';
8
+ /** Platform shape: `kody_bc_<16 alnum>_<32 base64url>`. */
9
+ const bootstrapCodePattern = /^kody_bc_([a-z0-9]{16})_([A-Za-z0-9_-]{32})$/;
10
+ export const bootstrapRedeemPath = 'v1/tokens/bootstrap/redeem';
11
+ export function parseCliBootstrapCode(value) {
12
+ const match = bootstrapCodePattern.exec(value.trim());
13
+ if (!match)
14
+ return null;
15
+ const [, codeId, secret] = match;
16
+ if (!codeId || !secret)
17
+ return null;
18
+ return { codeId, secret };
19
+ }
20
+ export function assertCliBootstrapCode(code) {
21
+ const trimmed = code.trim();
22
+ if (!parseCliBootstrapCode(trimmed)) {
23
+ throw new Error(`Invalid bootstrap code. Expected a one-shot ${cliBootstrapCodePrefix}… from cliCredentialBootstrap (MCP api / kody.cliCredentialBootstrap).`);
24
+ }
25
+ return trimmed;
26
+ }
27
+ /**
28
+ * POST /v1/tokens/bootstrap/redeem with JSON `{ code }` and **no** Authorization
29
+ * header (ADR 0056). Returns the minted `kody_at_…` once.
30
+ */
31
+ export async function redeemBootstrapCode(input) {
32
+ const code = assertCliBootstrapCode(input.code);
33
+ const apiUrl = input.apiUrl || defaultApiUrl;
34
+ assertTokenSafeApiUrl(apiUrl);
35
+ const url = capabilityProxyUrl(apiUrl, bootstrapRedeemPath);
36
+ const fetchFn = input.fetchFn ?? fetch;
37
+ let response;
38
+ try {
39
+ response = await fetchFn(url, {
40
+ method: 'POST',
41
+ headers: {
42
+ accept: 'application/json',
43
+ 'content-type': 'application/json',
44
+ 'user-agent': `${cliName}/${readPackageVersion()}`,
45
+ },
46
+ body: JSON.stringify({ code }),
47
+ });
48
+ }
49
+ catch (error) {
50
+ const reason = describeNetworkError(error);
51
+ throw new Error(`Could not reach the Kody API at ${url.origin} (${reason}). Check --api-url / KODY_API_URL and your network.`);
52
+ }
53
+ const body = await readJson(response);
54
+ if (!response.ok) {
55
+ throw describeRedeemFailure(response.status, body, url);
56
+ }
57
+ return parseRedeemResponse(body);
58
+ }
59
+ export function storedApiTokenFromRedeem(input) {
60
+ const token = input.redeemed.token.trim();
61
+ if (!token.startsWith('kody_at_')) {
62
+ throw new Error('Bootstrap redeem did not return a scoped kody_at_… API token.');
63
+ }
64
+ return {
65
+ version: 1,
66
+ apiUrl: input.apiUrl,
67
+ token,
68
+ tokenId: input.redeemed.id,
69
+ ...(input.redeemed.name ? { name: input.redeemed.name } : {}),
70
+ ...(Array.isArray(input.redeemed.scopes) ? { scopes: input.redeemed.scopes } : {}),
71
+ expiresAt: input.redeemed.expires_at ?? null,
72
+ maxExpiresAt: input.redeemed.max_expires_at ?? null,
73
+ createdVia: input.redeemed.created_via ?? 'cli-bootstrap',
74
+ };
75
+ }
76
+ /**
77
+ * Redeem a one-shot `kody_bc_…` and persist the resulting API token for
78
+ * `execute --local`. Never returns the token string to callers that print
79
+ * success output — use `stored.tokenId` / backend kind only.
80
+ */
81
+ export async function authBootstrap(input) {
82
+ const apiUrl = input.apiUrl || defaultApiUrl;
83
+ const redeemed = await redeemBootstrapCode({
84
+ code: input.code,
85
+ apiUrl,
86
+ fetchFn: input.fetchFn,
87
+ });
88
+ const stored = storedApiTokenFromRedeem({ apiUrl, redeemed });
89
+ const saved = saveStoredApiToken(stored, input.backend, input.resolution);
90
+ return {
91
+ stored,
92
+ backendKind: saved.backend.kind,
93
+ ...(saved.backend.path ? { backendPath: saved.backend.path } : {}),
94
+ };
95
+ }
96
+ function parseRedeemResponse(body) {
97
+ if (!isRecord(body) || typeof body.token !== 'string' || typeof body.id !== 'string') {
98
+ throw new Error('Bootstrap redeem returned an unexpected response.');
99
+ }
100
+ return {
101
+ token: body.token,
102
+ token_type: typeof body.token_type === 'string' ? body.token_type : undefined,
103
+ id: body.id,
104
+ name: typeof body.name === 'string' ? body.name : null,
105
+ scopes: Array.isArray(body.scopes)
106
+ ? body.scopes.filter((scope) => typeof scope === 'string')
107
+ : undefined,
108
+ status: typeof body.status === 'string' ? body.status : undefined,
109
+ idle_ttl_seconds: typeof body.idle_ttl_seconds === 'number' ? body.idle_ttl_seconds : undefined,
110
+ expires_at: typeof body.expires_at === 'string' ? body.expires_at : null,
111
+ max_expires_at: typeof body.max_expires_at === 'string' ? body.max_expires_at : null,
112
+ created_via: typeof body.created_via === 'string' ? body.created_via : undefined,
113
+ };
114
+ }
115
+ function describeRedeemFailure(status, body, url) {
116
+ const failure = readErrorBody(body);
117
+ const detail = failure?.message ? ` Server said: ${failure.message}` : '';
118
+ if (status === 400 || status === 401 || status === 403 || status === 404) {
119
+ return new Error(`Bootstrap redeem failed (HTTP ${status}). The code may be invalid, expired, or already used. Call cliCredentialBootstrap again for a fresh code.${detail}`);
120
+ }
121
+ return new Error(failure?.message ??
122
+ `Bootstrap redeem failed with HTTP ${status} (${url.pathname}).${detail}`);
123
+ }
124
+ async function readJson(response) {
125
+ const text = await response.text();
126
+ if (!text)
127
+ return null;
128
+ try {
129
+ return JSON.parse(text);
130
+ }
131
+ catch {
132
+ return text;
133
+ }
134
+ }
135
+ function readErrorBody(body) {
136
+ if (!isRecord(body) || body.error == null) {
137
+ if (typeof body === 'string' && body.trim())
138
+ return { code: null, message: body };
139
+ if (isRecord(body) && typeof body.message === 'string') {
140
+ return { code: null, message: body.message };
141
+ }
142
+ return null;
143
+ }
144
+ const { error } = body;
145
+ if (typeof error === 'string')
146
+ return { code: null, message: error };
147
+ if (isRecord(error)) {
148
+ const code = typeof error.code === 'string' ? error.code : null;
149
+ const message = typeof error.message === 'string' ? error.message : code ?? JSON.stringify(error);
150
+ return { code, message };
151
+ }
152
+ return { code: null, message: String(error) };
153
+ }
154
+ function isRecord(value) {
155
+ return value !== null && typeof value === 'object' && !Array.isArray(value);
156
+ }
157
+ //# sourceMappingURL=auth-bootstrap.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-bootstrap.js","sourceRoot":"","sources":["../src/auth-bootstrap.ts"],"names":[],"mappings":"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"}
package/dist/cli.d.ts CHANGED
@@ -1,6 +1,8 @@
1
- export { readApiToken, requireApiToken as resolveApiToken } from './api-token.js';
1
+ import { resolveScopedApiToken } from './api-token.js';
2
+ export { readApiToken, requireApiToken as resolveApiToken, resolveScopedApiToken, } from './api-token.js';
2
3
  export { resolveLocalExecuteBearer } from './local-execute-auth.js';
3
- export type CommandName = 'login' | 'logout' | 'status' | 'whoami' | 'search' | 'execute' | 'install' | 'skill' | 'help' | 'version';
4
+ export { authBootstrap, redeemBootstrapCode } from './auth-bootstrap.js';
5
+ export type CommandName = 'login' | 'logout' | 'status' | 'auth' | 'whoami' | 'search' | 'execute' | 'install' | 'skill' | 'help' | 'version';
4
6
  export declare function apiUrlFrom(values: {
5
7
  apiUrl?: string;
6
8
  }, env?: NodeJS.ProcessEnv): string;
@@ -58,9 +60,10 @@ export declare function buildExecuteToolArgs(input: {
58
60
  }): Record<string, unknown>;
59
61
  /**
60
62
  * Prefer a scoped API token when the user passed `--token`, or when
61
- * `KODY_API_TOKEN` is set and there is no stored `kody login` session.
62
- * Logged-in MCP OAuth still wins over an env-only token so a leftover
63
- * `KODY_API_TOKEN` does not hijack cloud MCP commands.
63
+ * `KODY_API_TOKEN` / a stored bootstrap token is available and there is no
64
+ * stored `kody login` session. Logged-in MCP OAuth still wins over an
65
+ * env-only or stored token so a leftover token does not hijack cloud MCP
66
+ * commands.
64
67
  */
65
68
  export declare function shouldUseApiToken(input: {
66
69
  tokenValues: {
@@ -69,6 +72,9 @@ export declare function shouldUseApiToken(input: {
69
72
  mcpUrl: string;
70
73
  allowEnvWithoutLogin: boolean;
71
74
  env?: NodeJS.ProcessEnv;
75
+ apiUrl?: string;
72
76
  /** Override session detection (tests). */
73
77
  hasSession?: boolean;
78
+ /** Test seam for stored bootstrap/API token lookup. */
79
+ loadApiToken?: NonNullable<Parameters<typeof resolveScopedApiToken>[0]>['loadApiToken'];
74
80
  }): boolean;
package/dist/cli.js CHANGED
@@ -1,6 +1,8 @@
1
1
  import { parseArgs } from 'node:util';
2
2
  import { readFile } from 'node:fs/promises';
3
- import { hasExplicitTokenFlag, readApiToken, requireApiToken, } from './api-token.js';
3
+ import { hasExplicitTokenFlag, requireApiToken, resolveScopedApiToken, } from './api-token.js';
4
+ import { deleteStoredApiToken, loadStoredApiToken, } from './api-token-store.js';
5
+ import { authBootstrap } from './auth-bootstrap.js';
4
6
  import { defaultApiUrl, defaultMcpUrl, modernMcpProtocolVersion } from './defaults.js';
5
7
  import { usage } from './help.js';
6
8
  import { ensureFreshCredentials, login } from './auth.js';
@@ -15,8 +17,9 @@ import { runRemoteExecuteWithToken } from './remote-execute.js';
15
17
  import { installSkill } from './skill.js';
16
18
  import { readPackageVersion } from './package-info.js';
17
19
  import { redactError } from './redact.js';
18
- export { readApiToken, requireApiToken as resolveApiToken } from './api-token.js';
20
+ export { readApiToken, requireApiToken as resolveApiToken, resolveScopedApiToken, } from './api-token.js';
19
21
  export { resolveLocalExecuteBearer } from './local-execute-auth.js';
22
+ export { authBootstrap, redeemBootstrapCode } from './auth-bootstrap.js';
20
23
  function mcpUrlFrom(values) {
21
24
  return values.mcpUrl || process.env.KODY_MCP_URL || defaultMcpUrl;
22
25
  }
@@ -66,6 +69,7 @@ export function resolveCommand(argv) {
66
69
  case 'login':
67
70
  case 'logout':
68
71
  case 'status':
72
+ case 'auth':
69
73
  case 'whoami':
70
74
  case 'search':
71
75
  case 'execute':
@@ -125,39 +129,103 @@ async function dispatch(parsed, write, writeErr) {
125
129
  return 0;
126
130
  }
127
131
  case 'logout': {
128
- const result = deleteCredentials(mcpUrl);
129
- write(result.deleted ? 'Logged out.\n' : 'No stored credentials.\n');
132
+ const apiUrl = apiUrlFrom({
133
+ apiUrl: typeof parsed.values['api-url'] === 'string'
134
+ ? parsed.values['api-url']
135
+ : undefined,
136
+ });
137
+ const oauth = deleteCredentials(mcpUrl);
138
+ const apiToken = deleteStoredApiToken(apiUrl);
139
+ if (!oauth.deleted && !apiToken.deleted) {
140
+ write('No stored credentials.\n');
141
+ return 0;
142
+ }
143
+ const parts = [];
144
+ if (oauth.deleted)
145
+ parts.push('Logged out of kody login.');
146
+ if (apiToken.deleted)
147
+ parts.push('Cleared stored bootstrap/API token.');
148
+ write(`${parts.join(' ')}\n`);
130
149
  return 0;
131
150
  }
132
151
  case 'status': {
152
+ const apiUrl = apiUrlFrom({
153
+ apiUrl: typeof parsed.values['api-url'] === 'string'
154
+ ? parsed.values['api-url']
155
+ : undefined,
156
+ });
133
157
  const credentials = loadCredentials(mcpUrl);
134
- if (!credentials) {
158
+ const storedApi = loadStoredApiToken(apiUrl);
159
+ if (!credentials && !storedApi) {
135
160
  write('Not logged in.\n');
136
161
  return 1;
137
162
  }
138
- const expires = credentials.expiresAt
139
- ? new Date(credentials.expiresAt).toISOString()
140
- : 'unknown';
163
+ const lines = [];
164
+ if (credentials) {
165
+ const expires = credentials.expiresAt
166
+ ? new Date(credentials.expiresAt).toISOString()
167
+ : 'unknown';
168
+ lines.push(`mcp: ${credentials.mcpUrl}`, `logged in: yes`, `access token expires: ${expires}`, `refresh token: ${credentials.refreshToken ? 'yes' : 'no'}`, `scope: ${credentials.scope ?? 'unknown'}`);
169
+ }
170
+ else {
171
+ lines.push(`mcp: ${mcpUrl}`, `logged in: no`);
172
+ }
173
+ if (storedApi) {
174
+ const scopes = storedApi.scopes?.join(', ') || '(unknown)';
175
+ lines.push(`api: ${storedApi.apiUrl}`, `stored API token: yes (${storedApi.tokenId})`, `API token scopes: ${scopes}`, `API token expires: ${storedApi.expiresAt ?? 'unknown'}`, `API token via: ${storedApi.createdVia ?? 'unknown'}`);
176
+ }
177
+ else {
178
+ lines.push(`api: ${apiUrl}`, `stored API token: no`);
179
+ }
180
+ lines.push('');
181
+ write(lines.join('\n'));
182
+ return 0;
183
+ }
184
+ case 'auth': {
185
+ const action = parsed.positionals[0];
186
+ if (action !== 'bootstrap') {
187
+ throw new Error('Usage: kody auth bootstrap --code <kody_bc_…> [--api-url <url>]');
188
+ }
189
+ const code = typeof parsed.values.code === 'string' ? parsed.values.code.trim() : '';
190
+ if (!code) {
191
+ throw new Error('Provide --code <kody_bc_…> from cliCredentialBootstrap (MCP api / kody.cliCredentialBootstrap).');
192
+ }
193
+ const apiUrl = apiUrlFrom({
194
+ apiUrl: typeof parsed.values['api-url'] === 'string'
195
+ ? parsed.values['api-url']
196
+ : undefined,
197
+ });
198
+ const result = await authBootstrap({ code, apiUrl });
199
+ const scopes = result.stored.scopes?.join(', ') || '(none)';
141
200
  write([
142
- `mcp: ${credentials.mcpUrl}`,
143
- `logged in: yes`,
144
- `access token expires: ${expires}`,
145
- `refresh token: ${credentials.refreshToken ? 'yes' : 'no'}`,
146
- `scope: ${credentials.scope ?? 'unknown'}`,
201
+ `Bootstrap API token stored for execute --local, search, whoami, and token-auth cloud execute.`,
202
+ `api: ${result.stored.apiUrl}`,
203
+ `token id: ${result.stored.tokenId}`,
204
+ `scopes: ${scopes}`,
205
+ `expires: ${result.stored.expiresAt ?? 'unknown'}`,
206
+ result.backendKind === 'file' && result.backendPath
207
+ ? `OS keychain was unavailable; token saved at ${result.backendPath} (mode 0600).`
208
+ : 'Token stored in the OS keychain.',
147
209
  '',
148
210
  ].join('\n'));
149
211
  return 0;
150
212
  }
151
213
  case 'whoami': {
152
214
  const tokenValues = tokenFlagValues(parsed.values);
153
- if (shouldUseApiToken({ tokenValues, mcpUrl, allowEnvWithoutLogin: true })) {
215
+ const apiUrl = apiUrlFrom({
216
+ apiUrl: typeof parsed.values['api-url'] === 'string'
217
+ ? parsed.values['api-url']
218
+ : undefined,
219
+ });
220
+ if (shouldUseApiToken({
221
+ tokenValues,
222
+ mcpUrl,
223
+ apiUrl,
224
+ allowEnvWithoutLogin: true,
225
+ })) {
154
226
  const identity = await whoamiWithApiToken({
155
- token: requireApiToken(tokenValues, process.env, 'whoami'),
156
- apiUrl: apiUrlFrom({
157
- apiUrl: typeof parsed.values['api-url'] === 'string'
158
- ? parsed.values['api-url']
159
- : undefined,
160
- }),
227
+ token: requireApiToken(tokenValues, process.env, 'whoami', { apiUrl }),
228
+ apiUrl,
161
229
  });
162
230
  if (json) {
163
231
  write(`${JSON.stringify(identity, null, 2)}\n`);
@@ -194,14 +262,20 @@ async function dispatch(parsed, write, writeErr) {
194
262
  case 'search': {
195
263
  const query = parsed.positionals.join(' ').trim();
196
264
  const tokenValues = tokenFlagValues(parsed.values);
197
- if (shouldUseApiToken({ tokenValues, mcpUrl, allowEnvWithoutLogin: true })) {
265
+ const apiUrl = apiUrlFrom({
266
+ apiUrl: typeof parsed.values['api-url'] === 'string'
267
+ ? parsed.values['api-url']
268
+ : undefined,
269
+ });
270
+ if (shouldUseApiToken({
271
+ tokenValues,
272
+ mcpUrl,
273
+ apiUrl,
274
+ allowEnvWithoutLogin: true,
275
+ })) {
198
276
  const result = await searchWithApiToken({
199
- token: requireApiToken(tokenValues, process.env, 'search'),
200
- apiUrl: apiUrlFrom({
201
- apiUrl: typeof parsed.values['api-url'] === 'string'
202
- ? parsed.values['api-url']
203
- : undefined,
204
- }),
277
+ token: requireApiToken(tokenValues, process.env, 'search', { apiUrl }),
278
+ apiUrl,
205
279
  query: query || undefined,
206
280
  entity: typeof parsed.values.entity === 'string' ? parsed.values.entity : undefined,
207
281
  domain: typeof parsed.values.domain === 'string' ? parsed.values.domain : undefined,
@@ -266,6 +340,7 @@ async function dispatch(parsed, write, writeErr) {
266
340
  shouldUseApiToken({
267
341
  tokenValues,
268
342
  mcpUrl,
343
+ apiUrl,
269
344
  allowEnvWithoutLogin: true,
270
345
  });
271
346
  const result = local
@@ -276,6 +351,7 @@ async function dispatch(parsed, write, writeErr) {
276
351
  token: await resolveLocalExecuteBearer({
277
352
  tokenValues,
278
353
  mcpUrl,
354
+ apiUrl,
279
355
  purpose: 'execute --local',
280
356
  }),
281
357
  apiUrl,
@@ -287,7 +363,7 @@ async function dispatch(parsed, write, writeErr) {
287
363
  invoke,
288
364
  params: args.params,
289
365
  conversationId: args.conversationId,
290
- token: requireApiToken(tokenValues, process.env, 'execute with an API token'),
366
+ token: requireApiToken(tokenValues, process.env, 'execute with an API token', { apiUrl }),
291
367
  apiUrl,
292
368
  })
293
369
  : await callKodyTool({ name: 'execute', args, mcpUrl });
@@ -368,17 +444,24 @@ function tokenFlagValues(values) {
368
444
  }
369
445
  /**
370
446
  * Prefer a scoped API token when the user passed `--token`, or when
371
- * `KODY_API_TOKEN` is set and there is no stored `kody login` session.
372
- * Logged-in MCP OAuth still wins over an env-only token so a leftover
373
- * `KODY_API_TOKEN` does not hijack cloud MCP commands.
447
+ * `KODY_API_TOKEN` / a stored bootstrap token is available and there is no
448
+ * stored `kody login` session. Logged-in MCP OAuth still wins over an
449
+ * env-only or stored token so a leftover token does not hijack cloud MCP
450
+ * commands.
374
451
  */
375
452
  export function shouldUseApiToken(input) {
376
453
  if (hasExplicitTokenFlag(input.tokenValues))
377
454
  return true;
378
455
  if (!input.allowEnvWithoutLogin)
379
456
  return false;
380
- if (!readApiToken(input.tokenValues, input.env))
457
+ if (!resolveScopedApiToken({
458
+ tokenValues: input.tokenValues,
459
+ env: input.env,
460
+ apiUrl: input.apiUrl,
461
+ loadApiToken: input.loadApiToken,
462
+ })) {
381
463
  return false;
464
+ }
382
465
  const loggedIn = input.hasSession ?? loadCredentials(input.mcpUrl) != null;
383
466
  return !loggedIn;
384
467
  }
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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"}
package/dist/help.js CHANGED
@@ -7,8 +7,9 @@ Install Kody as a remote MCP server in local agents, or use this CLI as a local
7
7
 
8
8
  Usage:
9
9
  kody login [--mcp-url <url>] [--no-browser]
10
- kody logout [--mcp-url <url>]
11
- kody status [--mcp-url <url>]
10
+ kody logout [--mcp-url <url>] [--api-url <url>]
11
+ kody status [--mcp-url <url>] [--api-url <url>]
12
+ kody auth bootstrap --code <kody_bc_…> [--api-url <url>]
12
13
  kody whoami [--mcp-url <url>] [--token <token>] [--api-url <url>] [--json]
13
14
  kody search [query] [--entity <ref>] [--domain <id>] [--limit <n>] [--token <token>] [--api-url <url>] [--json]
14
15
  kody execute [--invoke <ref> | --code <esm> | --file <path>] [--params <json>] [--conversation-id <id>] [--json]
@@ -22,25 +23,37 @@ Usage:
22
23
 
23
24
  --clients Comma-separated ids: ${hostIds.join(', ')}
24
25
 
26
+ auth bootstrap
27
+ Redeem a one-shot \`kody_bc_…\` from MCP \`cliCredentialBootstrap\`
28
+ (POST /v1/tokens/bootstrap/redeem, no Authorization header).
29
+ Stores the resulting \`kody_at_…\` for \`execute --local\`,
30
+ search, whoami, and token-auth cloud execute without printing
31
+ the token. Prefer this over tokenCreate for agents already on
32
+ MCP. Interactive humans can use \`kody login\` instead.
33
+
25
34
  --token / ${apiTokenEnvVar}
26
35
  Scoped API token (preferred via env). With no \`kody login\`
27
36
  session, search / whoami / execute use the Open API and
28
37
  CapabilityProxy — including cloud execute without --local.
38
+ Auth priority matches \`execute --local\`: \`--token\` /
39
+ ${apiTokenEnvVar}; stored bootstrap/API token from
40
+ \`auth bootstrap\`; then \`kody login\` where applicable.
29
41
  Mint with the MCP \`api\` tool \`tokenCreate\` (include
30
- \`local-execute\` plus the capability scopes you need).
31
- For \`execute --local\`, \`--token\` / ${apiTokenEnvVar} wins
32
- when set; otherwise a valid \`kody login\` session is used as
33
- the Bearer (no tokenCreate exchange).
42
+ \`local-execute\` plus the capability scopes you need), or use
43
+ \`auth bootstrap\` after \`cliCredentialBootstrap\`.
44
+ For \`execute --local\`, a valid \`kody login\` session can also
45
+ supply Bearer when no scoped token is available (no tokenCreate
46
+ exchange).
34
47
 
35
48
  --local Run the execute module on this machine (workerd, Linux/macOS).
36
49
  Requires Node.js 22 or newer. Auth: \`--token\` /
37
- ${apiTokenEnvVar}, or else \`kody login\`. Static kody:@…
38
- imports are fetched via POST /v1/local-execute/package-graph
39
- and embedded in local workerd (CapabilityProxy only for
40
- per-call kody:runtime hops — never a whole-module cloud
41
- kody.execute defer). Fails clearly when that package-graph
42
- API is unavailable. Cloud token execute (no --local) uses
43
- CapabilityProxy → kody.execute for every module.
50
+ ${apiTokenEnvVar}, else stored \`auth bootstrap\` token, else
51
+ \`kody login\`. Static kody:@… imports are fetched via POST
52
+ /v1/local-execute/package-graph and embedded in local workerd
53
+ (CapabilityProxy only for per-call kody:runtime hops — never a
54
+ whole-module cloud kody.execute defer). Fails clearly when that
55
+ package-graph API is unavailable. Cloud token execute (no
56
+ --local) uses CapabilityProxy → kody.execute for every module.
44
57
 
45
58
  Environment:
46
59
  KODY_MCP_URL Override the default MCP URL (${defaultMcpUrl})
package/dist/help.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"help.js","sourceRoot":"","sources":["../src/help.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,aAAa,EAAE,aAAa,EAAE,MAAM,eAAe,CAAA;AAC3F,OAAO,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAA;AAC3C,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAA;AAEtD,MAAM,CAAC,MAAM,KAAK,GAAG,YAAY,kBAAkB,EAAE;;;;;;;;;;;;;;;;;QAiB7C,aAAa,CAAC,aAAa,CAAC;;oCAEA,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC;;cAExC,cAAc;;;;;;sDAM0B,cAAc;;;;;;eAMrD,cAAc;;;;;;;;;sDASyB,aAAa;IAC/D,cAAc;mDACiC,aAAa;;;CAG/D,CAAA"}
1
+ {"version":3,"file":"help.js","sourceRoot":"","sources":["../src/help.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,aAAa,EAAE,aAAa,EAAE,aAAa,EAAE,MAAM,eAAe,CAAA;AAC3F,OAAO,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAA;AAC3C,OAAO,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAA;AAEtD,MAAM,CAAC,MAAM,KAAK,GAAG,YAAY,kBAAkB,EAAE;;;;;;;;;;;;;;;;;;QAkB7C,aAAa,CAAC,aAAa,CAAC;;oCAEA,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC;;;;;;;;;;cAUxC,cAAc;;;;;eAKb,cAAc;;;;;;;;;;;eAWd,cAAc;;;;;;;;;sDASyB,aAAa;IAC/D,cAAc;mDACiC,aAAa;;;CAG/D,CAAA"}
@@ -1,20 +1,18 @@
1
1
  import { ensureFreshCredentials } from './auth.js';
2
+ import { type ResolveScopedApiTokenInput } from './api-token.js';
2
3
  import type { SecretBackend } from './store.js';
3
4
  /**
4
5
  * Bearer for CapabilityProxy / package-graph under `execute --local`.
5
6
  *
6
- * Priority: `--token` / `KODY_API_TOKEN`, else a fresh `kody login` OAuth
7
- * access token (never printed). No under-the-hood `tokenCreate` exchange.
7
+ * Priority:
8
+ * 1. `--token` / `KODY_API_TOKEN`
9
+ * 2. Stored bootstrap/API token from `auth bootstrap --code`
10
+ * 3. Fresh `kody login` OAuth access token (never printed)
8
11
  *
9
- * Platform must accept MCP/user OAuth on those Open API routes
10
- * (https://github.com/kentcdodds/kody/issues/2812); until then a login-only
11
- * bearer gets 401 and the CLI surfaces that gap.
12
+ * No under-the-hood `tokenCreate` exchange. Do not scavenge host MCP tokens
13
+ * (ADR 0053).
12
14
  */
13
- export declare function resolveLocalExecuteBearer(input: {
14
- tokenValues?: {
15
- token?: string;
16
- };
17
- env?: NodeJS.ProcessEnv;
15
+ export declare function resolveLocalExecuteBearer(input: ResolveScopedApiTokenInput & {
18
16
  mcpUrl?: string;
19
17
  backend?: SecretBackend;
20
18
  fetchFn?: typeof fetch;
@@ -1,17 +1,18 @@
1
1
  import { ensureFreshCredentials } from './auth.js';
2
- import { missingLocalExecuteAuthMessage, readApiToken, } from './api-token.js';
2
+ import { missingLocalExecuteAuthMessage, resolveScopedApiToken, } from './api-token.js';
3
3
  /**
4
4
  * Bearer for CapabilityProxy / package-graph under `execute --local`.
5
5
  *
6
- * Priority: `--token` / `KODY_API_TOKEN`, else a fresh `kody login` OAuth
7
- * access token (never printed). No under-the-hood `tokenCreate` exchange.
6
+ * Priority:
7
+ * 1. `--token` / `KODY_API_TOKEN`
8
+ * 2. Stored bootstrap/API token from `auth bootstrap --code`
9
+ * 3. Fresh `kody login` OAuth access token (never printed)
8
10
  *
9
- * Platform must accept MCP/user OAuth on those Open API routes
10
- * (https://github.com/kentcdodds/kody/issues/2812); until then a login-only
11
- * bearer gets 401 and the CLI surfaces that gap.
11
+ * No under-the-hood `tokenCreate` exchange. Do not scavenge host MCP tokens
12
+ * (ADR 0053).
12
13
  */
13
14
  export async function resolveLocalExecuteBearer(input) {
14
- const token = readApiToken(input.tokenValues, input.env);
15
+ const token = resolveScopedApiToken(input);
15
16
  if (token)
16
17
  return token;
17
18
  const ensure = input.ensureCredentials ?? ensureFreshCredentials;
@@ -1 +1 @@
1
- {"version":3,"file":"local-execute-auth.js","sourceRoot":"","sources":["../src/local-execute-auth.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,sBAAsB,EAAE,MAAM,WAAW,CAAA;AAClD,OAAO,EACN,8BAA8B,EAC9B,YAAY,GACZ,MAAM,gBAAgB,CAAA;AAGvB;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,yBAAyB,CAAC,KAU/C;IACA,MAAM,KAAK,GAAG,YAAY,CAAC,KAAK,CAAC,WAAW,EAAE,KAAK,CAAC,GAAG,CAAC,CAAA;IACxD,IAAI,KAAK;QAAE,OAAO,KAAK,CAAA;IAEvB,MAAM,MAAM,GAAG,KAAK,CAAC,iBAAiB,IAAI,sBAAsB,CAAA;IAChE,IAAI,CAAC;QACJ,MAAM,WAAW,GAAG,MAAM,MAAM,CAAC;YAChC,MAAM,EAAE,KAAK,CAAC,MAAM;YACpB,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,GAAG,EAAE,KAAK,CAAC,GAAG;SACd,CAAC,CAAA;QACF,OAAO,WAAW,CAAC,WAAW,CAAA;IAC/B,CAAC;IAAC,MAAM,CAAC;QACR,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,KAAK,CAAC,OAAO,IAAI,iBAAiB,CAAC,CAAC,CAAA;IACpF,CAAC;AACF,CAAC"}
1
+ {"version":3,"file":"local-execute-auth.js","sourceRoot":"","sources":["../src/local-execute-auth.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,sBAAsB,EAAE,MAAM,WAAW,CAAA;AAClD,OAAO,EACN,8BAA8B,EAC9B,qBAAqB,GAErB,MAAM,gBAAgB,CAAA;AAGvB;;;;;;;;;;GAUG;AACH,MAAM,CAAC,KAAK,UAAU,yBAAyB,CAC9C,KAQC;IAED,MAAM,KAAK,GAAG,qBAAqB,CAAC,KAAK,CAAC,CAAA;IAC1C,IAAI,KAAK;QAAE,OAAO,KAAK,CAAA;IAEvB,MAAM,MAAM,GAAG,KAAK,CAAC,iBAAiB,IAAI,sBAAsB,CAAA;IAChE,IAAI,CAAC;QACJ,MAAM,WAAW,GAAG,MAAM,MAAM,CAAC;YAChC,MAAM,EAAE,KAAK,CAAC,MAAM;YACpB,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,OAAO,EAAE,KAAK,CAAC,OAAO;YACtB,GAAG,EAAE,KAAK,CAAC,GAAG;SACd,CAAC,CAAA;QACF,OAAO,WAAW,CAAC,WAAW,CAAA;IAC/B,CAAC;IAAC,MAAM,CAAC;QACR,MAAM,IAAI,KAAK,CAAC,8BAA8B,CAAC,KAAK,CAAC,OAAO,IAAI,iBAAiB,CAAC,CAAC,CAAA;IACpF,CAAC;AACF,CAAC"}
package/dist/redact.js CHANGED
@@ -1,6 +1,10 @@
1
1
  const secretPattern = /(access_token|refresh_token|client_secret|authorization)["']?\s*[:=]\s*["']?[^\s"',}]+/gi;
2
+ /** Never leak minted API tokens or one-shot bootstrap codes in CLI output. */
3
+ const kodySecretPattern = /\bkody_(?:at|bc)_[A-Za-z0-9_-]+\b/g;
2
4
  export function redact(value) {
3
- return value.replace(secretPattern, '$1=[redacted]');
5
+ return value
6
+ .replace(secretPattern, '$1=[redacted]')
7
+ .replace(kodySecretPattern, 'kody_[redacted]');
4
8
  }
5
9
  export function redactError(error) {
6
10
  if (error instanceof Error) {
@@ -1 +1 @@
1
- {"version":3,"file":"redact.js","sourceRoot":"","sources":["../src/redact.ts"],"names":[],"mappings":"AAAA,MAAM,aAAa,GAClB,0FAA0F,CAAA;AAE3F,MAAM,UAAU,MAAM,CAAC,KAAa;IACnC,OAAO,KAAK,CAAC,OAAO,CAAC,aAAa,EAAE,eAAe,CAAC,CAAA;AACrD,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,KAAc;IACzC,IAAI,KAAK,YAAY,KAAK,EAAE,CAAC;QAC5B,KAAK,CAAC,OAAO,GAAG,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,CAAA;QACrC,OAAO,KAAK,CAAA;IACb,CAAC;IACD,OAAO,IAAI,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAA;AACxC,CAAC"}
1
+ {"version":3,"file":"redact.js","sourceRoot":"","sources":["../src/redact.ts"],"names":[],"mappings":"AAAA,MAAM,aAAa,GAClB,0FAA0F,CAAA;AAE3F,8EAA8E;AAC9E,MAAM,iBAAiB,GAAG,oCAAoC,CAAA;AAE9D,MAAM,UAAU,MAAM,CAAC,KAAa;IACnC,OAAO,KAAK;SACV,OAAO,CAAC,aAAa,EAAE,eAAe,CAAC;SACvC,OAAO,CAAC,iBAAiB,EAAE,iBAAiB,CAAC,CAAA;AAChD,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,KAAc;IACzC,IAAI,KAAK,YAAY,KAAK,EAAE,CAAC;QAC5B,KAAK,CAAC,OAAO,GAAG,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,CAAA;QACrC,OAAO,KAAK,CAAA;IACb,CAAC;IACD,OAAO,IAAI,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAA;AACxC,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kodycodes/cli",
3
- "version": "1.7.0",
3
+ "version": "1.8.1",
4
4
  "description": "Official Kody MCP client CLI: login, secure token storage, search, and execute.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -81,19 +81,28 @@ whole-module cloud defer). If that package-graph API is missing, `--local`
81
81
  fails clearly rather than silently billing a remote execute.
82
82
 
83
83
  For `execute --local` auth: `--token` / `KODY_API_TOKEN` wins when set;
84
- otherwise use a valid `kody login` session (OAuth access token as Bearer —
85
- never print it, never mint via `tokenCreate` under the hood). Until the Open
86
- API accepts MCP OAuth on CapabilityProxy / package-graph
87
- (https://github.com/kentcdodds/kody/issues/2812), mint a scoped token with
88
- the MCP `api` tool `tokenCreate` — include `local-execute` plus the capability
89
- scopes the module calls — and pass `--token` or `KODY_API_TOKEN`. If neither
90
- login nor a token is set, the CLI error says that. `insufficient_scope` means
91
- the token is missing a scope; `feature_disabled` means the account
84
+ otherwise a stored token from `kody auth bootstrap --code` (after MCP
85
+ `cliCredentialBootstrap`); otherwise a valid `kody login` session (OAuth
86
+ access token as Bearer — never print it, never mint via `tokenCreate` under
87
+ the hood). Prefer bootstrap over `tokenCreate` for agents already on MCP so
88
+ `kody_at_…` never appears in chat. Until the Open API accepts MCP OAuth on
89
+ CapabilityProxy / package-graph
90
+ (https://github.com/kentcdodds/kody/issues/2812), use bootstrap or mint a
91
+ scoped token with the MCP `api` tool `tokenCreate` — include `local-execute`
92
+ plus the capability scopes the module calls — and pass `--token` or
93
+ `KODY_API_TOKEN`. If none of those are available, the CLI error says that
94
+ (bootstrap → login → tokenCreate for CI). `insufficient_scope` means the
95
+ token is missing a scope; `feature_disabled` means the account
92
96
  `local-execute` flag is off. Never read MCP OAuth tokens from the host.
93
97
 
94
98
  ```bash
99
+ # Agents on MCP:
100
+ # cliCredentialBootstrap → { bootstrap_code, cli_command }
101
+ npx @kodycodes/cli auth bootstrap --code 'kody_bc_…'
102
+ npx @kodycodes/cli execute --local --file ./task.js --params '{"q":"email"}'
103
+
95
104
  npx @kodycodes/cli login
96
105
  npx @kodycodes/cli execute --local --file ./task.js --params '{"q":"email"}'
97
- # Or with an explicit scoped token (wins over login):
106
+ # Or with an explicit scoped token (wins over login / bootstrap store):
98
107
  KODY_API_TOKEN=… npx @kodycodes/cli execute --local --file ./task.js --params '{"q":"email"}'
99
108
  ```