@gajae-code/coding-agent 0.15.2 → 0.15.4

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 (107) hide show
  1. package/CHANGELOG.md +43 -1
  2. package/dist/types/config/autorouting-tier-map.d.ts +0 -9
  3. package/dist/types/config/file-lock.d.ts +7 -1
  4. package/dist/types/config/keybindings.d.ts +13 -3
  5. package/dist/types/config/model-registry.d.ts +5 -0
  6. package/dist/types/config/model-resolver.d.ts +1 -0
  7. package/dist/types/config/settings-schema.d.ts +65 -1
  8. package/dist/types/coordinator/contract.d.ts +1 -1
  9. package/dist/types/coordinator-mcp/question-state.d.ts +42 -2
  10. package/dist/types/extensibility/extensions/types.d.ts +2 -0
  11. package/dist/types/gjc-runtime/deep-interview-state.d.ts +12 -0
  12. package/dist/types/gjc-runtime/workflow-placeholder.d.ts +6 -0
  13. package/dist/types/main.d.ts +1 -1
  14. package/dist/types/modes/action-registry.d.ts +1 -0
  15. package/dist/types/modes/components/hook-selector.d.ts +1 -0
  16. package/dist/types/modes/components/runtime-mcp-add-wizard.d.ts +1 -1
  17. package/dist/types/modes/components/welcome.d.ts +2 -0
  18. package/dist/types/modes/controllers/input-controller.d.ts +16 -1
  19. package/dist/types/modes/controllers/runtime-mcp-command-controller.d.ts +42 -0
  20. package/dist/types/modes/interactive-mode.d.ts +7 -0
  21. package/dist/types/modes/shared/oauth-url-copy.d.ts +9 -0
  22. package/dist/types/modes/types.d.ts +3 -0
  23. package/dist/types/modes/ui-language.d.ts +2 -1
  24. package/dist/types/sdk/broker/lifecycle-ledger.d.ts +1 -0
  25. package/dist/types/sdk/broker/session-index.d.ts +18 -0
  26. package/dist/types/sdk/bus/index.d.ts +4 -1
  27. package/dist/types/sdk/bus/telegram-daemon-contract.d.ts +4 -1
  28. package/dist/types/sdk/bus/telegram-daemon.d.ts +2 -0
  29. package/dist/types/sdk/cli/session-cli.d.ts +1 -1
  30. package/dist/types/sdk/lifecycle/service.d.ts +32 -5
  31. package/dist/types/sdk/session.d.ts +5 -0
  32. package/dist/types/session/agent-session.d.ts +4 -0
  33. package/dist/types/session/fallback-chain-controller.d.ts +8 -0
  34. package/dist/types/slash-commands/helpers/aside.d.ts +54 -0
  35. package/dist/types/tools/ask.d.ts +9 -0
  36. package/dist/types/utils/clipboard.d.ts +9 -1
  37. package/package.json +7 -7
  38. package/scripts/generate-sdk-adapter-parity-manifest.ts +5 -2
  39. package/scripts/generate-sdk-operation-inventory.ts +3 -0
  40. package/src/commands/sdk.ts +2 -2
  41. package/src/config/autorouting-tier-map.ts +0 -9
  42. package/src/config/file-lock.ts +15 -1
  43. package/src/config/keybindings.ts +13 -3
  44. package/src/config/model-registry.ts +132 -21
  45. package/src/config/model-resolver.ts +2 -1
  46. package/src/config/models-config-schema.ts +2 -2
  47. package/src/config/settings-schema.ts +66 -1
  48. package/src/config/settings.ts +1 -1
  49. package/src/coordinator/contract.ts +1 -0
  50. package/src/coordinator-mcp/question-state.ts +235 -4
  51. package/src/coordinator-mcp/server.ts +402 -2
  52. package/src/dap/client.ts +19 -8
  53. package/src/deep-interview/render-middleware.ts +6 -2
  54. package/src/extensibility/extensions/types.ts +2 -0
  55. package/src/gjc-runtime/deep-interview-stage.ts +20 -1
  56. package/src/gjc-runtime/deep-interview-state.ts +3 -1
  57. package/src/gjc-runtime/ralplan-runtime.ts +6 -1
  58. package/src/gjc-runtime/session-state-lock.ts +11 -2
  59. package/src/gjc-runtime/ultragoal-runtime.ts +5 -0
  60. package/src/gjc-runtime/workflow-placeholder.ts +33 -0
  61. package/src/internal-urls/docs-index.generated.ts +11 -9
  62. package/src/lsp/client.ts +39 -4
  63. package/src/main.ts +42 -11
  64. package/src/modes/action-registry.ts +7 -0
  65. package/src/modes/components/hook-selector.ts +2 -1
  66. package/src/modes/components/iterm-pet-transport.ts +4 -2
  67. package/src/modes/components/runtime-mcp-add-wizard.ts +38 -1
  68. package/src/modes/components/settings-selector.ts +1 -0
  69. package/src/modes/components/tool-status-header.ts +149 -41
  70. package/src/modes/components/welcome.ts +8 -0
  71. package/src/modes/controllers/extension-ui-controller.ts +1 -0
  72. package/src/modes/controllers/goal-mode-controller.ts +7 -2
  73. package/src/modes/controllers/input-controller.ts +141 -7
  74. package/src/modes/controllers/plan-mode-controller.ts +12 -4
  75. package/src/modes/controllers/runtime-mcp-command-controller.ts +164 -20
  76. package/src/modes/controllers/selector-controller.ts +11 -2
  77. package/src/modes/interactive-mode.ts +88 -1
  78. package/src/modes/shared/oauth-url-copy.ts +33 -0
  79. package/src/modes/types.ts +3 -0
  80. package/src/modes/ui-language.ts +44 -3
  81. package/src/runtime-mcp/oauth-flow.ts +19 -8
  82. package/src/runtime-mcp/transports/stdio.ts +27 -13
  83. package/src/sdk/acp/adapter.ts +29 -2
  84. package/src/sdk/broker/broker.ts +26 -6
  85. package/src/sdk/broker/lifecycle-ledger.ts +28 -1
  86. package/src/sdk/broker/lifecycle.ts +664 -5
  87. package/src/sdk/broker/session-index.ts +246 -0
  88. package/src/sdk/broker/transport.ts +1 -0
  89. package/src/sdk/bus/index.ts +135 -38
  90. package/src/sdk/bus/natives-augment.d.ts +20 -1
  91. package/src/sdk/bus/telegram-daemon-contract.ts +4 -1
  92. package/src/sdk/bus/telegram-daemon.ts +3 -0
  93. package/src/sdk/cli/session-cli.ts +34 -7
  94. package/src/sdk/lifecycle/service.ts +166 -11
  95. package/src/sdk/mcp/server.ts +2 -1
  96. package/src/sdk/protocol/operation-inventory.generated.json +40 -0
  97. package/src/sdk/protocol/operation-registry.ts +2 -1
  98. package/src/sdk/session.ts +91 -7
  99. package/src/session/agent-session.ts +473 -66
  100. package/src/session/fallback-chain-controller.ts +17 -0
  101. package/src/setup/frictionless-onboarding.ts +4 -4
  102. package/src/slash-commands/aside-command.test.ts +366 -0
  103. package/src/slash-commands/builtin-registry.ts +19 -0
  104. package/src/slash-commands/helpers/aside.ts +299 -0
  105. package/src/tools/ask-contract.ts +54 -3
  106. package/src/tools/ask.ts +54 -6
  107. package/src/utils/clipboard.ts +37 -28
package/CHANGELOG.md CHANGED
@@ -2,6 +2,46 @@
2
2
 
3
3
  ## [Unreleased]
4
4
 
5
+ ## [0.15.4] - 2026-08-29
6
+
7
+ - The `ask` tool now rejects empty or whitespace-only custom answers on every local and remote input path. Remote invalid answers receive a visible explanation and are retried at most three times with an event-loop yield between attempts before the ask is cancelled; local empty custom input is never returned as a valid answer. (#5001)
8
+
9
+ ## [0.15.3] - 2026-08-27
10
+
11
+ ### Added
12
+
13
+ - Added opt-in `compaction.adaptive.*` settings and wired them into post-turn and pre-prompt auto-compaction. Adaptive mode remains disabled by default, preserves fixed-token precedence, and exposes bounded base, aggression, call-window, and minimum-threshold controls.
14
+
15
+ - The `ask` tool declares its display-only argument fields (`questions.question`, `questions.options.label`) via `displaySafeEscapedArgFields`, so an `ask` call whose question text or option labels arrive as `\uXXXX` escapes (common from Anthropic models writing Korean or emoji) completes with a single warning instead of discarding the turn, charging the managed-fallback retry budget, and ultimately failing the run. Ids, workflow-gate metadata, and deep-interview records remain load-bearing and keep the fail-closed rejection. (#4983)
16
+
17
+ - Added an explicit `Copy OAuth URL` command-palette action for interactive `/login` and runtime MCP OAuth flows. It copies the exact pending authorization URL through the configured clipboard transport only after the user selects the action; it never overwrites the clipboard automatically and clears the pending URL when the flow ends. This preserves OSC 8 policy, tmux/SSH/no-hyperlink behavior, and avoids relying on padded soft-wrapped terminal rows for copying.
18
+ - Six navigation actions are now reachable from the command palette and dispatch a user remap: `app.session.dashboard`, `app.transcript.browse`, `app.transcript.prevTurn`, `app.transcript.nextTurn`, `app.queue.togglePane`, and `app.message.sendNow`. All six already carried a registry callback and an availability predicate but shipped with no curated palette entry and no key dispatch, so four were unreachable from every surface and two only through `/transcript` and `/sessions`. Each entry is listed through an opt-in availability gate, so an action whose predicate is false (send-now while idle, transcript turns with no anchored user messages, transcript browsing with an empty session) is not offered rather than being offered and refused on selection. Pre-existing curated palette entries keep their previous listing semantics: the gate is a sibling opt-in set, not a blanket filter, so entries such as thinking-cycle, model-cycle, external editor, and the session tree/fork actions are unaffected. Default chords stay empty; the new `setCustomKeyHandler` loops are inert until a user binds one of these ids, which previously would have been displayed by the palette without ever dispatching.
19
+ - The todo HUD can now be expanded. `app.todo.toggle` (`alt+shift+t`, remappable via `~/.gjc/agent/keybindings.json`) and a command-palette entry both reach `toggleTodoExpansion()`, which previously had no caller anywhere in the source: the HUD rendered a `+N more` row summarising hidden tasks with no way to reveal them. The action is unavailable while no phase has tasks, so the chord stays inert and the palette entry is not listed rather than being offered and refused.
20
+ - The session tree, branch-from-message, and resume actions now ship default chords: `alt+shift+s` (`app.session.tree`), `alt+shift+f` (`app.session.fork`), and `alt+shift+r` (`app.session.resume`). All three already had key-dispatch loops and curated palette entries; the loops were simply empty because the actions carried no default keys, so the bindings were reachable only through the palette. All three remain remappable via `~/.gjc/agent/keybindings.json`, and user bindings continue to win over defaults. Tree and branch stay unavailable on an empty session, so their chords are inert instead of opening an empty selector.
21
+ - New `startup.skipLogoAnimation` setting (Interaction tab, default off) skips the animated startup logo sweep. The welcome surface, its resting logo, and every information row (recent sessions, LSP state, flow keys) still render — unlike `startup.quiet`, which suppresses the whole surface. Previously the roughly three-second gradient sweep drove about 91 forced renders on every interactive start with no way to opt out short of losing the entire welcome screen. The value is read once during interactive startup, so changing it takes effect at the next start. Pet and loader motion are deliberately out of scope and unaffected.
22
+ - Added Japanese (`ja`) to the persisted `ui.language` response-language surface: the `/language` command and the Settings → Appearance selector. Accepted input spellings include `ja`, `ja-JP`, `japanese`, `jp`, `jpn`, and `日本語`. English and Korean behavior, defaults, and onboarding language ranking are unchanged. (#4947)
23
+ - Added `/aside`, a composer slash command that probes a user-installed Aside CLI (`~/.local/bin/aside`, the macOS `Aside CLI.app` bundle, then `PATH`) and runs explicit `exec` / `account` invocations from GJC. Bare `/aside` prints the resolved path and version; `/aside mcp` prints `gjc mcp add aside <cli> mcp --project` with a quoted concrete binary instead of starting a stdio server; `/aside repl` stays terminal-only because the GJC host cannot attach a TTY. Missing-binary output includes the official install command. This does not restore the reverted Aside browser-tool backend and does not enable browser-control by default.
24
+ - Added the semantic `gjc sdk session retire <sessionId>` wrapper for the identity-bound `session.reconcile_uncertain` lifecycle global. It fails closed on live, ambiguous, malformed, or endpoint-bearing state and retires stranded coordinator start intents through `gjc_coordinator_retire_start_session`.
25
+ - `gjc sdk session raw global --op session.reconcile_uncertain` retires an indexed `terminalUncertain` create effect after dead-host, absent-endpoint, and identity-bound leftover proof, appending `session_closed` and a ledger `terminal_error` successor. It does not weaken `session.close` / `session.delete`. The official `gjc_coordinator_retire_start_session` mutation seals a matching coordinator start-session `in_progress` projection only after the same broker proof (issue #4950).
26
+
27
+ ### Changed
28
+
29
+ - The pinned status rail now cues dropped segments instead of discarding them silently. When telemetry does not fit, the rail appends a width-reserved marker — `…+N` with the exact count of omitted segments when the count fits, degrading to a bare `…` when it cannot — in both loss paths: the single-row path that shrinks the path then pops right-side and left-side segments, and the multi-row path that stops at the `statusLine.maxRows` cutoff. Eviction order and semantics are deliberately unchanged: which segments survive is still decided by configured segment order, and no cross-segment priority policy is introduced. The marker reserves its cells inside the layout calculation and renders through a dedicated compact path with no padding or end caps, so it can occupy a single column and the final width truncation stays a defensive guard rather than deciding whether the cue survives. The count is never truncated into a wrong number: it is either exact or intentionally absent. Note that the rail was already dropping a segment at 48 columns for a two-segment preset; that loss is now visible.
30
+
31
+ ### Fixed
32
+
33
+ - `--no-tools` now disables every built-in tool. The flag is documented as "Disable all built-in tools" and maps to an empty explicit tool selection, but the session builder unconditionally folded `goal` back into any explicit selection whenever `goal.enabled` was on (its default), so a `--no-tools` run still exposed exactly one built-in tool against that promise. `goal` is still folded into a non-empty explicit selection such as `--tools read,bash`, where it carries session state rather than competing with the requested work tools, and sessions with no explicit selection are unaffected.
34
+ - The coordinator session-state lock now works on Windows. Two production defects and two POSIX-only fixtures were exposed once the suite reached a windows-latest shard (#4990): `processStartTime()` probed only through `ps`, which does not exist on Windows, so every owner start time was `null` and PID-reuse verdicts degraded to indeterminate; it now reads the natives addon's kernel-derived `Process.incarnation` on win32, the same evidence the SDK broker uses, and still returns `null` fail-closed when the incarnation cannot be proved. Separately, `createOwnerLock`'s failed-write retraction ran the identity-bound delete while the create descriptor was still open, which Windows refuses (the descriptor grants no share-delete), leaving a half-written owner record stranded at the lock path; the Windows strategy now closes the descriptor after it has vouched for the created object and lets the compare-and-delete re-prove the full recorded identity (dev/ino, link count, size, mtime, payload hash) at delete time, so a successor that took the pathname in the window is still refused. Fail-closed identity and successor semantics are unchanged. The two FIFO fixtures (created with `mkfifo`, whose EOF helper also needs `sh`) are now gated POSIX-only — the descriptor-proved-regular contract stays covered on Windows by the symlink variants — the suite gained cross-platform coverage for the portable start probe and the retract-under-open-handle ordering, and the suite plus its routing predicates now execute on the windows-latest dev-CI job.
35
+ - `gjc deep-interview write`/`stage` now report all envelope-reserved keys nested under `state` in `ignored_runtime_owned_keys`, including `source_state_revision` and `last_applied_draft_id`. A payload such as `{"state":{"current_phase":"cancelled"}}` returned an unqualified `ok:true` while the key was discarded before it reached disk, so a caller asking for a phase transition got a success receipt for an instruction that never took effect. The same key sent at the top level was already reported, and `gjc state deep-interview write` rejects it outright. Which keys are discarded, the persisted envelope, and every existing error are unchanged; only the response now names the discard.
36
+ - Idle notifications are now bound to the exact SDK connection generations that accepted their positioned identity prerequisite; raw-only recipients receive identity and idle through the same bounded writer command. Late joins, replaced generations, and saturated writers therefore cannot receive a dependent Telegram idle through an unrelated global broadcast.
37
+ - Interactive input now releases the foreground submission loop at the terminal `agent_end` boundary even when forced recovery leaves the provider-facing prompt unresolved. This lets the main loop reinstall its input callback for exactly one follow-up submission without bypassing pending-submission or goal-mode ownership, completing the terminal-boundary fix in #4741. (#4970)
38
+ - Managed escaped non-ASCII tool-call recovery now carries the literal-UTF-8 steering instruction on every bounded retry, charges and advances the fallback chain once after a model exhausts those retries, and fails closed only after every eligible fallback model has exhausted its own bounded recovery. Escaped arguments remain unexecuted and excluded from durable history.
39
+ - When OSC 8 hyperlinks are enabled, the `/login` URL row is now an anchor pointing at itself, so a login URL wider than the pane stays clickable on every wrapped fragment. A login URL is one unbreakable token, so a pane narrower than the URL splits it across rows; the row printed the bare URL, so the wrap layer had no link to carry (#4711) and every fragment rendered as dead text. Bare URLs in Markdown prose already got this treatment; the login row did not. The existing hyperlink policy still disables OSC 8 where the terminal or user settings do not support it.
40
+ - Coordinator uncertain-retirement retries now replay a completed retired start intent when a crash occurs after broker proof is sealed but before the retirement idempotency record is finalized; lifecycle retirement also revalidates the exact `sdk` parent identity before index closure, preventing a replacement directory from inheriting stale cleanup authority (#4950).
41
+ - Foreground activity animation now uses layout-only TUI repaints, avoiding repeated reconstruction of unchanged transcript content during long sessions.
42
+ - Notification adapters can now opt into one live representation per native effect: adapters that accept a positioned event are excluded from its matching raw fan-out, while ordinary direct SDK and raw-only legacy subscribers retain their existing delivery. Telegram opts in, preventing turn output, tool activity, and reasoning summaries from rendering twice after #4570; acknowledged terminal shutdown delivery is unchanged.
43
+ - Lean notifications no longer replay a retained completion receipt at idle when identical text was already delivered immediately before an autonomous `ask`; distinct receipts and other settlement windows remain preserved.
44
+
5
45
  ## [0.15.2] - 2026-08-25
6
46
 
7
47
  ### Changed
@@ -26,7 +66,9 @@
26
66
 
27
67
  ### Fixed
28
68
 
29
- - Onboarding language detection (`/tutorial`, first-run onboarding) no longer misreads English or Korean transcripts as French, Spanish, or German. Word evidence for space-delimited languages is matched on token boundaries instead of substrings — `le`/`la`/`el` used to match inside `file`, `please`, `class`, and `help`, so plain English handed French a majority — Korean, Japanese, and Chinese are identified by script instead of particle substrings, script counts and word hits share one ranking so two Hangul or Han characters cannot override a clearly English transcript, a claimant script needs two characters before it may claim mixed han text so one stray Hangul or kana glyph cannot erase dominant han evidence, a language must lead the runner-up outright to beat the OS locale, and an explicit `ui.language` selection outranks both. `/language` also accepts locale tags such as `en-US` / `ko-KR` and now rejects hostile inputs that used to resolve to inherited object properties (`__proto__`, `constructor`) instead of canonical `en`/`ko`.
69
+ - Onboarding language detection (`/tutorial`, first-run onboarding) no longer misreads English or Korean transcripts as French, Spanish, or German. Word evidence for space-delimited languages is matched on token boundaries instead of substrings — `le`/`la`/`el` used to match inside `file`, `please`, `class`, and `help`, so plain English handed French a majority — Korean, Japanese, and Chinese are identified by script instead of particle substrings, script counts and word hits share one ranking so two Hangul or Han characters cannot override a clearly English transcript, a Hangul claimant needs two characters before it may claim mixed han text so one stray Hangul glyph cannot erase dominant han evidence, a language must lead the runner-up outright to beat the OS locale, and an explicit `ui.language` selection outranks both. `/language` also accepts locale tags such as `en-US` / `ko-KR` and now rejects hostile inputs that used to resolve to inherited object properties (`__proto__`, `constructor`) instead of canonical `en`/`ko`.
70
+ - Fresh SDK and print sessions now admit a matching credential- and endpoint-scoped discovered-model cache before validating an explicit provider/model, avoiding a startup provider request; caller-supplied registries, foreign credentials, and unknown models remain fail-closed.
71
+ - Fresh SDK and print sessions now admit a matching credential- and endpoint-scoped discovered-model cache before validating an explicit provider/model, and revalidate pre-existing dynamic targets against the selected row; caller-supplied registries stay immutable while foreign credentials and unknown models remain fail-closed.
30
72
  - `ask` question wording and option labels no longer use the post-resample U+2014 display-text exemption because accepted calls enter durable session history and deep-interview rounds; genuinely display-only tool fields retain the existing exemption (#4926).
31
73
  - Gajae Pet now treats forwarded `LC_TERMINAL=iTerm2` and `TERM_PROGRAM=iTerm.app` values as probe hints over SSH, enabling iTerm2 only after an active OSC 1337 File-capability reply. Generic SSH, spoofed/noninteractive/CI environments, and unmanaged tmux/screen/zellij nesting remain on the text fallback; verified Kitty and Sixel keep precedence. (#4911)
32
74
  - Interactive terminal completion now publishes the local `agent_end` boundary before waiting for the ordered coordinator sidecar write, so slow or lock-hostile WSL drvfs mounts cannot leave the foreground activity indicator and composer busy after a turn has completed. Coordinator persistence ordering and extension delivery remain unchanged. (#4741)
@@ -259,15 +259,6 @@ export declare const TIER_MAP_SKIP_LIST: {
259
259
  readonly "cursor/gemini-3.7-flash-medium": {
260
260
  readonly rationale: "post-rebase catalog addition from dev; not yet curated";
261
261
  };
262
- readonly "google-antigravity/gemini-3.7-flash-high": {
263
- readonly rationale: "post-rebase catalog addition from dev; not yet curated";
264
- };
265
- readonly "google-antigravity/gemini-3.7-flash-low": {
266
- readonly rationale: "post-rebase catalog addition from dev; not yet curated";
267
- };
268
- readonly "google-antigravity/gemini-3.7-flash-medium": {
269
- readonly rationale: "post-rebase catalog addition from dev; not yet curated";
270
- };
271
262
  readonly "google-antigravity/gemini-3.7-flash-tiered": {
272
263
  readonly rationale: "post-rebase catalog addition from dev; not yet curated";
273
264
  };
@@ -15,7 +15,13 @@ export declare const FileLockTestHooks: {
15
15
  /**
16
16
  * Returns the OS-provided process start timestamp for PID-reuse detection.
17
17
  * `ps` is available on the supported Unix hosts (macOS and Linux), unlike
18
- * Linux's `/proc/<pid>/stat` pseudo-file.
18
+ * Linux's `/proc/<pid>/stat` pseudo-file. Windows has no `ps`; there the
19
+ * kernel-derived process creation time exposed by the natives addon
20
+ * (`Process.incarnation`, the same identity evidence the SDK broker prefers)
21
+ * is used instead. Either way the value is only ever compared for equality
22
+ * against a value this same function produced on the same platform, and `null`
23
+ * stays fail-closed: an owner whose incarnation cannot be proved is never
24
+ * treated as reused.
19
25
  */
20
26
  export declare function processStartTime(pid: number): string | null;
21
27
  /** @internal */
@@ -25,6 +25,7 @@ interface AppKeybindings {
25
25
  "app.clipboard.pasteText": true;
26
26
  "app.clipboard.copyLine": true;
27
27
  "app.clipboard.copyPrompt": true;
28
+ "app.clipboard.copyOAuthUrl": true;
28
29
  "app.session.new": true;
29
30
  "app.session.tree": true;
30
31
  "app.session.fork": true;
@@ -48,6 +49,7 @@ interface AppKeybindings {
48
49
  "app.transcript.nextTurn": true;
49
50
  "app.mode.cycle": true;
50
51
  "app.tasks.toggle": true;
52
+ "app.todo.toggle": true;
51
53
  "app.queue.togglePane": true;
52
54
  "app.message.sendNow": true;
53
55
  }
@@ -274,20 +276,24 @@ export declare const KEYBINDINGS: {
274
276
  readonly defaultKeys: "alt+shift+c";
275
277
  readonly description: "Copy prompt";
276
278
  };
279
+ readonly "app.clipboard.copyOAuthUrl": {
280
+ readonly defaultKeys: "alt+shift+u";
281
+ readonly description: "Copy OAuth URL";
282
+ };
277
283
  readonly "app.session.new": {
278
284
  readonly defaultKeys: "ctrl+n";
279
285
  readonly description: "Start a new session";
280
286
  };
281
287
  readonly "app.session.tree": {
282
- readonly defaultKeys: [];
288
+ readonly defaultKeys: "alt+shift+s";
283
289
  readonly description: "Show session tree";
284
290
  };
285
291
  readonly "app.session.fork": {
286
- readonly defaultKeys: [];
292
+ readonly defaultKeys: "alt+shift+f";
287
293
  readonly description: "Branch from message";
288
294
  };
289
295
  readonly "app.session.resume": {
290
- readonly defaultKeys: [];
296
+ readonly defaultKeys: "alt+shift+r";
291
297
  readonly description: "Resume session";
292
298
  };
293
299
  readonly "app.session.observe": {
@@ -366,6 +372,10 @@ export declare const KEYBINDINGS: {
366
372
  readonly defaultKeys: "alt+t";
367
373
  readonly description: "Toggle tasks pane";
368
374
  };
375
+ readonly "app.todo.toggle": {
376
+ readonly defaultKeys: "alt+shift+t";
377
+ readonly description: "Toggle todo list expansion";
378
+ };
369
379
  readonly "app.queue.togglePane": {
370
380
  readonly defaultKeys: [];
371
381
  readonly description: "Toggle message queue pane";
@@ -359,6 +359,11 @@ export declare class ModelRegistry {
359
359
  refresh(strategy?: ModelRefreshStrategy): Promise<void>;
360
360
  refreshInBackground(strategy?: ModelRefreshStrategy): void;
361
361
  refreshProvider(providerId: string, strategy?: ModelRefreshStrategy): Promise<void>;
362
+ admitCachedProviderForStoredLiteralCredential(providerId: string, selector: AuthCredentialSelector): boolean;
363
+ /** @internal Validate an existing startup model without mutating a caller-supplied registry. */
364
+ validateModelForStoredLiteralCredential(providerId: string, modelId: string, selector: AuthCredentialSelector): boolean;
365
+ /** @internal Whether startup must establish credential-scoped cache provenance for this exact target. */
366
+ requiresStoredLiteralCredentialCacheAdmission(providerId: string, modelId: string): boolean;
362
367
  /**
363
368
  * Get any error from loading models.json (undefined if no error).
364
369
  */
@@ -152,6 +152,7 @@ export interface ModelChainResolutionOptions {
152
152
  aliasIntent?: "preset-equivalent" | "reject";
153
153
  canonicalSessionId?: string | null;
154
154
  credentialSessionId?: string;
155
+ signal?: AbortSignal;
155
156
  }
156
157
  export declare function resolveModelChainWithAuth(modelPatterns: readonly string[], modelRegistry: ModelLookupRegistry & Pick<ModelRegistry, "getApiKey">, settings?: Settings, sessionId?: string, options?: ModelChainResolutionOptions): Promise<{
157
158
  model?: Model<Api>;
@@ -604,7 +604,7 @@ export declare const SETTINGS_SCHEMA: {
604
604
  };
605
605
  readonly "ui.language": {
606
606
  readonly type: "enum";
607
- readonly values: readonly ["en", "ko"];
607
+ readonly values: readonly ["en", "ko", "ja"];
608
608
  readonly default: "en";
609
609
  readonly ui: {
610
610
  readonly tab: "appearance";
@@ -616,6 +616,9 @@ export declare const SETTINGS_SCHEMA: {
616
616
  }, {
617
617
  readonly value: "ko";
618
618
  readonly label: "Korean (한국어)";
619
+ }, {
620
+ readonly value: "ja";
621
+ readonly label: "Japanese (日本語)";
619
622
  }];
620
623
  };
621
624
  };
@@ -1848,6 +1851,15 @@ export declare const SETTINGS_SCHEMA: {
1848
1851
  }];
1849
1852
  };
1850
1853
  };
1854
+ readonly "startup.skipLogoAnimation": {
1855
+ readonly type: "boolean";
1856
+ readonly default: false;
1857
+ readonly ui: {
1858
+ readonly tab: "interaction";
1859
+ readonly label: "Skip Startup Logo Animation";
1860
+ readonly description: "Skip the animated startup logo sweep; the welcome surface, its resting logo, and all information rows still render. Applies at the next interactive start.";
1861
+ };
1862
+ };
1851
1863
  readonly "startup.checkUpdate": {
1852
1864
  readonly type: "boolean";
1853
1865
  readonly default: true;
@@ -2181,6 +2193,51 @@ export declare const SETTINGS_SCHEMA: {
2181
2193
  }];
2182
2194
  };
2183
2195
  };
2196
+ readonly "compaction.adaptive.enabled": {
2197
+ readonly type: "boolean";
2198
+ readonly default: false;
2199
+ readonly ui: {
2200
+ readonly tab: "context";
2201
+ readonly label: "Adaptive Compaction";
2202
+ readonly description: "Adjust compaction frequency by context size and call rate";
2203
+ };
2204
+ };
2205
+ readonly "compaction.adaptive.baseThresholdPercent": {
2206
+ readonly type: "number";
2207
+ readonly default: 85;
2208
+ readonly ui: {
2209
+ readonly tab: "context";
2210
+ readonly label: "Adaptive Base Threshold %";
2211
+ readonly description: "Base context percentage used when adaptive compaction is enabled";
2212
+ };
2213
+ };
2214
+ readonly "compaction.adaptive.aggression": {
2215
+ readonly type: "number";
2216
+ readonly default: 0.15;
2217
+ readonly ui: {
2218
+ readonly tab: "context";
2219
+ readonly label: "Adaptive Aggression";
2220
+ readonly description: "How strongly call rate lowers the compaction threshold; use 0 to 1";
2221
+ };
2222
+ };
2223
+ readonly "compaction.adaptive.turnWindow": {
2224
+ readonly type: "number";
2225
+ readonly default: 15;
2226
+ readonly ui: {
2227
+ readonly tab: "context";
2228
+ readonly label: "Call-Rate Window";
2229
+ readonly description: "Minutes of recent calls considered by adaptive compaction";
2230
+ };
2231
+ };
2232
+ readonly "compaction.adaptive.minThresholdPercent": {
2233
+ readonly type: "number";
2234
+ readonly default: 50;
2235
+ readonly ui: {
2236
+ readonly tab: "context";
2237
+ readonly label: "Adaptive Floor %";
2238
+ readonly description: "Lowest context percentage adaptive compaction may lower the threshold to";
2239
+ };
2240
+ };
2184
2241
  readonly "compaction.handoffSaveToDisk": {
2185
2242
  readonly type: "boolean";
2186
2243
  readonly default: false;
@@ -4509,6 +4566,13 @@ export interface CompactionSettings {
4509
4566
  strategy: "context-full" | "handoff" | "off";
4510
4567
  thresholdPercent: number;
4511
4568
  thresholdTokens: number;
4569
+ adaptive: {
4570
+ enabled: boolean;
4571
+ baseThresholdPercent: number;
4572
+ aggression: number;
4573
+ turnWindow: number;
4574
+ minThresholdPercent: number;
4575
+ };
4512
4576
  reserveTokens: number;
4513
4577
  keepRecentTokens: number;
4514
4578
  handoffSaveToDisk: boolean;
@@ -1,4 +1,4 @@
1
1
  export declare const COORDINATOR_MCP_PROTOCOL_VERSION = "2024-11-05";
2
2
  export declare const COORDINATOR_MCP_SERVER_NAME = "gjc-coordinator-mcp";
3
- export declare const COORDINATOR_MCP_TOOL_NAMES: readonly ["gjc_coordinator_list_sessions", "gjc_coordinator_read_status", "gjc_coordinator_read_tail", "gjc_coordinator_list_questions", "gjc_coordinator_list_artifacts", "gjc_coordinator_read_artifact", "gjc_coordinator_read_coordination_status", "gjc_coordinator_watch_events", "gjc_coordinator_register_session", "gjc_coordinator_start_session", "gjc_coordinator_activate_session", "gjc_coordinator_stop_session", "gjc_coordinator_send_prompt", "gjc_coordinator_submit_question_answer", "gjc_coordinator_read_turn", "gjc_coordinator_await_turn", "gjc_coordinator_report_status", "gjc_coordinator_register_codex_handoff", "gjc_coordinator_read_codex_handoff", "gjc_coordinator_ack_codex_handoff", "gjc_delegate_plan", "gjc_delegate_execute"];
3
+ export declare const COORDINATOR_MCP_TOOL_NAMES: readonly ["gjc_coordinator_list_sessions", "gjc_coordinator_read_status", "gjc_coordinator_read_tail", "gjc_coordinator_list_questions", "gjc_coordinator_list_artifacts", "gjc_coordinator_read_artifact", "gjc_coordinator_read_coordination_status", "gjc_coordinator_watch_events", "gjc_coordinator_register_session", "gjc_coordinator_start_session", "gjc_coordinator_retire_start_session", "gjc_coordinator_activate_session", "gjc_coordinator_stop_session", "gjc_coordinator_send_prompt", "gjc_coordinator_submit_question_answer", "gjc_coordinator_read_turn", "gjc_coordinator_await_turn", "gjc_coordinator_report_status", "gjc_coordinator_register_codex_handoff", "gjc_coordinator_read_codex_handoff", "gjc_coordinator_ack_codex_handoff", "gjc_delegate_plan", "gjc_delegate_execute"];
4
4
  export type CoordinatorToolName = (typeof COORDINATOR_MCP_TOOL_NAMES)[number];
@@ -308,7 +308,7 @@ export interface CreationRequestV1 {
308
308
  key_digest: string;
309
309
  request_digest: string;
310
310
  tool: string;
311
- phase: "claimed" | "remote_started" | "wal_committed" | "projected" | "completed" | "uncertain";
311
+ phase: "claimed" | "remote_started" | "wal_committed" | "projected" | "completed" | "uncertain" | "retired";
312
312
  canonical_create_intent: CanonicalCreateIntentV1 | null;
313
313
  remote_create_key: string;
314
314
  session_id: string | null;
@@ -317,12 +317,45 @@ export interface CreationRequestV1 {
317
317
  key_id: string;
318
318
  public_key: string;
319
319
  } | null;
320
+ /** Retirement is staged before the broker effect so a post-effect crash can replay safely. */
321
+ retirement_intent?: CreationRetirementIntentV1;
320
322
  wal_revision?: number;
321
323
  wal_digest?: string;
322
324
  safe_response?: Record<string, unknown>;
323
325
  created_at: string;
324
326
  updated_at: string;
325
327
  }
328
+ export interface CreationRetirementProofV1 {
329
+ session_id: string;
330
+ cwd: string;
331
+ state_root: string;
332
+ endpoint_generation: number;
333
+ endpoint_mtime_ms: number;
334
+ process_incarnation: string;
335
+ host_incarnation: string;
336
+ lifecycle_request_id: string;
337
+ remote_create_key: string;
338
+ }
339
+ export interface CreationRetirementBrokerProofV1 {
340
+ session_id: string;
341
+ retired: true;
342
+ ledger_state: "terminal_error";
343
+ index_type: "session_closed";
344
+ state_root: string;
345
+ endpoint_generation: number;
346
+ endpoint_mtime_ms: number;
347
+ process_incarnation: string;
348
+ host_incarnation: string;
349
+ lifecycle_request_id: string;
350
+ remote_create_key: string;
351
+ }
352
+ export interface CreationRetirementIntentV1 {
353
+ phase: "intent" | "pre_effect_rejected" | "broker_retired";
354
+ proof: CreationRetirementProofV1;
355
+ retirement_key_digest?: string;
356
+ broker_proof?: CreationRetirementBrokerProofV1;
357
+ updated_at: string;
358
+ }
326
359
  export interface NamespaceDeletionEntryV1 {
327
360
  deletion_id: string;
328
361
  session_id: string;
@@ -528,8 +561,15 @@ export declare function compactTransaction(transaction: CoordinatorSessionTransa
528
561
  export declare function repairProjections(paths: CoordinatorStatePaths, sessionId: string, project: (canonical: CoordinatorSessionTransactionV1["canonical"]) => Promise<void>, options?: {
529
562
  signal?: AbortSignal;
530
563
  }): Promise<void>;
564
+ /** Claims retirement under the creation receipt before any broker effect. */
565
+ export declare function recordCreationRetirementIntent(paths: CoordinatorStatePaths, keyDigest: string, proof: CreationRetirementProofV1, retirementKeyDigest?: string): Promise<CreationRequestV1>;
566
+ /** Replaces only a pre-effect retirement proof after an explicit broker rejection. */
567
+ export declare function replaceCreationRetirementIntent(paths: CoordinatorStatePaths, keyDigest: string, proof: CreationRetirementProofV1, retirementKeyDigest: string): Promise<CreationRequestV1>;
568
+ /** Records the bounded broker proof before receipt advancement or idempotency sealing. */
569
+ export declare function recordCreationRetirementBrokerProof(paths: CoordinatorStatePaths, keyDigest: string, proof: CreationRetirementProofV1, brokerProof: CreationRetirementBrokerProofV1): Promise<CreationRequestV1>;
531
570
  /** Advances a creation receipt only after its WAL or projection authority exists. */
532
- export declare function advanceCreationReceipt(paths: CoordinatorStatePaths, keyDigest: string, phase: "projected" | "completed" | "uncertain", safeResponse?: Record<string, unknown>): Promise<void>;
571
+ export declare function assertCreationRetirementIdentity(paths: CoordinatorStatePaths, keyDigest: string, proof: CreationRetirementProofV1): Promise<CreationRequestV1>;
572
+ export declare function advanceCreationReceipt(paths: CoordinatorStatePaths, keyDigest: string, phase: "projected" | "completed" | "uncertain" | "retired", safeResponse?: Record<string, unknown>, proof?: CreationRetirementProofV1): Promise<void>;
533
573
  export declare function hasEmergencyCapacity(transaction: CoordinatorSessionTransactionV1, incomingBytes: number, essential: boolean): boolean;
534
574
  export declare function recordDeletionIntent(paths: CoordinatorStatePaths, entry: NamespaceDeletionEntryV1): Promise<void>;
535
575
  export declare function advanceDeletion(paths: CoordinatorStatePaths, deletionId: string, phase: NamespaceDeletionEntryV1["phase"], cleanup?: Partial<NamespaceDeletionEntryV1["cleanup"]>, safeResponse?: Record<string, unknown>): Promise<void>;
@@ -80,6 +80,8 @@ export interface ExtensionUIDialogOptions {
80
80
  customInput?: {
81
81
  optionLabel: string;
82
82
  onSubmit: (text: string) => void;
83
+ /** Empty/whitespace-only submissions may be rejected by the selector. */
84
+ allowEmpty?: boolean;
83
85
  };
84
86
  /**
85
87
  * Inline free-text input for a non-answer clarification action. It is
@@ -99,6 +99,18 @@ export declare function deriveRoundKey(interviewId: string | undefined, input: {
99
99
  round: number;
100
100
  questionId?: string;
101
101
  }): string;
102
+ /**
103
+ * Envelope-reserved keys that are never legitimate interview `state` fields.
104
+ *
105
+ * A malformed write that wraps a whole envelope under `state`
106
+ * (`gjc state deep-interview write --input '{"state": <envelope>}'`) leaks these
107
+ * into the nested state. Because normalization otherwise preserves unknown
108
+ * nested fields, they would accrete a recursive `state.state` chain (plus stale
109
+ * `receipt`/`skill`/`version`/... duplicates) that no later merge or write ever
110
+ * removes, permanently corrupting the shape. They are stripped from `state` on
111
+ * normalize so the canonical envelope self-heals on the next write.
112
+ */
113
+ export declare const ENVELOPE_RESERVED_STATE_KEYS: readonly ["state", "receipt", "skill", "version", "updated_at", "active", "current_phase", "state_revision", "source_state_revision", "last_applied_draft_id", "session_id"];
102
114
  /**
103
115
  * Canonicalize a deep-interview envelope: interview data nested under `state`,
104
116
  * legacy flattened fields hoisted in losslessly, transcript duplicates removed
@@ -0,0 +1,6 @@
1
+ /** Shared placeholder semantics for model-authored workflow content. */
2
+ export declare const WORKFLOW_PLACEHOLDER_CORRECTION = "provide a specific, non-placeholder question or objective instead of empty, whitespace, unused, TODO, TBD, N/A, N-A, NA, none, placeholder, or stub";
3
+ /** Exact, case-insensitive placeholder detection; meaningful sentences remain valid. */
4
+ export declare function isWorkflowPlaceholderText(value: unknown): boolean;
5
+ /** Detect a legacy formatted deep-interview ask whose visible body is a placeholder. */
6
+ export declare function isLegacyDeepInterviewPlaceholder(value: unknown): boolean;
@@ -47,7 +47,7 @@ export interface InteractiveModeNotify {
47
47
  kind: "warn" | "error" | "info";
48
48
  message: string;
49
49
  }
50
- export declare function submitInteractiveInput(mode: Pick<InteractiveMode, "markPendingSubmissionStarted" | "finishPendingSubmission" | "showError" | "checkShutdownRequested">, session: Pick<AgentSession, "prompt" | "promptCustomMessage">, input: SubmittedUserInput): Promise<void>;
50
+ export declare function submitInteractiveInput(mode: Pick<InteractiveMode, "markPendingSubmissionStarted" | "finishPendingSubmission" | "showError" | "checkShutdownRequested" | "waitForAgentEnd">, session: Pick<AgentSession, "prompt" | "promptCustomMessage">, input: SubmittedUserInput): Promise<void>;
51
51
  type StartupModelProfileArgs = {
52
52
  session: AgentSession;
53
53
  settings: Settings;
@@ -26,4 +26,5 @@ export declare class ActionRegistry<Context> {
26
26
  all(): readonly ActionDefinition<Context>[];
27
27
  isAvailable(id: AppKeybinding): boolean;
28
28
  execute(id: AppKeybinding): Promise<boolean>;
29
+ executeFresh(id: AppKeybinding): Promise<boolean>;
29
30
  }
@@ -47,6 +47,7 @@ export interface HookSelectorOptions {
47
47
  customInput?: {
48
48
  optionLabel: string;
49
49
  onSubmit: (text: string) => void;
50
+ allowEmpty?: boolean;
50
51
  };
51
52
  clarificationInput?: {
52
53
  optionLabel: string;
@@ -20,7 +20,7 @@ export interface MCPAddWizardOAuthResult {
20
20
  }
21
21
  export declare class MCPAddWizard extends Container {
22
22
  #private;
23
- constructor(onComplete: (name: string, config: MCPServerConfig, scope: Scope) => void, onCancel: () => void, onOAuth?: (endpointUrl: string, authUrl: string, tokenUrl: string, clientId: string, clientSecret: string, scopes: string) => Promise<MCPAddWizardOAuthResult>, onTestConnection?: (config: MCPServerConfig) => Promise<void>, onRender?: () => void, initialName?: string);
23
+ constructor(onComplete: (name: string, config: MCPServerConfig, scope: Scope) => void, onCancel: () => void, onOAuth?: (endpointUrl: string, authUrl: string, tokenUrl: string, clientId: string, clientSecret: string, scopes: string, signal: AbortSignal) => Promise<MCPAddWizardOAuthResult>, onTestConnection?: (config: MCPServerConfig) => Promise<void>, onRender?: () => void, onCommandPalette?: (keyData: string) => boolean, initialName?: string, onOAuthCredentialCleanup?: (credentialId: string) => Promise<void> | void, onOAuthCredentialCleanupError?: (credentialId: string, error: unknown) => void);
24
24
  dispose(): void;
25
25
  handleInput(keyData: string): void;
26
26
  }
@@ -18,6 +18,8 @@ export interface WelcomeComponentOptions {
18
18
  collapseChangelog?: boolean;
19
19
  buildLabel?: string;
20
20
  keyDisplayContext?: KeyDisplayContext;
21
+ /** Render the resting logo frame instead of playing the startup gradient sweep. */
22
+ reducedMotion?: boolean;
21
23
  }
22
24
  /**
23
25
  * GJC-native launch surface with compact command affordances, project
@@ -1,8 +1,17 @@
1
1
  import { type AutocompleteProvider, type SlashCommand } from "@gajae-code/tui";
2
- import { type ComposerSubmissionOptions, type InteractiveModeContext } from "../../modes/types";
2
+ import { type ComposerSubmissionOptions, type InteractiveModeContext, type SubmittedUserInput } from "../../modes/types";
3
3
  import { loadPastedImageBatch } from "../../utils/pasted-image-loading";
4
4
  import { ActionRegistry } from "../action-registry";
5
5
  import type { PasteTextContext } from "../components/custom-editor";
6
+ /**
7
+ * Navigation actions that already carry a registry callback and an availability
8
+ * predicate but shipped with no curated command-palette entry and no key
9
+ * dispatch, leaving them unreachable from the palette. They opt into
10
+ * availability gating so an unavailable id is not listed, and each gets a remap
11
+ * dispatch loop while keeping `defaultKeys: []` -- inert at defaults, but a user
12
+ * binding now dispatches instead of only being rendered by the selector.
13
+ */
14
+ export declare const AVAILABILITY_GATED_NAV_PALETTE_ACTIONS: readonly ["app.session.dashboard", "app.transcript.browse", "app.transcript.prevTurn", "app.transcript.nextTurn", "app.queue.togglePane", "app.message.sendNow"];
6
15
  export declare const INTERACTIVE_ABORT_CLEANUP_TIMEOUT_MS = 5000;
7
16
  export declare const BACKGROUND_FOLD_DOUBLE_PRESS_MS = 750;
8
17
  interface InputControllerDependencies {
@@ -16,6 +25,12 @@ export declare class InputController {
16
25
  setupKeyHandlers(): void;
17
26
  setupEditorSubmitHandler(): void;
18
27
  submitText(text: string, composer: ComposerSubmissionOptions): Promise<void>;
28
+ takeDeferredSubmission(): SubmittedUserInput | undefined;
29
+ takeDeferredSubmissionForShutdown(): {
30
+ text: string;
31
+ images?: InteractiveModeContext["pendingImages"];
32
+ } | undefined;
33
+ discardDeferredSubmission(): void;
19
34
  handleCtrlC(): void;
20
35
  handleCtrlD(): void;
21
36
  handleCtrlZ(): void;
@@ -1,4 +1,37 @@
1
+ import { type MCPOAuthConfig, MCPOAuthFlow } from "../../runtime-mcp/oauth-flow";
1
2
  import type { InteractiveModeContext } from "../types";
3
+ /**
4
+ * Outcome of {@link MCPCommandController}'s OAuth handler.
5
+ *
6
+ * `clientId`/`clientSecret` are populated when the OAuth provider required (or
7
+ * accepted) dynamic client registration; callers MUST persist them alongside
8
+ * `credentialId` so subsequent token refreshes and reauthorizations can reuse
9
+ * the same registered client. Both are also set when the caller pre-supplied a
10
+ * client id via the wizard or `oauth.clientId` in `mcp.json`, in which case the
11
+ * write-back is a no-op.
12
+ */
13
+ interface OAuthFlowResult {
14
+ credentialId: string;
15
+ tokenEndpoint: string;
16
+ clientId?: string;
17
+ clientSecret?: string;
18
+ }
19
+ type MCPAuthFlow = Pick<MCPOAuthFlow, "resolvedClientId" | "registeredClientSecret"> & {
20
+ login(): Promise<{
21
+ access: string;
22
+ refresh: string;
23
+ expires: number;
24
+ }>;
25
+ };
26
+ type MCPAuthCallbacks = {
27
+ onAuth(info: {
28
+ url: string;
29
+ instructions?: string;
30
+ }): void;
31
+ onProgress(message: string): void;
32
+ signal?: AbortSignal;
33
+ };
34
+ type MCPAuthFlowFactory = (config: MCPOAuthConfig, callbacks: MCPAuthCallbacks) => MCPAuthFlow;
2
35
  export declare class MCPCommandController {
3
36
  #private;
4
37
  private ctx;
@@ -7,4 +40,13 @@ export declare class MCPCommandController {
7
40
  * Handle /mcp command and route to subcommands
8
41
  */
9
42
  handle(text: string): Promise<void>;
43
+ /**
44
+ * Handle OAuth authentication flow for MCP server
45
+ */
46
+ /** Internal OAuth entry point; injectable flow construction keeps controller lifecycle coverage deterministic. */
47
+ handleOAuthFlow(endpointUrl: string, authUrl: string, tokenUrl: string, clientId: string, clientSecret: string, scopes: string, callbackPort?: number, callbackPath?: string, redirectUri?: string, oauthMeta?: {
48
+ issuer?: string;
49
+ issuerResponseIssSupported?: boolean;
50
+ }, createFlow?: MCPAuthFlowFactory, openBrowser?: (url: string) => void, signal?: AbortSignal): Promise<OAuthFlowResult>;
10
51
  }
52
+ export {};
@@ -126,6 +126,10 @@ export declare class InteractiveMode implements InteractiveModeContext {
126
126
  skillCommands: Map<string, Skill>;
127
127
  oauthManualInput: OAuthManualInputManager;
128
128
  promptSuggestion: PromptSuggestionController;
129
+ waitForAgentEnd(): {
130
+ promise: Promise<void>;
131
+ dispose: () => void;
132
+ };
129
133
  readonly lspServers: LspStartupServerInfo[] | undefined;
130
134
  mcpManager?: import("../runtime-mcp").MCPManager;
131
135
  /** Direct controller capabilities for consumers that coordinate mode transitions. */
@@ -177,6 +181,9 @@ export declare class InteractiveMode implements InteractiveModeContext {
177
181
  }): void;
178
182
  showError(message: string): void;
179
183
  showWarning(message: string): void;
184
+ beginOAuthUrlForCopy(url: string): () => void;
185
+ hasOAuthUrlForCopy(): boolean;
186
+ copyOAuthUrl(): Promise<void>;
180
187
  syncActivityIndicator(): void;
181
188
  ensureLoadingAnimation(): void;
182
189
  stopLoadingAnimation(options?: ActivityIndicatorStopOptions): void;
@@ -0,0 +1,9 @@
1
+ export interface OAuthUrlCopyLeaseHost {
2
+ beginOAuthUrlForCopy(url: string): () => void;
3
+ }
4
+ export interface OAuthUrlCopyLease {
5
+ replace(url: string): void;
6
+ release(): void;
7
+ }
8
+ export declare function buildOAuthLoginAnchor(url: string, label?: string, hyperlinks?: boolean): string;
9
+ export declare function createOAuthUrlCopyLease(host: OAuthUrlCopyLeaseHost): OAuthUrlCopyLease;
@@ -173,6 +173,9 @@ export interface InteractiveModeContext {
173
173
  }): void;
174
174
  showError(message: string): void;
175
175
  showWarning(message: string): void;
176
+ beginOAuthUrlForCopy(url: string): () => void;
177
+ hasOAuthUrlForCopy(): boolean;
178
+ copyOAuthUrl(): Promise<void>;
176
179
  notifyConfigChanged?: () => Promise<void> | void;
177
180
  showNewVersionNotification(newVersion: string): void;
178
181
  clearEditor(): void;
@@ -1,4 +1,4 @@
1
- export declare const UI_LANGUAGES: readonly ["en", "ko"];
1
+ export declare const UI_LANGUAGES: readonly ["en", "ko", "ja"];
2
2
  export type UiLanguage = (typeof UI_LANGUAGES)[number];
3
3
  declare const ENGLISH_STRINGS: {
4
4
  readonly "settings.title": "Settings";
@@ -21,6 +21,7 @@ declare const ENGLISH_STRINGS: {
21
21
  readonly "settings.language.description": "Language for human-facing interactive UI text";
22
22
  readonly "settings.language.english": "English";
23
23
  readonly "settings.language.korean": "Korean (한국어)";
24
+ readonly "settings.language.japanese": "Japanese (日本語)";
24
25
  readonly "language.current": "Current UI language:";
25
26
  readonly "language.changed": "UI language changed to";
26
27
  readonly "language.unknown": "Unknown language";
@@ -144,5 +144,6 @@ export declare class LifecycleLedger {
144
144
  findCleanupPendingBySessionId(sessionId: string, excludingIdentity: string): LifecycleLedgerEntry | undefined;
145
145
  hasUncertainCleanupForSession(sessionId: string, excludingIdentity: string): boolean;
146
146
  get(identity: string): LifecycleLedgerEntry | undefined;
147
+ listUncertainCreatesBySessionId(sessionId: string, effectMarker?: string, remoteCreateKey?: string): LifecycleLedgerEntry[];
147
148
  findPendingCleanupByTarget(sessionId: string, cwd: string, transcriptPath: string): LifecycleLedgerEntry | undefined;
148
149
  }