claudish 14.1.0 → 14.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -575,7 +575,7 @@ var init_onepassword_config = __esm(() => {
575
575
  });
576
576
 
577
577
  // src/version.ts
578
- var VERSION = "14.1.0";
578
+ var VERSION = "14.3.0";
579
579
 
580
580
  // src/redact.ts
581
581
  function isPlaceholder(value) {
@@ -747,9 +747,9 @@ function scheduleFlush() {
747
747
  }
748
748
  });
749
749
  }
750
- function rotateOldLogs(dir, keep) {
750
+ function rotateOldLogs(dir, keep, name = "claudish") {
751
751
  try {
752
- const files = readdirSync(dir).filter((f) => f.startsWith("claudish_") && f.endsWith(".log")).sort().reverse();
752
+ const files = readdirSync(dir).filter((f) => f.startsWith(`${name}_`) && f.endsWith(".log")).sort().reverse();
753
753
  for (const file of files.slice(keep)) {
754
754
  try {
755
755
  unlinkSync(join2(dir, file));
@@ -788,7 +788,7 @@ function redactDeep(val, key) {
788
788
  return val;
789
789
  }
790
790
  function isStructuralLogWorthy(msg) {
791
- return msg.startsWith("[SSE:") || msg.startsWith("[Suppressed]") || msg.startsWith("[Proxy]") || msg.startsWith("[Claude Code]") || msg.startsWith("[Fallback]") || msg.startsWith("[Recovery]") || msg.startsWith("[Streaming] ===") || msg.startsWith("[Streaming] Chunk:") || msg.startsWith("[Streaming] Received") || msg.startsWith("[Streaming] Text-based tool calls") || msg.startsWith("[Streaming] Final usage") || msg.startsWith("[Streaming] Sending") || msg.startsWith("[AnthropicSSE] Stream complete") || msg.startsWith("[AnthropicSSE] Tool use:") || msg.includes("Response status:") || msg.includes("Error") || msg.includes("error") || msg.includes("[Auto-route]");
791
+ return msg.startsWith("[SSE:") || msg.startsWith("[Suppressed]") || msg.startsWith("[Proxy]") || msg.startsWith("[Claude Code]") || msg.startsWith("[Fallback]") || msg.startsWith("[mcp]") || msg.startsWith("[recommended]") || msg.startsWith("[catalog]") || msg.startsWith("[effort]") || msg.startsWith("[team]") || msg.startsWith("[Recovery]") || msg.startsWith("[Streaming] ===") || msg.startsWith("[Streaming] Chunk:") || msg.startsWith("[Streaming] Received") || msg.startsWith("[Streaming] Text-based tool calls") || msg.startsWith("[Streaming] Final usage") || msg.startsWith("[Streaming] Sending") || msg.startsWith("[AnthropicSSE] Stream complete") || msg.startsWith("[AnthropicSSE] Tool use:") || msg.includes("Response status:") || msg.includes("Error") || msg.includes("error") || msg.includes("[Auto-route]");
792
792
  }
793
793
  function redactLogLine(message, timestamp) {
794
794
  if (message.startsWith("[SSE:")) {
@@ -805,20 +805,24 @@ function logFileStamp() {
805
805
  const timestamp = new Date().toISOString().replace(/[:.]/g, "-").split("T").join("_").slice(0, -5);
806
806
  return `${timestamp}_${process.pid}`;
807
807
  }
808
- function initLogger(debugMode, level = "info", noLogs = false) {
808
+ function initLogger(debugMode, level = "info", noLogs = false, name = "claudish", keep = 20) {
809
809
  if (!noLogs) {
810
- const logsDir = join2(homedir2(), ".claudish", "logs");
811
- if (!existsSync2(logsDir)) {
812
- mkdirSync(logsDir, { recursive: true });
813
- }
814
- alwaysOnLogPath = join2(logsDir, `claudish_${logFileStamp()}.log`);
815
- writeFileSync2(alwaysOnLogPath, `Claudish Session Log - ${new Date().toISOString()}
810
+ try {
811
+ const logsDir = join2(homedir2(), ".claudish", "logs");
812
+ if (!existsSync2(logsDir)) {
813
+ mkdirSync(logsDir, { recursive: true });
814
+ }
815
+ alwaysOnLogPath = join2(logsDir, `${name}_${logFileStamp()}.log`);
816
+ writeFileSync2(alwaysOnLogPath, `Claudish Session Log - ${new Date().toISOString()}
816
817
  Mode: structural (content redacted)
817
818
  ${"=".repeat(60)}
818
819
 
819
820
  `);
820
- rotateOldLogs(logsDir, 20);
821
- scheduleFlush();
821
+ rotateOldLogs(logsDir, keep, name);
822
+ scheduleFlush();
823
+ } catch {
824
+ alwaysOnLogPath = null;
825
+ }
822
826
  }
823
827
  if (debugMode) {
824
828
  logLevel = level;
@@ -6621,6 +6625,25 @@ var init_remote_provider_types = __esm(() => {
6621
6625
  };
6622
6626
  });
6623
6627
 
6628
+ // src/fs-atomic.ts
6629
+ import { randomUUID } from "crypto";
6630
+ import { mkdirSync as mkdirSync6, renameSync, unlinkSync as unlinkSync2, writeFileSync as writeFileSync6 } from "fs";
6631
+ import { dirname as dirname5 } from "path";
6632
+ function writeFileAtomic(path, text) {
6633
+ mkdirSync6(dirname5(path), { recursive: true });
6634
+ const tmp = `${path}.tmp.${process.pid}.${randomUUID()}`;
6635
+ try {
6636
+ writeFileSync6(tmp, text, "utf-8");
6637
+ renameSync(tmp, path);
6638
+ } catch (error) {
6639
+ try {
6640
+ unlinkSync2(tmp);
6641
+ } catch {}
6642
+ throw error;
6643
+ }
6644
+ }
6645
+ var init_fs_atomic = () => {};
6646
+
6624
6647
  // src/providers/connection-wire.ts
6625
6648
  function isObject(value) {
6626
6649
  return value !== null && typeof value === "object" && !Array.isArray(value);
@@ -6729,9 +6752,9 @@ function normaliseCatalogPayload(data) {
6729
6752
  }
6730
6753
 
6731
6754
  // src/providers/all-models-cache.ts
6732
- import { existsSync as existsSync7, mkdirSync as mkdirSync6, readFileSync as readFileSync7, statSync as statSync2, writeFileSync as writeFileSync6 } from "fs";
6755
+ import { existsSync as existsSync7, readFileSync as readFileSync7, statSync as statSync2 } from "fs";
6733
6756
  import { homedir as homedir9 } from "os";
6734
- import { dirname as dirname5, join as join9 } from "path";
6757
+ import { join as join9 } from "path";
6735
6758
  function reasoningStatusOf(entry) {
6736
6759
  if (entry.reasoningStatus === "known" || entry.reasoningStatus === "unknown") {
6737
6760
  return entry.reasoningStatus;
@@ -6808,7 +6831,10 @@ function readSidecarRegistry(path) {
6808
6831
  try {
6809
6832
  const raw = JSON.parse(readFileSync7(routeRegistryPathFor(path), "utf-8"));
6810
6833
  return typeof raw.generationId === "string" && isRouteRegistry(raw.registry) ? raw : null;
6811
- } catch {
6834
+ } catch (err) {
6835
+ if (err?.code !== "ENOENT") {
6836
+ log(`[catalog] unreadable route registry for ${path}: ${err instanceof Error ? err.message : String(err)}`);
6837
+ }
6812
6838
  return null;
6813
6839
  }
6814
6840
  }
@@ -6834,7 +6860,8 @@ function readAllModelsCache(path = ALL_MODELS_CACHE_PATH) {
6834
6860
  let cache;
6835
6861
  try {
6836
6862
  cache = parseAllModelsCache(JSON.parse(readFileSync7(path, "utf-8")));
6837
- } catch {
6863
+ } catch (err) {
6864
+ log(`[catalog] unreadable ${path}: ${err instanceof Error ? err.message : String(err)}`);
6838
6865
  cache = null;
6839
6866
  }
6840
6867
  if (cache && !cache.routeRegistry && side) {
@@ -6849,20 +6876,20 @@ function readAllModelsCache(path = ALL_MODELS_CACHE_PATH) {
6849
6876
  return cache;
6850
6877
  }
6851
6878
  function writeRouteRegistry(routeRegistry, path = ALL_MODELS_CACHE_PATH) {
6852
- mkdirSync6(dirname5(path), { recursive: true });
6853
- writeFileSync6(routeRegistryPathFor(path), JSON.stringify(routeRegistry), "utf-8");
6879
+ writeFileAtomic(routeRegistryPathFor(path), JSON.stringify(routeRegistry));
6854
6880
  _readMemo.delete(path);
6855
6881
  }
6856
6882
  function writeAllModelsCache(data, path = ALL_MODELS_CACHE_PATH) {
6857
- mkdirSync6(dirname5(path), { recursive: true });
6858
- writeFileSync6(path, JSON.stringify(data), "utf-8");
6883
+ writeFileAtomic(path, JSON.stringify(data));
6859
6884
  if (data.routeRegistry) {
6860
- writeFileSync6(routeRegistryPathFor(path), JSON.stringify(data.routeRegistry), "utf-8");
6885
+ writeFileAtomic(routeRegistryPathFor(path), JSON.stringify(data.routeRegistry));
6861
6886
  }
6862
6887
  _readMemo.delete(path);
6863
6888
  }
6864
6889
  var ALL_MODELS_CACHE_PATH, _readMemo;
6865
6890
  var init_all_models_cache = __esm(() => {
6891
+ init_fs_atomic();
6892
+ init_logger();
6866
6893
  init_connection_wire();
6867
6894
  ALL_MODELS_CACHE_PATH = join9(homedir9(), ".claudish", "cloud-models-catalog-v3.json");
6868
6895
  _readMemo = new Map;
@@ -12412,9 +12439,9 @@ import {
12412
12439
  mkdirSync as mkdirSync7,
12413
12440
  openSync as openSync2,
12414
12441
  readFileSync as readFileSync9,
12415
- renameSync,
12442
+ renameSync as renameSync2,
12416
12443
  statSync as statSync3,
12417
- unlinkSync as unlinkSync2,
12444
+ unlinkSync as unlinkSync3,
12418
12445
  writeSync as writeSync2
12419
12446
  } from "fs";
12420
12447
  import { dirname as dirname6 } from "path";
@@ -12443,10 +12470,10 @@ function writeCredentialFileAtomic(path, data) {
12443
12470
  } finally {
12444
12471
  closeSync2(fd);
12445
12472
  }
12446
- renameSync(tmp, path);
12473
+ renameSync2(tmp, path);
12447
12474
  } catch (err) {
12448
12475
  try {
12449
- unlinkSync2(tmp);
12476
+ unlinkSync3(tmp);
12450
12477
  } catch {}
12451
12478
  throw err;
12452
12479
  }
@@ -12562,7 +12589,7 @@ class CredentialFileState {
12562
12589
  }
12563
12590
  const path = this.opts.path();
12564
12591
  try {
12565
- unlinkSync2(path);
12592
+ unlinkSync3(path);
12566
12593
  } catch (err) {
12567
12594
  if (err?.code !== "ENOENT")
12568
12595
  return "unreadable";
@@ -12630,7 +12657,7 @@ var init_credential_file = __esm(() => {
12630
12657
  // src/auth/oauth-manager.ts
12631
12658
  import { exec as exec2 } from "child_process";
12632
12659
  import { createHash as createHash2, randomBytes as randomBytes2 } from "crypto";
12633
- import { existsSync as existsSync10, mkdirSync as mkdirSync8, unlinkSync as unlinkSync3 } from "fs";
12660
+ import { existsSync as existsSync10, mkdirSync as mkdirSync8, unlinkSync as unlinkSync4 } from "fs";
12634
12661
  import { homedir as homedir12 } from "os";
12635
12662
  import { join as join12 } from "path";
12636
12663
  import { promisify as promisify2 } from "util";
@@ -12669,7 +12696,7 @@ class OAuthManager {
12669
12696
  deleteCredentials() {
12670
12697
  const credPath = this.getCredentialsPath();
12671
12698
  if (existsSync10(credPath)) {
12672
- unlinkSync3(credPath);
12699
+ unlinkSync4(credPath);
12673
12700
  log(`[${this.providerName}] Credentials deleted`);
12674
12701
  }
12675
12702
  }
@@ -13133,7 +13160,7 @@ var init_clock = __esm(() => {
13133
13160
  });
13134
13161
 
13135
13162
  // src/recovery/coordinator.ts
13136
- import { randomUUID } from "crypto";
13163
+ import { randomUUID as randomUUID2 } from "crypto";
13137
13164
  function hostOf2(endpoint) {
13138
13165
  try {
13139
13166
  return new URL(endpoint).host || endpoint;
@@ -13220,7 +13247,7 @@ function joinEpisode(seed) {
13220
13247
  } else {
13221
13248
  const nowPerf = clock.now();
13222
13249
  ep = {
13223
- episodeId: randomUUID(),
13250
+ episodeId: randomUUID2(),
13224
13251
  key,
13225
13252
  providerDisplayName: seed.providerDisplayName,
13226
13253
  endpoint: seed.endpoint,
@@ -13713,7 +13740,7 @@ var init_transient_retry = __esm(() => {
13713
13740
  });
13714
13741
 
13715
13742
  // src/providers/grok/grok-credentials.ts
13716
- import { existsSync as existsSync11, readFileSync as readFileSync10, renameSync as renameSync2, writeFileSync as writeFileSync7 } from "fs";
13743
+ import { existsSync as existsSync11, readFileSync as readFileSync10, renameSync as renameSync3, writeFileSync as writeFileSync7 } from "fs";
13717
13744
  import { homedir as homedir14 } from "os";
13718
13745
  import { join as join14 } from "path";
13719
13746
  function grokHome() {
@@ -13843,7 +13870,7 @@ function persistRefreshedToken(scope, refreshedFrom, next) {
13843
13870
  const tmp = `${path}.claudish.tmp`;
13844
13871
  writeFileSync7(tmp, `${JSON.stringify(parsed, null, 2)}
13845
13872
  `, { mode: 384 });
13846
- renameSync2(tmp, path);
13873
+ renameSync3(tmp, path);
13847
13874
  }
13848
13875
  async function performRefresh(cred) {
13849
13876
  if (!cred.refreshToken || !cred.clientId) {
@@ -30875,7 +30902,7 @@ __export(exports_antigravity, {
30875
30902
  AntigravityProviderTransport: () => AntigravityProviderTransport,
30876
30903
  resolveAntigravityServedModel: () => resolveAntigravityServedModel
30877
30904
  });
30878
- import { randomUUID as randomUUID2 } from "crypto";
30905
+ import { randomUUID as randomUUID3 } from "crypto";
30879
30906
  function antigravityEndpoint() {
30880
30907
  return `${antigravityHost()}/v1internal:streamGenerateContent?alt=sse`;
30881
30908
  }
@@ -31057,7 +31084,7 @@ class AntigravityProviderTransport {
31057
31084
  const envelope = {
31058
31085
  model,
31059
31086
  project: this.projectId,
31060
- user_prompt_id: randomUUID2(),
31087
+ user_prompt_id: randomUUID3(),
31061
31088
  request: innerPayload
31062
31089
  };
31063
31090
  if (this.tierId && this.tierId !== "free-tier") {
@@ -31320,7 +31347,7 @@ function redactSecrets2(text) {
31320
31347
  }
31321
31348
 
31322
31349
  // src/auth/credentials/antigravity-credential.ts
31323
- import { randomUUID as randomUUID3 } from "crypto";
31350
+ import { randomUUID as randomUUID4 } from "crypto";
31324
31351
  function createActivityRequestId2() {
31325
31352
  return Math.random().toString(36).substring(7);
31326
31353
  }
@@ -31354,7 +31381,7 @@ class AntigravityCredentialProvider {
31354
31381
  const env = {
31355
31382
  model: servedModel,
31356
31383
  project: projectId,
31357
- user_prompt_id: randomUUID3(),
31384
+ user_prompt_id: randomUUID4(),
31358
31385
  request: inner
31359
31386
  };
31360
31387
  if (tierId && tierId !== "free-tier") {
@@ -31642,7 +31669,7 @@ var init_api_key_credential = __esm(() => {
31642
31669
  // src/auth/codex-oauth.ts
31643
31670
  import { exec as exec3 } from "child_process";
31644
31671
  import { createHash as createHash11, randomBytes as randomBytes4 } from "crypto";
31645
- import { closeSync as closeSync4, existsSync as existsSync16, openSync as openSync4, readFileSync as readFileSync14, unlinkSync as unlinkSync4, writeSync as writeSync3 } from "fs";
31672
+ import { closeSync as closeSync4, existsSync as existsSync16, openSync as openSync4, readFileSync as readFileSync14, unlinkSync as unlinkSync5, writeSync as writeSync3 } from "fs";
31646
31673
  import { createServer } from "http";
31647
31674
  import { homedir as homedir21 } from "os";
31648
31675
  import { join as join21 } from "path";
@@ -31699,7 +31726,7 @@ class CodexOAuth {
31699
31726
  async logout() {
31700
31727
  const credPath = this.getCredentialsPath();
31701
31728
  if (existsSync16(credPath)) {
31702
- unlinkSync4(credPath);
31729
+ unlinkSync5(credPath);
31703
31730
  log("[CodexOAuth] Credentials deleted");
31704
31731
  }
31705
31732
  this.credentials = null;
@@ -32327,7 +32354,7 @@ import {
32327
32354
  mkdirSync as mkdirSync10,
32328
32355
  openSync as openSync5,
32329
32356
  readFileSync as readFileSync16,
32330
- unlinkSync as unlinkSync5,
32357
+ unlinkSync as unlinkSync6,
32331
32358
  writeSync as writeSync4
32332
32359
  } from "fs";
32333
32360
  import { homedir as homedir23, hostname, platform, release as release2 } from "os";
@@ -32568,7 +32595,7 @@ Waiting for authorization...`);
32568
32595
  async logout() {
32569
32596
  const credPath = kimiOAuthPath();
32570
32597
  if (existsSync17(credPath)) {
32571
- unlinkSync5(credPath);
32598
+ unlinkSync6(credPath);
32572
32599
  log("[KimiOAuth] Credentials deleted");
32573
32600
  }
32574
32601
  this.state.forget();
@@ -32882,7 +32909,7 @@ import {
32882
32909
  existsSync as existsSync19,
32883
32910
  mkdirSync as mkdirSync11,
32884
32911
  readFileSync as readFileSync18,
32885
- renameSync as renameSync3,
32912
+ renameSync as renameSync4,
32886
32913
  rmSync as rmSync3,
32887
32914
  writeFileSync as writeFileSync8
32888
32915
  } from "fs";
@@ -32921,7 +32948,7 @@ function writeMuseStore(kind, record, dir = defaultMuseStoreDir()) {
32921
32948
  writeFileSync8(tmp, `${JSON.stringify(record, null, 2)}
32922
32949
  `, { mode: 384 });
32923
32950
  chmodSync(tmp, 384);
32924
- renameSync3(tmp, path);
32951
+ renameSync4(tmp, path);
32925
32952
  }
32926
32953
  function writeBorrowedCopy(accessToken, subsTierName, dir = defaultMuseStoreDir(), now = () => new Date) {
32927
32954
  const copy = {
@@ -34698,7 +34725,14 @@ function startCatalogWarm() {
34698
34725
  if (_warmPromise)
34699
34726
  return _warmPromise;
34700
34727
  const promise = refreshCatalog(8000).then((result) => {
34701
- if (result.kind !== "refreshed" && _warmPromise === promise)
34728
+ if (result.kind === "refreshed")
34729
+ return;
34730
+ log(`[catalog] refresh failed: ${result.kind === "fetch_failed" ? result.reason : `incompatible contract ${result.serverContractVersion ?? "unknown"}`}`);
34731
+ if (_warmPromise === promise)
34732
+ _warmPromise = null;
34733
+ }, (err) => {
34734
+ log(`[catalog] refresh threw: ${err instanceof Error ? err.message : String(err)}`);
34735
+ if (_warmPromise === promise)
34702
34736
  _warmPromise = null;
34703
34737
  });
34704
34738
  _warmPromise = promise;
@@ -34729,13 +34763,20 @@ async function ensureRouteRegistryReady(timeoutMs = 5000) {
34729
34763
  await waitForCatalogWarm(timeoutMs);
34730
34764
  }
34731
34765
  async function waitForCatalogWarm(timeoutMs) {
34766
+ let timedOut = false;
34732
34767
  await Promise.race([
34733
34768
  startCatalogWarm(),
34734
- new Promise((resolve) => setTimeout(resolve, timeoutMs))
34769
+ new Promise((resolve) => setTimeout(() => {
34770
+ timedOut = true;
34771
+ resolve();
34772
+ }, timeoutMs))
34735
34773
  ]);
34774
+ if (timedOut)
34775
+ log(`[catalog] still refreshing after ${timeoutMs} ms; the caller goes on without it`);
34736
34776
  }
34737
34777
  var DEFAULT_CATALOG_URL = "https://us-central1-claudish-6da10.cloudfunctions.net/queryModels?status=all&catalog=slim&includeRouteVariants=true&limit=1000", MAX_CATALOG_PAGES = 40, CATALOG_PAGE_LIMIT = 1000, _memCache = null, _catalogEntriesForTest, _warmPromise = null;
34738
34778
  var init_catalog_client = __esm(() => {
34779
+ init_logger();
34739
34780
  init_all_models_cache();
34740
34781
  init_catalog_route_bindings();
34741
34782
  init_connection_wire();
@@ -34981,14 +35022,14 @@ var init_proto_codec = __esm(() => {
34981
35022
  });
34982
35023
 
34983
35024
  // src/providers/devin/devin-request.ts
34984
- import { randomUUID as randomUUID4 } from "crypto";
35025
+ import { randomUUID as randomUUID5 } from "crypto";
34985
35026
  function encodeChatMetadata(meta) {
34986
35027
  const version = meta.clientVersion ?? DEVIN_CLI_VERSION;
34987
35028
  return msg(bytes(1, "devin-cli"), bytes(2, version), bytes(3, meta.apiKey), bytes(4, "en"), bytes(5, meta.platform ?? process.platform), bytes(7, version), bytes(12, "chisel"), bytes(28, "chisel"));
34988
35029
  }
34989
35030
  function encodeMessage(message) {
34990
35031
  const parts = [
34991
- bytes(1, message.id ?? randomUUID4()),
35032
+ bytes(1, message.id ?? randomUUID5()),
34992
35033
  vint(2, DEVIN_ROLE[message.role])
34993
35034
  ];
34994
35035
  if (message.text)
@@ -37155,8 +37196,8 @@ import {
37155
37196
  existsSync as existsSync21,
37156
37197
  mkdirSync as mkdirSync13,
37157
37198
  readFileSync as readFileSync21,
37158
- renameSync as renameSync4,
37159
- unlinkSync as unlinkSync6,
37199
+ renameSync as renameSync5,
37200
+ unlinkSync as unlinkSync7,
37160
37201
  writeFileSync as writeFileSync10
37161
37202
  } from "fs";
37162
37203
  import { homedir as homedir29 } from "os";
@@ -37197,7 +37238,7 @@ function writeToDisk(events) {
37197
37238
  const payload = { version: 1, events: trimmed };
37198
37239
  const tmpFile = join29(CLAUDISH_DIR, `stats-buffer.tmp.${process.pid}.json`);
37199
37240
  writeFileSync10(tmpFile, JSON.stringify(payload, null, 2), "utf-8");
37200
- renameSync4(tmpFile, BUFFER_FILE);
37241
+ renameSync5(tmpFile, BUFFER_FILE);
37201
37242
  memoryCache = trimmed;
37202
37243
  } catch {}
37203
37244
  }
@@ -37240,7 +37281,7 @@ function clearBuffer() {
37240
37281
  memoryCache = [];
37241
37282
  eventsSinceLastFlush = 0;
37242
37283
  if (existsSync21(BUFFER_FILE)) {
37243
- unlinkSync6(BUFFER_FILE);
37284
+ unlinkSync7(BUFFER_FILE);
37244
37285
  }
37245
37286
  } catch {}
37246
37287
  }
@@ -59614,7 +59655,9 @@ function toSlotRow(id, snap, acct, now = Date.now(), upstreamRecords = []) {
59614
59655
  idle_seconds: idle,
59615
59656
  activity: terminal ? null : snap.turnEndRecordMissing && snap.activity ? `${snap.activity}: turn_end_record_missing` : snap.agentCountMismatch && snap.activity ? `${snap.activity}: agent_count_mismatch` : snap.activity,
59616
59657
  pane: snap.paneId || null,
59617
- recent: snap.recent
59658
+ recent: snap.recent,
59659
+ agent_requested: id.agentRequested ?? null,
59660
+ agent: snap.agent ?? null
59618
59661
  };
59619
59662
  }
59620
59663
  var init_slot_row = __esm(() => {
@@ -60027,8 +60070,161 @@ var init_cache_ttl = __esm(() => {
60027
60070
  FIREBASE_CACHE_TTL_MS = FIREBASE_CACHE_TTL_HOURS * 60 * 60 * 1000;
60028
60071
  });
60029
60072
 
60073
+ // src/providers/effort-recommendations.ts
60074
+ import { readFileSync as readFileSync25, statSync as statSync9 } from "fs";
60075
+ function effortRecommendationsPathFor(catalogPath) {
60076
+ return catalogPath.endsWith(".json") ? `${catalogPath.slice(0, -5)}.efforts.json` : `${catalogPath}.efforts.json`;
60077
+ }
60078
+ function isRecord(value) {
60079
+ return typeof value === "object" && value !== null && !Array.isArray(value);
60080
+ }
60081
+ function parseEffortRecommendations(raw) {
60082
+ const out = {};
60083
+ if (!isRecord(raw))
60084
+ return out;
60085
+ for (const [modelId, byTask] of Object.entries(raw)) {
60086
+ const entries = modelId ? parseModelEntries(byTask) : {};
60087
+ if (Object.keys(entries).length > 0)
60088
+ out[modelId] = entries;
60089
+ }
60090
+ return out;
60091
+ }
60092
+ function parseModelEntries(byTask) {
60093
+ const entries = {};
60094
+ if (!isRecord(byTask))
60095
+ return entries;
60096
+ for (const [taskType, entry] of Object.entries(byTask)) {
60097
+ if (!taskType || !isRecord(entry))
60098
+ continue;
60099
+ if (typeof entry.effort !== "string" || entry.effort === "")
60100
+ continue;
60101
+ const sendableOn = parseSendableOn(entry.sendableOn);
60102
+ if (sendableOn.length === 0)
60103
+ continue;
60104
+ entries[taskType] = typeof entry.basis === "string" ? { effort: entry.effort, basis: entry.basis, sendableOn } : { effort: entry.effort, sendableOn };
60105
+ }
60106
+ return entries;
60107
+ }
60108
+ function nonEmptyString(value) {
60109
+ return typeof value === "string" && value !== "";
60110
+ }
60111
+ function parseSendableOn(raw) {
60112
+ if (!Array.isArray(raw))
60113
+ return [];
60114
+ const out = [];
60115
+ for (const item of raw) {
60116
+ if (!isRecord(item))
60117
+ continue;
60118
+ const { routeId, routeProfileId, externalModelId, encoding } = item;
60119
+ if (!nonEmptyString(routeId) || !nonEmptyString(routeProfileId))
60120
+ continue;
60121
+ if (!nonEmptyString(externalModelId))
60122
+ continue;
60123
+ out.push(typeof encoding === "string" ? { routeId, routeProfileId, externalModelId, encoding } : { routeId, routeProfileId, externalModelId });
60124
+ }
60125
+ return out;
60126
+ }
60127
+ function parseSidecar(raw) {
60128
+ if (!isRecord(raw) || raw.contractVersion !== SIDECAR_CONTRACT_VERSION)
60129
+ return null;
60130
+ if (raw.format !== SIDECAR_FORMAT)
60131
+ return null;
60132
+ if (!isRecord(raw.generations))
60133
+ return null;
60134
+ const generations = {};
60135
+ for (const [generationId, generation] of Object.entries(raw.generations)) {
60136
+ if (!generationId || !isRecord(generation))
60137
+ continue;
60138
+ if (typeof generation.writtenAt !== "number" || !Number.isFinite(generation.writtenAt)) {
60139
+ continue;
60140
+ }
60141
+ generations[generationId] = {
60142
+ writtenAt: generation.writtenAt,
60143
+ efforts: parseEffortRecommendations(generation.efforts)
60144
+ };
60145
+ }
60146
+ return { contractVersion: SIDECAR_CONTRACT_VERSION, format: SIDECAR_FORMAT, generations };
60147
+ }
60148
+ function statOrNull2(path) {
60149
+ try {
60150
+ const { mtimeMs, size } = statSync9(path);
60151
+ return { mtimeMs, size };
60152
+ } catch {
60153
+ return null;
60154
+ }
60155
+ }
60156
+ function readSidecarFile(path) {
60157
+ try {
60158
+ return parseSidecar(JSON.parse(readFileSync25(path, "utf-8")));
60159
+ } catch (err) {
60160
+ if (err?.code !== "ENOENT") {
60161
+ log(`[effort] unreadable ${path}: ${err instanceof Error ? err.message : String(err)}`);
60162
+ }
60163
+ return null;
60164
+ }
60165
+ }
60166
+ function foreignSidecarFormat(path) {
60167
+ try {
60168
+ const raw = JSON.parse(readFileSync25(path, "utf-8"));
60169
+ if (isRecord(raw) && raw.format !== SIDECAR_FORMAT)
60170
+ return raw.format ?? "none";
60171
+ } catch {}
60172
+ return;
60173
+ }
60174
+ function readEffortRecommendations(path = EFFORT_RECOMMENDATIONS_PATH) {
60175
+ const stat = statOrNull2(path);
60176
+ if (!stat) {
60177
+ _readMemo2.delete(path);
60178
+ return null;
60179
+ }
60180
+ const key = `${stat.mtimeMs}:${stat.size}`;
60181
+ const memo = _readMemo2.get(path);
60182
+ if (memo && memo.key === key)
60183
+ return memo.sidecar;
60184
+ const sidecar = readSidecarFile(path);
60185
+ _readMemo2.set(path, { key, sidecar });
60186
+ return sidecar;
60187
+ }
60188
+ function writeEffortRecommendations(generationId, raw, path = EFFORT_RECOMMENDATIONS_PATH) {
60189
+ const existing = readSidecarFile(path);
60190
+ if (!existing && !_foreignFormatLogged) {
60191
+ const foreign = foreignSidecarFormat(path);
60192
+ if (foreign !== undefined) {
60193
+ _foreignFormatLogged = true;
60194
+ log(`[effort] replacing a sidecar of format ${String(foreign)} with format ${SIDECAR_FORMAT} at ${path}; its generations are dropped`);
60195
+ }
60196
+ }
60197
+ const merged = {
60198
+ ...existing?.generations ?? {},
60199
+ [generationId]: { writtenAt: Date.now(), efforts: parseEffortRecommendations(raw) }
60200
+ };
60201
+ const kept = Object.entries(merged).sort(([, a], [, b]) => b.writtenAt - a.writtenAt).slice(0, MAX_GENERATIONS);
60202
+ const sidecar = {
60203
+ contractVersion: SIDECAR_CONTRACT_VERSION,
60204
+ format: SIDECAR_FORMAT,
60205
+ generations: Object.fromEntries(kept)
60206
+ };
60207
+ writeFileAtomic(path, JSON.stringify(sidecar));
60208
+ _readMemo2.delete(path);
60209
+ }
60210
+ function latestEffortRecommendations(path = EFFORT_RECOMMENDATIONS_PATH) {
60211
+ const sidecar = readEffortRecommendations(path);
60212
+ if (!sidecar)
60213
+ return null;
60214
+ const newest = Object.entries(sidecar.generations).sort(([, a], [, b]) => b.writtenAt - a.writtenAt)[0];
60215
+ return newest ? { generationId: newest[0], efforts: newest[1].efforts } : null;
60216
+ }
60217
+ var SIDECAR_CONTRACT_VERSION = 3, SIDECAR_FORMAT = 2, MAX_GENERATIONS = 4, EFFORT_RECOMMENDATIONS_PATH, _foreignFormatLogged = false, _readMemo2;
60218
+ var init_effort_recommendations = __esm(() => {
60219
+ init_fs_atomic();
60220
+ init_logger();
60221
+ init_all_models_cache();
60222
+ EFFORT_RECOMMENDATIONS_PATH = effortRecommendationsPathFor(ALL_MODELS_CACHE_PATH);
60223
+ _readMemo2 = new Map;
60224
+ });
60225
+
60030
60226
  // src/model-loader.ts
60031
- import { existsSync as existsSync25, mkdirSync as mkdirSync16, readFileSync as readFileSync25, writeFileSync as writeFileSync15 } from "fs";
60227
+ import { existsSync as existsSync25, readFileSync as readFileSync26 } from "fs";
60032
60228
  import { homedir as homedir32 } from "os";
60033
60229
  import { join as join35 } from "path";
60034
60230
  function isRecommendationTier(value) {
@@ -60174,17 +60370,17 @@ function recommendationProjection(recommendations, richModels = []) {
60174
60370
  plans: cache.plans
60175
60371
  } : { catalogGenerationId: "", entries: [], plans: [] }, richModels);
60176
60372
  }
60177
- function isRecord(value) {
60373
+ function isRecord2(value) {
60178
60374
  return value !== null && typeof value === "object" && !Array.isArray(value);
60179
60375
  }
60180
60376
  function isStringArray(value) {
60181
60377
  return Array.isArray(value) && value.every((item) => typeof item === "string");
60182
60378
  }
60183
60379
  function isRouteObject(value) {
60184
- return isRecord(value) && typeof value.plan === "string" && typeof value.command === "string" && (value.prefix === undefined || typeof value.prefix === "string") && (value.planIds === undefined || isStringArray(value.planIds));
60380
+ return isRecord2(value) && typeof value.plan === "string" && typeof value.command === "string" && (value.prefix === undefined || typeof value.prefix === "string") && (value.planIds === undefined || isStringArray(value.planIds));
60185
60381
  }
60186
60382
  function isUsableRow(value) {
60187
- if (!isRecord(value))
60383
+ if (!isRecord2(value))
60188
60384
  return false;
60189
60385
  if (typeof value.id !== "string" || value.id.length === 0)
60190
60386
  return false;
@@ -60196,7 +60392,7 @@ function isUsableRow(value) {
60196
60392
  return false;
60197
60393
  }
60198
60394
  const pricing = value.pricing;
60199
- if (!isRecord(pricing) || typeof pricing.input !== "string" || typeof pricing.output !== "string" || typeof pricing.average !== "string") {
60395
+ if (!isRecord2(pricing) || typeof pricing.input !== "string" || typeof pricing.output !== "string" || typeof pricing.average !== "string") {
60200
60396
  return false;
60201
60397
  }
60202
60398
  if (value.releaseDate !== undefined && typeof value.releaseDate !== "string")
@@ -60209,7 +60405,7 @@ function isUsableRow(value) {
60209
60405
  return true;
60210
60406
  }
60211
60407
  function readProjectedRecommendationsDoc(value) {
60212
- if (!isRecord(value))
60408
+ if (!isRecord2(value))
60213
60409
  return null;
60214
60410
  if (value.contractVersion !== 3)
60215
60411
  return null;
@@ -60235,15 +60431,21 @@ function readRecommendedModelsCacheFile() {
60235
60431
  return null;
60236
60432
  let parsed;
60237
60433
  try {
60238
- parsed = JSON.parse(readFileSync25(RECOMMENDED_MODELS_CACHE_PATH, "utf-8"));
60239
- } catch {
60434
+ parsed = JSON.parse(readFileSync26(RECOMMENDED_MODELS_CACHE_PATH, "utf-8"));
60435
+ } catch (err) {
60436
+ log(`[recommended] unreadable ${RECOMMENDED_MODELS_CACHE_PATH}: ${err instanceof Error ? err.message : String(err)}`);
60240
60437
  return null;
60241
60438
  }
60242
- if (!isRecord(parsed) || parsed.projectionVersion !== RECOMMENDED_PROJECTION_VERSION) {
60439
+ if (!isRecord2(parsed) || parsed.projectionVersion !== RECOMMENDED_PROJECTION_VERSION) {
60440
+ log(`[recommended] ${RECOMMENDED_MODELS_CACHE_PATH} has projection version ${isRecord2(parsed) ? String(parsed.projectionVersion) : "none"}; this build reads ${RECOMMENDED_PROJECTION_VERSION}`);
60243
60441
  return null;
60244
60442
  }
60245
60443
  return readProjectedRecommendationsDoc(parsed);
60246
60444
  }
60445
+ function readLastRecommendedModels() {
60446
+ const doc = readRecommendedModelsCacheFile();
60447
+ return doc && doc.models.length > 0 ? doc : null;
60448
+ }
60247
60449
  function sectionDefFor(tier) {
60248
60450
  const index = RECOMMENDATION_TIER_INDEX.get(tier);
60249
60451
  return index === undefined ? undefined : RECOMMENDATION_SECTIONS[index];
@@ -60408,7 +60610,7 @@ function computeQuickPicks(primaries) {
60408
60610
  return { budget, largeContext, mostCapable, visionCoding, agentic };
60409
60611
  }
60410
60612
  async function getRecommendedModels(opts = {}) {
60411
- const { forceRefresh = false } = opts;
60613
+ const { forceRefresh = false, effortsPath = EFFORT_RECOMMENDATIONS_PATH } = opts;
60412
60614
  const cached = _cachedRecommendedModels;
60413
60615
  if (!forceRefresh && cached && cached.generationId === readAllModelsCache()?.catalogGenerationId) {
60414
60616
  return cached;
@@ -60432,15 +60634,20 @@ async function getRecommendedModels(opts = {}) {
60432
60634
  if (response.recommendations.generationId !== generationId) {
60433
60635
  throw new Error("Recommendation and model catalog generations differ");
60434
60636
  }
60637
+ try {
60638
+ writeEffortRecommendations(generationId, response.recommendations.efforts, effortsPath);
60639
+ } catch (err) {
60640
+ log(`[effort] sidecar write failed for generation ${generationId}: ${err instanceof Error ? err.message : String(err)}`);
60641
+ }
60435
60642
  const top100 = await fetchCatalogData(`${FIREBASE_BASE_URL}?catalog=top100`, RECOMMENDED_FETCH_TIMEOUT_MS, generationId);
60436
60643
  const data = recommendationProjection(response.recommendations, top100.models);
60437
60644
  if (data.models.length > 0) {
60438
60645
  _cachedRecommendedModels = data;
60439
60646
  try {
60440
- const cacheDir = join35(homedir32(), ".claudish");
60441
- mkdirSync16(cacheDir, { recursive: true });
60442
- writeFileSync15(RECOMMENDED_MODELS_CACHE_PATH, JSON.stringify(data), "utf-8");
60443
- } catch {}
60647
+ writeFileAtomic(RECOMMENDED_MODELS_CACHE_PATH, JSON.stringify(data));
60648
+ } catch (err) {
60649
+ log(`[recommended] cache write failed: ${err instanceof Error ? err.message : String(err)}`);
60650
+ }
60444
60651
  return data;
60445
60652
  }
60446
60653
  } catch (error) {
@@ -60463,7 +60670,8 @@ function getRecommendedModelsSync() {
60463
60670
  async function warmRecommendedModels() {
60464
60671
  try {
60465
60672
  return await getRecommendedModels({ forceRefresh: true });
60466
- } catch {
60673
+ } catch (err) {
60674
+ log(`[recommended] warm failed: ${err instanceof Error ? err.message : String(err)}`);
60467
60675
  return null;
60468
60676
  }
60469
60677
  }
@@ -60571,11 +60779,14 @@ function getAvailableModels() {
60571
60779
  }
60572
60780
  var RECOMMENDATION_SECTIONS, RECOMMENDATION_TIER_INDEX, _cachedModelInfo = null, _cachedModelIds = null, _cachedRecommendedModels = null, FIREBASE_BASE_URL = "https://us-central1-claudish-6da10.cloudfunctions.net/queryModels", FIREBASE_RECOMMENDED_URL, RECOMMENDED_PROJECTION_VERSION = 2, RECOMMENDED_MODELS_CACHE_PATH, RECOMMENDED_FETCH_TIMEOUT_MS = 5000, SEARCH_FETCH_TIMEOUT_MS = 1e4, RECOMMENDED_ROUTE_TIER_ORDER;
60573
60781
  var init_model_loader = __esm(() => {
60782
+ init_fs_atomic();
60783
+ init_logger();
60574
60784
  init_all_models_cache();
60575
60785
  init_auto_route();
60576
60786
  init_cache_ttl();
60577
60787
  init_catalog_client();
60578
60788
  init_catalog_route_bindings();
60789
+ init_effort_recommendations();
60579
60790
  init_route_candidates();
60580
60791
  RECOMMENDATION_SECTIONS = [
60581
60792
  { recommendationTier: "flagship", title: "Flagship", quickPickEligible: true },
@@ -64162,7 +64373,7 @@ var init_DiscoveryNotice = __esm(() => {
64162
64373
  });
64163
64374
 
64164
64375
  // src/providers/model-descriptions.ts
64165
- import { existsSync as existsSync26, mkdirSync as mkdirSync17, readFileSync as readFileSync26, writeFileSync as writeFileSync16 } from "fs";
64376
+ import { existsSync as existsSync26, mkdirSync as mkdirSync16, readFileSync as readFileSync27, writeFileSync as writeFileSync15 } from "fs";
64166
64377
  import { homedir as homedir33 } from "os";
64167
64378
  import { dirname as dirname13, join as join36 } from "path";
64168
64379
  function emptyDescriptionIndex() {
@@ -64186,7 +64397,7 @@ function readCache(path) {
64186
64397
  if (!existsSync26(path))
64187
64398
  return null;
64188
64399
  try {
64189
- const raw = JSON.parse(readFileSync26(path, "utf-8"));
64400
+ const raw = JSON.parse(readFileSync27(path, "utf-8"));
64190
64401
  if (!raw || typeof raw !== "object" || typeof raw.byId !== "object" || raw.byId === null) {
64191
64402
  return null;
64192
64403
  }
@@ -64202,8 +64413,8 @@ function readCache(path) {
64202
64413
  }
64203
64414
  function writeCache(path, cache) {
64204
64415
  try {
64205
- mkdirSync17(dirname13(path), { recursive: true });
64206
- writeFileSync16(path, JSON.stringify(cache), "utf-8");
64416
+ mkdirSync16(dirname13(path), { recursive: true });
64417
+ writeFileSync15(path, JSON.stringify(cache), "utf-8");
64207
64418
  } catch (e) {
64208
64419
  log(`[model-descriptions] cache write failed: ${e?.message ?? String(e)}`);
64209
64420
  }
@@ -70443,7 +70654,7 @@ function renderRecommendedText(doc, getNativePrefix) {
70443
70654
  return lines.join(`
70444
70655
  `);
70445
70656
  }
70446
- function markdownRow(group, getNativePrefix) {
70657
+ function markdownRow(group) {
70447
70658
  const m = group.primary;
70448
70659
  const pricing = formatListingPrice(m);
70449
70660
  const ctx = m.context || "N/A";
@@ -70455,24 +70666,24 @@ function markdownRow(group, getNativePrefix) {
70455
70666
  if (m.supportsVision)
70456
70667
  caps.push("vision");
70457
70668
  const capsLine = caps.length > 0 ? caps.join(", ") : "none";
70458
- const prefixes = collectRoutingPrefixes(group, getNativePrefix);
70459
- const accessLine = prefixes.length > 0 ? prefixes.map((p) => `\`${p}@${m.id}\``).join(" \xB7 ") : `\`${m.id}\``;
70460
70669
  return [
70461
70670
  `### ${m.id}`,
70462
70671
  `- **Pricing**: ${pricing} avg \xB7 ${ctx} context`,
70463
70672
  `- **Capabilities**: ${capsLine}`,
70464
- `- **Access**: ${accessLine}`,
70465
70673
  ""
70466
70674
  ].join(`
70467
70675
  `);
70468
70676
  }
70469
- function renderRecommendedMarkdown(doc, getNativePrefix) {
70677
+ function renderRecommendedMarkdown(doc) {
70470
70678
  const sections = groupRecommendedModels(doc.models);
70471
70679
  let output = `# Recommended Models
70472
70680
 
70473
70681
  `;
70474
70682
  output += `_Last updated: ${doc.lastUpdated || "unknown"}_
70475
70683
 
70684
+ `;
70685
+ output += `Pass each model by its bare id (the heading); claudish routing picks the provider.
70686
+
70476
70687
  `;
70477
70688
  for (const section of sections) {
70478
70689
  output += `## ${section.title}
@@ -70483,7 +70694,7 @@ function renderRecommendedMarkdown(doc, getNativePrefix) {
70483
70694
 
70484
70695
  `;
70485
70696
  for (const group of section.groups)
70486
- output += markdownRow(group, getNativePrefix);
70697
+ output += markdownRow(group);
70487
70698
  }
70488
70699
  const picks = computeQuickPicks(quickPickCandidates(sections));
70489
70700
  const pickLines = [];
@@ -70507,6 +70718,23 @@ function renderRecommendedMarkdown(doc, getNativePrefix) {
70507
70718
  }
70508
70719
  return output;
70509
70720
  }
70721
+ function renderEffortTableMarkdown(efforts) {
70722
+ const models = Object.keys(efforts).sort();
70723
+ if (models.length === 0)
70724
+ return "";
70725
+ const taskTypes = [...new Set(models.flatMap((m) => Object.keys(efforts[m])))].sort();
70726
+ const lines = [
70727
+ "## Recommended effort by task type",
70728
+ "",
70729
+ "Map your task to a column, take the cell for each model you run, and pass it: " + '`team` `efforts: {"<model>": "<level>"}` (keys exactly as in `models`), ' + "`create_session` / `run_prompt` `effort`. A model with no cell keeps Claude Code's " + "own effort.",
70730
+ "",
70731
+ `| model | ${taskTypes.join(" | ")} |`,
70732
+ `|---|${taskTypes.map(() => "---").join("|")}|`,
70733
+ ...models.map((m) => `| ${m} | ${taskTypes.map((t) => efforts[m][t]?.effort ?? "-").join(" | ")} |`)
70734
+ ];
70735
+ return lines.join(`
70736
+ `);
70737
+ }
70510
70738
  var init_recommended_listing = __esm(() => {
70511
70739
  init_model_loader();
70512
70740
  init_provider_definitions();
@@ -70571,7 +70799,7 @@ var init_branding = __esm(() => {
70571
70799
  });
70572
70800
 
70573
70801
  // src/update-checker.ts
70574
- import { existsSync as existsSync27, mkdirSync as mkdirSync18, readFileSync as readFileSync27, unlinkSync as unlinkSync7, writeFileSync as writeFileSync17 } from "fs";
70802
+ import { existsSync as existsSync27, mkdirSync as mkdirSync17, readFileSync as readFileSync28, unlinkSync as unlinkSync8, writeFileSync as writeFileSync16 } from "fs";
70575
70803
  import { homedir as homedir34, platform as platform2, tmpdir } from "os";
70576
70804
  import { join as join37 } from "path";
70577
70805
  function getCacheFilePath() {
@@ -70584,7 +70812,7 @@ function getCacheFilePath() {
70584
70812
  }
70585
70813
  try {
70586
70814
  if (!existsSync27(cacheDir)) {
70587
- mkdirSync18(cacheDir, { recursive: true });
70815
+ mkdirSync17(cacheDir, { recursive: true });
70588
70816
  }
70589
70817
  return join37(cacheDir, "update-check.json");
70590
70818
  } catch {
@@ -70597,7 +70825,7 @@ function readCache2() {
70597
70825
  if (!existsSync27(cachePath)) {
70598
70826
  return null;
70599
70827
  }
70600
- const data = JSON.parse(readFileSync27(cachePath, "utf-8"));
70828
+ const data = JSON.parse(readFileSync28(cachePath, "utf-8"));
70601
70829
  return data;
70602
70830
  } catch {
70603
70831
  return null;
@@ -70610,7 +70838,7 @@ function writeCache2(latestVersion) {
70610
70838
  lastCheck: Date.now(),
70611
70839
  latestVersion
70612
70840
  };
70613
- writeFileSync17(cachePath, JSON.stringify(data), "utf-8");
70841
+ writeFileSync16(cachePath, JSON.stringify(data), "utf-8");
70614
70842
  } catch {}
70615
70843
  }
70616
70844
  function isCacheValid(cache) {
@@ -70621,7 +70849,7 @@ function clearCache() {
70621
70849
  try {
70622
70850
  const cachePath = getCacheFilePath();
70623
70851
  if (existsSync27(cachePath)) {
70624
- unlinkSync7(cachePath);
70852
+ unlinkSync8(cachePath);
70625
70853
  }
70626
70854
  } catch {}
70627
70855
  }
@@ -76560,9 +76788,9 @@ var init_seam_hooks = __esm(() => {
76560
76788
  });
76561
76789
 
76562
76790
  // src/hooks/seam-tap.ts
76563
- import { randomUUID as randomUUID5 } from "crypto";
76791
+ import { randomUUID as randomUUID6 } from "crypto";
76564
76792
  function newRequestId() {
76565
- return randomUUID5();
76793
+ return randomUUID6();
76566
76794
  }
76567
76795
 
76568
76796
  class EndLine {
@@ -76890,7 +77118,7 @@ var init_response_seam = __esm(() => {
76890
77118
  });
76891
77119
 
76892
77120
  // src/services/pricing-cache.ts
76893
- import { existsSync as existsSync28, readFileSync as readFileSync28, statSync as statSync9 } from "fs";
77121
+ import { existsSync as existsSync28, readFileSync as readFileSync29, statSync as statSync10 } from "fs";
76894
77122
  import { homedir as homedir35 } from "os";
76895
77123
  import { join as join38 } from "path";
76896
77124
  function prefixMatch(modelName) {
@@ -76932,10 +77160,10 @@ function loadDiskCache() {
76932
77160
  try {
76933
77161
  if (!existsSync28(CACHE_FILE))
76934
77162
  return false;
76935
- const stat = statSync9(CACHE_FILE);
77163
+ const stat = statSync10(CACHE_FILE);
76936
77164
  const age = Date.now() - stat.mtimeMs;
76937
77165
  const isFresh = age < CACHE_TTL_MS5;
76938
- const raw = readFileSync28(CACHE_FILE, "utf-8");
77166
+ const raw = readFileSync29(CACHE_FILE, "utf-8");
76939
77167
  const data = JSON.parse(raw);
76940
77168
  for (const [key, pricing] of Object.entries(data)) {
76941
77169
  pricingMap.set(key, pricing);
@@ -76958,7 +77186,7 @@ var init_pricing_cache = __esm(() => {
76958
77186
  });
76959
77187
 
76960
77188
  // src/proxy-server.ts
76961
- import { appendFileSync as appendFileSync6, mkdirSync as mkdirSync19 } from "fs";
77189
+ import { appendFileSync as appendFileSync6, mkdirSync as mkdirSync18 } from "fs";
76962
77190
  import { join as join39 } from "path";
76963
77191
  function isTerminalRoutingFailure(e) {
76964
77192
  return e instanceof RoutingError;
@@ -76969,7 +77197,7 @@ function maybeCaptureClassifierRequest(c, body) {
76969
77197
  try {
76970
77198
  const dir = join39(process.cwd(), "logs");
76971
77199
  if (!classifierCaptureDirReady) {
76972
- mkdirSync19(dir, { recursive: true });
77200
+ mkdirSync18(dir, { recursive: true });
76973
77201
  classifierCaptureDirReady = true;
76974
77202
  }
76975
77203
  const record = {
@@ -77481,10 +77709,10 @@ var init_proxy_server = __esm(() => {
77481
77709
  import {
77482
77710
  copyFileSync as copyFileSync2,
77483
77711
  existsSync as existsSync29,
77484
- mkdirSync as mkdirSync20,
77485
- readFileSync as readFileSync29,
77712
+ mkdirSync as mkdirSync19,
77713
+ readFileSync as readFileSync30,
77486
77714
  readdirSync as readdirSync3,
77487
- unlinkSync as unlinkSync8
77715
+ unlinkSync as unlinkSync9
77488
77716
  } from "fs";
77489
77717
  import { homedir as homedir36 } from "os";
77490
77718
  import { dirname as dirname14, join as join40 } from "path";
@@ -77502,7 +77730,7 @@ function clearAllModelCaches() {
77502
77730
  const files = readdirSync3(cacheDir);
77503
77731
  for (const file of files) {
77504
77732
  if (cachePatterns.includes(file)) {
77505
- unlinkSync8(join40(cacheDir, file));
77733
+ unlinkSync9(join40(cacheDir, file));
77506
77734
  cleared++;
77507
77735
  }
77508
77736
  }
@@ -79003,7 +79231,7 @@ ${h("MORE INFO")}
79003
79231
  function printAIAgentGuide() {
79004
79232
  try {
79005
79233
  const guidePath = join40(__dirname2, "../AI_AGENT_GUIDE.md");
79006
- const guideContent = readFileSync29(guidePath, "utf-8");
79234
+ const guideContent = readFileSync30(guidePath, "utf-8");
79007
79235
  console.log(guideContent);
79008
79236
  } catch (error) {
79009
79237
  console.error("Error reading AI Agent Guide:");
@@ -79041,15 +79269,15 @@ async function initializeClaudishSkill() {
79041
79269
  }
79042
79270
  try {
79043
79271
  if (!existsSync29(claudeDir)) {
79044
- mkdirSync20(claudeDir, { recursive: true });
79272
+ mkdirSync19(claudeDir, { recursive: true });
79045
79273
  console.log("\uD83D\uDCC1 Created .claude/ directory");
79046
79274
  }
79047
79275
  if (!existsSync29(skillsDir)) {
79048
- mkdirSync20(skillsDir, { recursive: true });
79276
+ mkdirSync19(skillsDir, { recursive: true });
79049
79277
  console.log("\uD83D\uDCC1 Created .claude/skills/ directory");
79050
79278
  }
79051
79279
  if (!existsSync29(claudishSkillDir)) {
79052
- mkdirSync20(claudishSkillDir, { recursive: true });
79280
+ mkdirSync19(claudishSkillDir, { recursive: true });
79053
79281
  console.log("\uD83D\uDCC1 Created .claude/skills/claudish-usage/ directory");
79054
79282
  }
79055
79283
  copyFileSync2(sourceSkillPath, skillFile);
@@ -79273,11 +79501,11 @@ import {
79273
79501
  chmodSync as chmodSync2,
79274
79502
  closeSync as closeSync8,
79275
79503
  existsSync as existsSync31,
79276
- mkdirSync as mkdirSync21,
79504
+ mkdirSync as mkdirSync20,
79277
79505
  mkdtempSync,
79278
79506
  openSync as openSync8,
79279
79507
  rmSync as rmSync5,
79280
- writeFileSync as writeFileSync18
79508
+ writeFileSync as writeFileSync17
79281
79509
  } from "fs";
79282
79510
  import { connect as netConnect } from "net";
79283
79511
  import { join as join42 } from "path";
@@ -79345,7 +79573,7 @@ function planMagmuxWrap(input) {
79345
79573
  const id = `claudish-${pid}`;
79346
79574
  const controlSocket = `/tmp/magmux-${id}.sock`;
79347
79575
  const tmpRoot = input.tmpRoot ?? "/tmp";
79348
- mkdirSync21(tmpRoot, { recursive: true });
79576
+ mkdirSync20(tmpRoot, { recursive: true });
79349
79577
  const scriptDir = mkdtempSync(join42(tmpRoot, "claudish-launch-"));
79350
79578
  chmodSync2(scriptDir, 448);
79351
79579
  const scriptPath = join42(scriptDir, "claude-launch.sh");
@@ -79353,7 +79581,7 @@ function planMagmuxWrap(input) {
79353
79581
  const deltas = envDeltas(parentEnv, input.childEnv);
79354
79582
  const fd = openSync8(scriptPath, "wx", 384);
79355
79583
  try {
79356
- writeFileSync18(fd, buildLauncherScript(input.claudeBinary, input.claudeArgs, deltas));
79584
+ writeFileSync17(fd, buildLauncherScript(input.claudeBinary, input.claudeArgs, deltas));
79357
79585
  } finally {
79358
79586
  closeSync8(fd);
79359
79587
  }
@@ -79829,7 +80057,7 @@ var init_process_identity = __esm(() => {
79829
80057
  // src/pane/pane-launch.ts
79830
80058
  import { execFile as execFile3, spawn } from "child_process";
79831
80059
  import { randomBytes as randomBytes8 } from "crypto";
79832
- import { chmodSync as chmodSync3, lstatSync as lstatSync2, mkdirSync as mkdirSync22, mkdtempSync as mkdtempSync2, writeFileSync as writeFileSync19 } from "fs";
80060
+ import { chmodSync as chmodSync3, lstatSync as lstatSync2, mkdirSync as mkdirSync21, mkdtempSync as mkdtempSync2, writeFileSync as writeFileSync18 } from "fs";
79833
80061
  import { join as join44, resolve as resolve3 } from "path";
79834
80062
  function uid() {
79835
80063
  return typeof process.getuid === "function" ? process.getuid() : 0;
@@ -79850,17 +80078,17 @@ function assertPrivateDir(p) {
79850
80078
  function ensureSockRoot(given = sockRootFor()) {
79851
80079
  const root = resolve3(given);
79852
80080
  try {
79853
- mkdirSync22(root, { mode: 448 });
80081
+ mkdirSync21(root, { mode: 448 });
79854
80082
  } catch (e) {
79855
80083
  if (e.code === "ENOENT")
79856
- mkdirSync22(root, { recursive: true, mode: 448 });
80084
+ mkdirSync21(root, { recursive: true, mode: 448 });
79857
80085
  else if (e.code !== "EEXIST")
79858
80086
  throw e;
79859
80087
  }
79860
80088
  assertPrivateDir(root);
79861
80089
  const panes = join44(root, "panes");
79862
80090
  try {
79863
- mkdirSync22(panes, { mode: 448 });
80091
+ mkdirSync21(panes, { mode: 448 });
79864
80092
  } catch (e) {
79865
80093
  if (e.code !== "EEXIST")
79866
80094
  throw e;
@@ -79941,6 +80169,18 @@ function reservedMessage(flag) {
79941
80169
  return `${flag} would start a different claudish mode inside the pane`;
79942
80170
  return null;
79943
80171
  }
80172
+ function requestedAgentOf(flags) {
80173
+ let agent = null;
80174
+ for (let i = 0;i < flags.length; i++) {
80175
+ const [name, inline] = splitFlag(flags[i]);
80176
+ if (name !== "--agent")
80177
+ continue;
80178
+ const value = inline ?? flags[i + 1];
80179
+ if (value && !value.startsWith("-"))
80180
+ agent = value;
80181
+ }
80182
+ return agent;
80183
+ }
79944
80184
  function flagsRemoveRead(flags) {
79945
80185
  for (let i = 0;i < flags.length; i++) {
79946
80186
  const [name, inline] = splitFlag(flags[i]);
@@ -80122,8 +80362,8 @@ function createLaunchDirs(root) {
80122
80362
  return { ctlDir, turnDir };
80123
80363
  }
80124
80364
  function writeLauncherFiles(ctlDir, script) {
80125
- writeFileSync19(join44(ctlDir, "pane-launch.sh"), script, { mode: 384, flag: "wx" });
80126
- writeFileSync19(join44(ctlDir, "sh-shim"), SHELL_SHIM, { mode: 448, flag: "wx" });
80365
+ writeFileSync18(join44(ctlDir, "pane-launch.sh"), script, { mode: 384, flag: "wx" });
80366
+ writeFileSync18(join44(ctlDir, "sh-shim"), SHELL_SHIM, { mode: 448, flag: "wx" });
80127
80367
  }
80128
80368
  function spawnPaneWatcher(args) {
80129
80369
  const proc = spawn("/bin/sh", watcherArgv(args), {
@@ -80527,12 +80767,12 @@ import {
80527
80767
  accessSync,
80528
80768
  existsSync as existsSync32,
80529
80769
  lstatSync as lstatSync3,
80530
- readFileSync as readFileSync30,
80770
+ readFileSync as readFileSync31,
80531
80771
  readdirSync as readdirSync4,
80532
- renameSync as renameSync5,
80772
+ renameSync as renameSync6,
80533
80773
  rmSync as rmSync6,
80534
- unlinkSync as unlinkSync9,
80535
- writeFileSync as writeFileSync20
80774
+ unlinkSync as unlinkSync10,
80775
+ writeFileSync as writeFileSync19
80536
80776
  } from "fs";
80537
80777
  import { join as join45 } from "path";
80538
80778
  function ownerStartOfSelf() {
@@ -80560,15 +80800,15 @@ function recordsDir(root) {
80560
80800
  function writeRecord(root, rec) {
80561
80801
  const p = recordPathOf(root, rec.paneId);
80562
80802
  const tmp = `${p}.tmp-${process.pid}`;
80563
- writeFileSync20(tmp, `${JSON.stringify(rec)}
80803
+ writeFileSync19(tmp, `${JSON.stringify(rec)}
80564
80804
  `, { mode: 384 });
80565
- renameSync5(tmp, p);
80805
+ renameSync6(tmp, p);
80566
80806
  }
80567
80807
  function readRecord(root, paneId) {
80568
80808
  if (!isValidPaneId(paneId))
80569
80809
  return null;
80570
80810
  try {
80571
- return validRecord(JSON.parse(readFileSync30(recordPathOf(root, paneId), "utf8")), paneId);
80811
+ return validRecord(JSON.parse(readFileSync31(recordPathOf(root, paneId), "utf8")), paneId);
80572
80812
  } catch {
80573
80813
  return null;
80574
80814
  }
@@ -80580,7 +80820,7 @@ function updateRecord(root, paneId, patch) {
80580
80820
  }
80581
80821
  function deleteRecord(root, paneId) {
80582
80822
  try {
80583
- unlinkSync9(recordPathOf(root, paneId));
80823
+ unlinkSync10(recordPathOf(root, paneId));
80584
80824
  } catch {}
80585
80825
  }
80586
80826
  function validRecord(v, stem) {
@@ -80625,7 +80865,7 @@ function readRecords(root) {
80625
80865
  }
80626
80866
  function readGroupFile(ctlDir) {
80627
80867
  try {
80628
- return parseGroupFile(readFileSync30(join45(ctlDir, "group"), "utf8"));
80868
+ return parseGroupFile(readFileSync31(join45(ctlDir, "group"), "utf8"));
80629
80869
  } catch {
80630
80870
  return null;
80631
80871
  }
@@ -80634,8 +80874,8 @@ function writeGroupFile(ctlDir, snap) {
80634
80874
  const p = join45(ctlDir, "group");
80635
80875
  const tmp = `${p}.tmp`;
80636
80876
  try {
80637
- writeFileSync20(tmp, formatGroupFile(snap), { mode: 384 });
80638
- renameSync5(tmp, p);
80877
+ writeFileSync19(tmp, formatGroupFile(snap), { mode: 384 });
80878
+ renameSync6(tmp, p);
80639
80879
  } catch {}
80640
80880
  }
80641
80881
  function removePaneFiles(root, f) {
@@ -81844,7 +82084,7 @@ var init_screen_classifier = __esm(() => {
81844
82084
  });
81845
82085
 
81846
82086
  // src/pane/session-registry.ts
81847
- import { readFileSync as readFileSync31, readdirSync as readdirSync5 } from "fs";
82087
+ import { readFileSync as readFileSync32, readdirSync as readdirSync5 } from "fs";
81848
82088
  import { join as join48 } from "path";
81849
82089
  function parseRegistryRecord(raw) {
81850
82090
  let parsed;
@@ -81926,7 +82166,7 @@ class SessionRegistry {
81926
82166
  readPid(pid) {
81927
82167
  let raw;
81928
82168
  try {
81929
- raw = readFileSync31(join48(this.dir, `${pid}.json`), "utf8");
82169
+ raw = readFileSync32(join48(this.dir, `${pid}.json`), "utf8");
81930
82170
  } catch {
81931
82171
  return null;
81932
82172
  }
@@ -82229,7 +82469,7 @@ import {
82229
82469
  readSync as readSync4,
82230
82470
  readdirSync as readdirSync6,
82231
82471
  realpathSync as realpathSync3,
82232
- statSync as statSync10
82472
+ statSync as statSync11
82233
82473
  } from "fs";
82234
82474
  import { join as join49 } from "path";
82235
82475
  function initialFollowerState(resolvePath = safeRealpath) {
@@ -82240,6 +82480,7 @@ function initialFollowerState(resolvePath = safeRealpath) {
82240
82480
  mainAssistantIds: [],
82241
82481
  mainAssistantSeen: new Set,
82242
82482
  session: { stopHooksSeen: false, provenHookless: false },
82483
+ agentSetting: null,
82243
82484
  records: 0,
82244
82485
  resolvePath
82245
82486
  };
@@ -82564,6 +82805,8 @@ function applyRecord(state, record, offset) {
82564
82805
  if (r.isSidechain)
82565
82806
  return state;
82566
82807
  noteMainAssistant(state, r);
82808
+ if (r.type === "agent-setting" && typeof r.agentSetting === "string" && r.agentSetting)
82809
+ state.agentSetting = r.agentSetting;
82567
82810
  if (r.type === "system" && r.subtype === "stop_hook_summary") {
82568
82811
  state.session.stopHooksSeen = true;
82569
82812
  state.session.provenHookless = false;
@@ -82846,7 +83089,8 @@ class TranscriptFollower {
82846
83089
  usage: { tokensIn, tokensOut },
82847
83090
  toolCalls: this.state.toolUseIds.size,
82848
83091
  lastAppendAt: this.lastAppend,
82849
- session: { ...this.state.session }
83092
+ session: { ...this.state.session },
83093
+ agentSetting: this.state.agentSetting
82850
83094
  };
82851
83095
  }
82852
83096
  }
@@ -82862,7 +83106,7 @@ function lastHumanPromptOffset(path) {
82862
83106
  }
82863
83107
  function fileSize(p) {
82864
83108
  try {
82865
- return statSync10(p).size;
83109
+ return statSync11(p).size;
82866
83110
  } catch {
82867
83111
  return 0;
82868
83112
  }
@@ -82886,7 +83130,7 @@ var init_transcript_follower = __esm(() => {
82886
83130
  });
82887
83131
 
82888
83132
  // src/pane/pane-session.ts
82889
- import { readFileSync as readFileSync32, realpathSync as realpathSync4, rmSync as rmSync7, statSync as statSync11, writeFileSync as writeFileSync21 } from "fs";
83133
+ import { readFileSync as readFileSync33, realpathSync as realpathSync4, rmSync as rmSync7, statSync as statSync12, writeFileSync as writeFileSync20 } from "fs";
82890
83134
  import { join as join50 } from "path";
82891
83135
  function iso(ms) {
82892
83136
  return new Date(ms).toISOString();
@@ -83082,7 +83326,7 @@ class PaneSessionImpl {
83082
83326
  return this.spawnFailed(new Error("magmux did not start"));
83083
83327
  this.magmux = proc;
83084
83328
  try {
83085
- writeFileSync21(join50(this.ctlDir, "magmux.pid"), `${proc.pid}
83329
+ writeFileSync20(join50(this.ctlDir, "magmux.pid"), `${proc.pid}
83086
83330
  `, { mode: 384 });
83087
83331
  } catch {}
83088
83332
  updateRecord(this.root, this.paneId, { magmuxPid: proc.pid });
@@ -84800,7 +85044,7 @@ ${screenTailOf(this.screen)}`
84800
85044
  if (!p)
84801
85045
  return 0;
84802
85046
  try {
84803
- return statSync11(p).size;
85047
+ return statSync12(p).size;
84804
85048
  } catch {
84805
85049
  return 0;
84806
85050
  }
@@ -84809,7 +85053,7 @@ ${screenTailOf(this.screen)}`
84809
85053
  const p = this.errorLogPath();
84810
85054
  if (p && this.errorLogSize() > st.errorLogSize) {
84811
85055
  try {
84812
- const text = readFileSync32(p, "utf8").slice(st.errorLogSize).trim();
85056
+ const text = readFileSync33(p, "utf8").slice(st.errorLogSize).trim();
84813
85057
  return { status: null, category: "upstream_error_log", text };
84814
85058
  } catch {}
84815
85059
  }
@@ -84920,7 +85164,8 @@ ${screenTailOf(this.screen)}`
84920
85164
  shape: this.shape,
84921
85165
  turnEndRecordMissing: !terminal && this.phase === "RUNNING" && this.activity === "finishing" && this.turnEndMissing,
84922
85166
  agentCountMismatch: !terminal && this.phase === "RUNNING" && this.agentMismatch !== null,
84923
- recent: cur && cur.recent.length > 0 ? cur.recent : null
85167
+ recent: cur && cur.recent.length > 0 ? cur.recent : null,
85168
+ agent: view.agentSetting
84924
85169
  };
84925
85170
  }
84926
85171
  phaseActivity() {
@@ -85606,7 +85851,7 @@ __export(exports_session_discovery, {
85606
85851
  transcriptPathFor: () => transcriptPathFor
85607
85852
  });
85608
85853
  import { execFile as execFile4, execFileSync as execFileSync3 } from "child_process";
85609
- import { closeSync as closeSync10, openSync as openSync10, readSync as readSync5, readdirSync as readdirSync7, realpathSync as realpathSync5, statSync as statSync12 } from "fs";
85854
+ import { closeSync as closeSync10, openSync as openSync10, readSync as readSync5, readdirSync as readdirSync7, realpathSync as realpathSync5, statSync as statSync13 } from "fs";
85610
85855
  import { basename as basename4, join as join51 } from "path";
85611
85856
  function projectsDir(env = process.env) {
85612
85857
  return join51(claudeConfigDir(env), "projects");
@@ -85677,7 +85922,7 @@ function sessionsIn(dirName) {
85677
85922
  for (const n of names) {
85678
85923
  const file = join51(dir, n);
85679
85924
  try {
85680
- const st = statSync12(file);
85925
+ const st = statSync13(file);
85681
85926
  if (st.size === 0)
85682
85927
  continue;
85683
85928
  const row = {
@@ -85838,7 +86083,7 @@ function discoverWorktreeGroups(repo) {
85838
86083
  g.activeNow = g.sessions.some((s) => isActive(s));
85839
86084
  if (g.path) {
85840
86085
  try {
85841
- g.createdMs = statSync12(g.path).birthtimeMs;
86086
+ g.createdMs = statSync13(g.path).birthtimeMs;
85842
86087
  } catch {}
85843
86088
  }
85844
86089
  if (!g.createdMs && g.sessions.length > 0) {
@@ -85926,7 +86171,7 @@ function hydrateSession(row) {
85926
86171
  row.hydrated = true;
85927
86172
  if (isActive(row)) {
85928
86173
  try {
85929
- row.sizeBytes = statSync12(row.file).size;
86174
+ row.sizeBytes = statSync13(row.file).size;
85930
86175
  } catch {}
85931
86176
  }
85932
86177
  const head = parseRecords(readChunk(row.file, 0, Math.min(HEAD_BYTES, row.sizeBytes)), false);
@@ -86051,17 +86296,17 @@ var init_session_discovery = __esm(() => {
86051
86296
  });
86052
86297
 
86053
86298
  // src/team-orchestrator.ts
86054
- import { randomBytes as randomBytes9, randomUUID as randomUUID6 } from "crypto";
86299
+ import { randomBytes as randomBytes9, randomUUID as randomUUID7 } from "crypto";
86055
86300
  import {
86056
86301
  existsSync as existsSync34,
86057
86302
  lstatSync as lstatSync4,
86058
- mkdirSync as mkdirSync23,
86059
- readFileSync as readFileSync33,
86303
+ mkdirSync as mkdirSync22,
86304
+ readFileSync as readFileSync34,
86060
86305
  readdirSync as readdirSync8,
86061
86306
  realpathSync as realpathSync6,
86062
86307
  rmSync as rmSync8,
86063
- statSync as statSync13,
86064
- writeFileSync as writeFileSync22
86308
+ statSync as statSync14,
86309
+ writeFileSync as writeFileSync21
86065
86310
  } from "fs";
86066
86311
  import { basename as basename5, dirname as dirname18, join as join52, resolve as resolve5, sep } from "path";
86067
86312
  function slotTerminal(e) {
@@ -86155,14 +86400,16 @@ function neverSpawnedRow(e, m) {
86155
86400
  idle_seconds: null,
86156
86401
  activity: null,
86157
86402
  pane: null,
86158
- recent: null
86403
+ recent: null,
86404
+ agent_requested: e.agentRequested,
86405
+ agent: null
86159
86406
  };
86160
86407
  }
86161
86408
  function liveSlotRow(run, e) {
86162
86409
  if (!e.session)
86163
86410
  return neverSpawnedRow(e, run.status.models[e.id]);
86164
86411
  const snap = e.session.snapshot();
86165
- return toSlotRow({ slot: e.id, model: e.model, spawnModel: e.spawnModel }, snap, refreshAccounting(e, snap), Date.now(), upstreamRecordsFor(snap, upstreamLogPath(run.path, e.id)));
86412
+ return toSlotRow({ slot: e.id, model: e.model, spawnModel: e.spawnModel, agentRequested: e.agentRequested }, snap, refreshAccounting(e, snap), Date.now(), upstreamRecordsFor(snap, upstreamLogPath(run.path, e.id)));
86166
86413
  }
86167
86414
  function outcomeOf(states) {
86168
86415
  const ok = states.filter((s) => s === "COMPLETED").length;
@@ -86219,7 +86466,9 @@ function teamRunRowFromDisk(path, status) {
86219
86466
  idle_seconds: null,
86220
86467
  activity: null,
86221
86468
  pane: m?.pane ?? null,
86222
- recent: null
86469
+ recent: null,
86470
+ agent_requested: m?.agentRequested ?? null,
86471
+ agent: m?.agent ?? null
86223
86472
  };
86224
86473
  });
86225
86474
  const settled = slots.length > 0 && slots.every((s) => isTerminalState(s.state));
@@ -86237,14 +86486,14 @@ function teamRunRowFromDisk(path, status) {
86237
86486
  }
86238
86487
  function statusMtimeMs(path) {
86239
86488
  try {
86240
- return statSync13(join52(path, "status.json")).mtimeMs;
86489
+ return statSync14(join52(path, "status.json")).mtimeMs;
86241
86490
  } catch {
86242
86491
  return null;
86243
86492
  }
86244
86493
  }
86245
86494
  function readManifestOrNull(path) {
86246
86495
  try {
86247
- return JSON.parse(readFileSync33(join52(path, "manifest.json"), "utf-8"));
86496
+ return JSON.parse(readFileSync34(join52(path, "manifest.json"), "utf-8"));
86248
86497
  } catch {
86249
86498
  return null;
86250
86499
  }
@@ -86446,7 +86695,7 @@ function persistErrorLog(errorLogPath, header, sections) {
86446
86695
  parts.push(`--- ${title} ---`, body.trim() ? redactSecrets(body) : "(empty)", "");
86447
86696
  }
86448
86697
  try {
86449
- writeFileSync22(errorLogPath, parts.join(`
86698
+ writeFileSync21(errorLogPath, parts.join(`
86450
86699
  `), "utf-8");
86451
86700
  } catch {}
86452
86701
  }
@@ -86488,7 +86737,7 @@ function readTeamInputFile(inputPath) {
86488
86737
  if (!existsSync34(resolved)) {
86489
86738
  throw new Error(`Input file not found: ${resolved}`);
86490
86739
  }
86491
- const text = readFileSync33(resolved, "utf-8");
86740
+ const text = readFileSync34(resolved, "utf-8");
86492
86741
  if (text.trim().length === 0) {
86493
86742
  throw new Error(`Input file is empty: ${resolved}`);
86494
86743
  }
@@ -86501,10 +86750,10 @@ function setupSession(sessionPath, models, input) {
86501
86750
  if (existsSync34(join52(sessionPath, "manifest.json"))) {
86502
86751
  throw new Error(`Session already exists at ${sessionPath}. Use a new directory path or delete the existing session first.`);
86503
86752
  }
86504
- mkdirSync23(join52(sessionPath, "work"), { recursive: true });
86505
- mkdirSync23(join52(sessionPath, "errors"), { recursive: true });
86753
+ mkdirSync22(join52(sessionPath, "work"), { recursive: true });
86754
+ mkdirSync22(join52(sessionPath, "errors"), { recursive: true });
86506
86755
  if (input !== undefined) {
86507
- writeFileSync22(join52(sessionPath, "input.md"), input, "utf-8");
86756
+ writeFileSync21(join52(sessionPath, "input.md"), input, "utf-8");
86508
86757
  } else if (!existsSync34(join52(sessionPath, "input.md"))) {
86509
86758
  throw new Error(`No input.md found at ${sessionPath} and no input provided`);
86510
86759
  }
@@ -86522,9 +86771,9 @@ function setupSession(sessionPath, models, input) {
86522
86771
  model: models[i],
86523
86772
  assignedAt: now
86524
86773
  };
86525
- mkdirSync23(join52(sessionPath, "work", anonId), { recursive: true });
86774
+ mkdirSync22(join52(sessionPath, "work", anonId), { recursive: true });
86526
86775
  }
86527
- writeFileSync22(join52(sessionPath, "manifest.json"), JSON.stringify(manifest, null, 2), "utf-8");
86776
+ writeFileSync21(join52(sessionPath, "manifest.json"), JSON.stringify(manifest, null, 2), "utf-8");
86528
86777
  const status = {
86529
86778
  startedAt: now,
86530
86779
  models: Object.fromEntries(Object.keys(manifest.models).map((id) => [
@@ -86539,7 +86788,7 @@ function setupSession(sessionPath, models, input) {
86539
86788
  }
86540
86789
  ]))
86541
86790
  };
86542
- writeFileSync22(join52(sessionPath, "status.json"), JSON.stringify(status, null, 2), "utf-8");
86791
+ writeFileAtomic(join52(sessionPath, "status.json"), JSON.stringify(status, null, 2));
86543
86792
  return manifest;
86544
86793
  }
86545
86794
  function assertValidRequirePattern(pattern) {
@@ -86598,10 +86847,11 @@ async function startModelsIn(flight, sessionPath, opts) {
86598
86847
  const flagCheck = checkChildFlags(claudeFlags);
86599
86848
  if (!flagCheck.ok)
86600
86849
  throw new Error(`invalid_args: ${flagCheck.message}`);
86850
+ const agentRequested = requestedAgentOf(claudeFlags);
86601
86851
  const path = resolve5(sessionPath);
86602
- const manifest = JSON.parse(readFileSync33(join52(path, "manifest.json"), "utf-8"));
86852
+ const manifest = JSON.parse(readFileSync34(join52(path, "manifest.json"), "utf-8"));
86603
86853
  const statusPath = join52(path, "status.json");
86604
- const inputContent = readFileSync33(join52(path, "input.md"), "utf-8");
86854
+ const inputContent = readFileSync34(join52(path, "input.md"), "utf-8");
86605
86855
  const readAvailable = !flagsRemoveRead(claudeFlags);
86606
86856
  const refusal = deliveryRefusal(inputContent, readAvailable);
86607
86857
  if (refusal)
@@ -86612,7 +86862,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86612
86862
  const hookEngine = await (opts.hookEngine ?? (() => loadHooksOnce()))().catch(() => null);
86613
86863
  const spawnPlan = await (opts.spawnPlanner ?? prehydrateCredentialsForSpawn)(Object.values(manifest.models).map((m) => m.model));
86614
86864
  await assertMagmuxAvailable();
86615
- const statusCache = JSON.parse(readFileSync33(statusPath, "utf-8"));
86865
+ const statusCache = JSON.parse(readFileSync34(statusPath, "utf-8"));
86616
86866
  const startMs = Date.now();
86617
86867
  const runId = mintRunId(path, startMs);
86618
86868
  statusCache.runId = runId;
@@ -86622,7 +86872,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86622
86872
  statusCache.models[id] = { ...statusCache.models[id], ...update };
86623
86873
  }
86624
86874
  function flushStatus() {
86625
- writeFileSync22(statusPath, JSON.stringify(statusCache, null, 2), "utf-8");
86875
+ writeFileAtomic(statusPath, JSON.stringify(statusCache, null, 2));
86626
86876
  }
86627
86877
  function updateModelStatus(id, update) {
86628
86878
  if (aborting)
@@ -86637,16 +86887,20 @@ async function startModelsIn(flight, sessionPath, opts) {
86637
86887
  }
86638
86888
  const minOutputBytes = opts.minOutputBytes ?? DEFAULT_MIN_OUTPUT_BYTES;
86639
86889
  const requirePattern = opts.requirePattern;
86640
- mkdirSync23(statsDir(path), { recursive: true });
86890
+ mkdirSync22(statsDir(path), { recursive: true });
86641
86891
  const entries = new Map;
86642
86892
  let run = null;
86643
86893
  const errorLogPathOf = (id) => join52(path, "errors", `${id}.log`);
86644
86894
  const upstreamLogOf = (id) => upstreamLogPath(path, id);
86645
- const commandOf = (e) => ["claudish", "-i", "--model", e.spawnModel ?? e.model, "-y", "--quiet", ...claudeFlags].join(" ");
86895
+ const flagsOf = (e) => {
86896
+ const effort = opts.efforts?.[e.model];
86897
+ return effort ? [...claudeFlags, "--effort-override", effort] : claudeFlags;
86898
+ };
86899
+ const commandOf = (e) => ["claudish", "-i", "--model", e.spawnModel ?? e.model, "-y", "--quiet", ...flagsOf(e)].join(" ");
86646
86900
  function writeResponse(e, text) {
86647
86901
  e.answer = text;
86648
86902
  try {
86649
- writeFileSync22(join52(path, `response-${e.id}.md`), text, "utf-8");
86903
+ writeFileSync21(join52(path, `response-${e.id}.md`), text, "utf-8");
86650
86904
  } catch (err) {
86651
86905
  persistErrorLog(errorLogPathOf(e.id), `response file not written: ${String(err)}`, []);
86652
86906
  }
@@ -86656,7 +86910,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86656
86910
  if (e.answer !== null || !e.session)
86657
86911
  return;
86658
86912
  try {
86659
- writeFileSync22(join52(path, `response-${e.id}.md`), e.session.chainText(), "utf-8");
86913
+ writeFileSync21(join52(path, `response-${e.id}.md`), e.session.chainText(), "utf-8");
86660
86914
  } catch (err) {
86661
86915
  persistErrorLog(errorLogPathOf(e.id), `response file not written: ${String(err)}`, []);
86662
86916
  }
@@ -86710,6 +86964,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86710
86964
  lastActivityAt: snap.lastActivityAt,
86711
86965
  turnsCompleted: snap.turnsCompleted,
86712
86966
  claudeCodeVersion: snap.claudeCodeVersion,
86967
+ agent: snap.agent ?? null,
86713
86968
  anomalies: notableAnomalies(snap),
86714
86969
  ...accountingFields(refreshAccounting(e, snap))
86715
86970
  };
@@ -86819,7 +87074,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86819
87074
  session = await startPaneSession({
86820
87075
  kind: "t",
86821
87076
  label: e.id,
86822
- callerFlags: claudeFlags,
87077
+ callerFlags: flagsOf(e),
86823
87078
  spawnModel: e.spawnModel ?? e.model,
86824
87079
  cwd,
86825
87080
  sessionUuid: uuid,
@@ -86881,6 +87136,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86881
87136
  id,
86882
87137
  model: entry.model,
86883
87138
  spawnModel,
87139
+ agentRequested,
86884
87140
  tokenFile,
86885
87141
  session: null,
86886
87142
  acct: emptyAccounting(provider),
@@ -86888,7 +87144,7 @@ async function startModelsIn(flight, sessionPath, opts) {
86888
87144
  stopReason: null
86889
87145
  };
86890
87146
  entries.set(id, e);
86891
- const uuid = randomUUID6();
87147
+ const uuid = randomUUID7();
86892
87148
  const transcriptPath = transcriptPathFor(cwd, uuid, projects);
86893
87149
  updateModelStatus(id, {
86894
87150
  state: "STARTING",
@@ -86899,6 +87155,8 @@ async function startModelsIn(flight, sessionPath, opts) {
86899
87155
  model: entry.model,
86900
87156
  spawnModel,
86901
87157
  provider,
87158
+ agentRequested,
87159
+ agent: null,
86902
87160
  sessionUuid: uuid,
86903
87161
  transcriptPath,
86904
87162
  pane: null,
@@ -87013,12 +87271,14 @@ async function startModelsIn(flight, sessionPath, opts) {
87013
87271
  emitProgress("settled");
87014
87272
  try {
87015
87273
  opts.onSettled?.(statusCache);
87016
- } catch {}
87274
+ } catch (err) {
87275
+ log(`[team] onSettled failed for ${path}: ${err instanceof Error ? err.message : String(err)}`);
87276
+ }
87017
87277
  resolveSettled();
87018
87278
  }
87019
87279
  return statusCache;
87020
87280
  })();
87021
- done.catch(() => {});
87281
+ done.catch((err) => log(`[team] run failed at ${path}: ${err instanceof Error ? err.message : String(err)}`));
87022
87282
  return {
87023
87283
  runId,
87024
87284
  teamSessionId: basename5(path),
@@ -87042,14 +87302,14 @@ async function judgeResponses(sessionPath, opts = {}) {
87042
87302
  const responses = {};
87043
87303
  for (const file of responseFiles) {
87044
87304
  const id = file.replace(/^response-/, "").replace(/\.md$/, "");
87045
- responses[id] = readFileSync33(join52(sessionPath, file), "utf-8");
87305
+ responses[id] = readFileSync34(join52(sessionPath, file), "utf-8");
87046
87306
  }
87047
- const input = readFileSync33(join52(sessionPath, "input.md"), "utf-8");
87307
+ const input = readFileSync34(join52(sessionPath, "input.md"), "utf-8");
87048
87308
  const judgePrompt = buildJudgePrompt(input, responses);
87049
- writeFileSync22(join52(sessionPath, "judge-prompt.md"), judgePrompt, "utf-8");
87309
+ writeFileSync21(join52(sessionPath, "judge-prompt.md"), judgePrompt, "utf-8");
87050
87310
  const judgeModels = opts.judges ?? getDefaultJudgeModels(sessionPath);
87051
87311
  const judgePath = join52(sessionPath, "judging");
87052
- mkdirSync23(judgePath, { recursive: true });
87312
+ mkdirSync22(judgePath, { recursive: true });
87053
87313
  setupSession(judgePath, judgeModels, judgePrompt);
87054
87314
  await runModels(judgePath, {
87055
87315
  claudeFlags: opts.claudeFlags,
@@ -87059,11 +87319,11 @@ async function judgeResponses(sessionPath, opts = {}) {
87059
87319
  });
87060
87320
  const votes = parseJudgeVotes(judgePath, Object.keys(responses));
87061
87321
  const verdict = aggregateVerdict(votes, Object.keys(responses));
87062
- writeFileSync22(join52(sessionPath, "verdict.md"), formatVerdict(verdict, sessionPath), "utf-8");
87322
+ writeFileSync21(join52(sessionPath, "verdict.md"), formatVerdict(verdict, sessionPath), "utf-8");
87063
87323
  return verdict;
87064
87324
  }
87065
87325
  function getStatus(sessionPath) {
87066
- return JSON.parse(readFileSync33(join52(sessionPath, "status.json"), "utf-8"));
87326
+ return JSON.parse(readFileSync34(join52(sessionPath, "status.json"), "utf-8"));
87067
87327
  }
87068
87328
  function readTeamStatus(sessionPath) {
87069
87329
  try {
@@ -87071,7 +87331,11 @@ function readTeamStatus(sessionPath) {
87071
87331
  if (parsed && typeof parsed === "object" && parsed.models && typeof parsed.models === "object") {
87072
87332
  return parsed;
87073
87333
  }
87074
- } catch {}
87334
+ } catch (err) {
87335
+ if (err?.code !== "ENOENT") {
87336
+ log(`[team] unreadable status.json at ${sessionPath}: ${err instanceof Error ? err.message : String(err)}`);
87337
+ }
87338
+ }
87075
87339
  return { startedAt: new Date().toISOString(), models: {} };
87076
87340
  }
87077
87341
  function summarise(status) {
@@ -87099,7 +87363,7 @@ function fisherYatesShuffle(arr) {
87099
87363
  return arr;
87100
87364
  }
87101
87365
  function getDefaultJudgeModels(sessionPath) {
87102
- const manifest = JSON.parse(readFileSync33(join52(sessionPath, "manifest.json"), "utf-8"));
87366
+ const manifest = JSON.parse(readFileSync34(join52(sessionPath, "manifest.json"), "utf-8"));
87103
87367
  return Object.values(manifest.models).map((e) => e.model);
87104
87368
  }
87105
87369
  function buildJudgePrompt(input, responses) {
@@ -87162,8 +87426,9 @@ function parseJudgeVotes(judgePath, responseIds) {
87162
87426
  const judgeId = file.replace(/^response-/, "").replace(/\.md$/, "");
87163
87427
  let content;
87164
87428
  try {
87165
- content = readFileSync33(join52(judgePath, file), "utf-8");
87166
- } catch {
87429
+ content = readFileSync34(join52(judgePath, file), "utf-8");
87430
+ } catch (err) {
87431
+ log(`[team] judge answer ${file} unreadable: ${err instanceof Error ? err.message : String(err)}`);
87167
87432
  continue;
87168
87433
  }
87169
87434
  const votePattern = /```vote\s*\n([\s\S]*?)\n\s*```/g;
@@ -87214,7 +87479,7 @@ function aggregateVerdict(votes, responseIds) {
87214
87479
  function formatVerdict(verdict, sessionPath) {
87215
87480
  let manifest = null;
87216
87481
  try {
87217
- manifest = JSON.parse(readFileSync33(join52(sessionPath, "manifest.json"), "utf-8"));
87482
+ manifest = JSON.parse(readFileSync34(join52(sessionPath, "manifest.json"), "utf-8"));
87218
87483
  } catch {}
87219
87484
  let output = `# Team Verdict
87220
87485
 
@@ -87249,12 +87514,14 @@ var startsInFlight, teamRuns, newestRunByPath, SETTLED_RUN_RETENTION_MS, MAX_SET
87249
87514
  var init_team_orchestrator = __esm(() => {
87250
87515
  init_prehydrate();
87251
87516
  init_config();
87517
+ init_fs_atomic();
87252
87518
  init_upstream_error_capture();
87253
87519
  init_hooks();
87254
87520
  init_inbox();
87255
87521
  init_sinks();
87256
87522
  init_request_stage();
87257
87523
  init_binding();
87524
+ init_logger();
87258
87525
  init_pane();
87259
87526
  init_redact();
87260
87527
  init_session_discovery();
@@ -87267,7 +87534,7 @@ var init_team_orchestrator = __esm(() => {
87267
87534
  });
87268
87535
 
87269
87536
  // src/mcp-session/inherited-settings.ts
87270
- import { existsSync as existsSync35, readFileSync as readFileSync34, statSync as statSync14 } from "fs";
87537
+ import { existsSync as existsSync35, readFileSync as readFileSync35, statSync as statSync15 } from "fs";
87271
87538
  import { join as join53, resolve as resolve6 } from "path";
87272
87539
  function isPlainObject7(value) {
87273
87540
  return typeof value === "object" && value !== null && !Array.isArray(value);
@@ -87313,7 +87580,7 @@ function readSettingsValue(value) {
87313
87580
  return parseLayer(value, value);
87314
87581
  let text;
87315
87582
  try {
87316
- text = readFileSync34(value, "utf-8");
87583
+ text = readFileSync35(value, "utf-8");
87317
87584
  } catch (err) {
87318
87585
  throw new Error(`invalid_args: settings ${value} cannot be read (${err.message})`);
87319
87586
  }
@@ -87325,7 +87592,7 @@ function buildInheritedSettingsLayer(setupFrom, callerFlags) {
87325
87592
  const file = join53(setupFrom, ".claude", name);
87326
87593
  if (!existsSync35(file))
87327
87594
  continue;
87328
- layers.push(parseLayer(readFileSync34(file, "utf-8"), file));
87595
+ layers.push(parseLayer(readFileSync35(file, "utf-8"), file));
87329
87596
  }
87330
87597
  const restFlags = [];
87331
87598
  for (let i = 0;i < callerFlags.length; i++) {
@@ -87355,7 +87622,7 @@ function resolveSetupFrom(arg, workDir, serverCwd) {
87355
87622
  let setupFrom = serverCwd;
87356
87623
  if (typeof arg === "string") {
87357
87624
  setupFrom = resolve6(arg);
87358
- if (!statSync14(setupFrom, { throwIfNoEntry: false })?.isDirectory()) {
87625
+ if (!statSync15(setupFrom, { throwIfNoEntry: false })?.isDirectory()) {
87359
87626
  throw new Error(`invalid_args: setup_from ${setupFrom} is not an existing directory`);
87360
87627
  }
87361
87628
  } else if (arg !== undefined) {
@@ -87366,20 +87633,20 @@ function resolveSetupFrom(arg, workDir, serverCwd) {
87366
87633
  var init_inherited_settings = () => {};
87367
87634
 
87368
87635
  // src/mcp-session/session-manager.ts
87369
- import { randomUUID as randomUUID7 } from "crypto";
87636
+ import { randomUUID as randomUUID8 } from "crypto";
87370
87637
  import {
87371
87638
  appendFileSync as appendFileSync7,
87372
87639
  closeSync as closeSync11,
87373
87640
  createWriteStream,
87374
87641
  existsSync as existsSync36,
87375
- mkdirSync as mkdirSync24,
87642
+ mkdirSync as mkdirSync23,
87376
87643
  openSync as openSync11,
87377
- readFileSync as readFileSync35,
87644
+ readFileSync as readFileSync36,
87378
87645
  readSync as readSync6,
87379
- renameSync as renameSync6,
87646
+ renameSync as renameSync7,
87380
87647
  rmSync as rmSync9,
87381
- statSync as statSync15,
87382
- writeFileSync as writeFileSync23
87648
+ statSync as statSync16,
87649
+ writeFileSync as writeFileSync22
87383
87650
  } from "fs";
87384
87651
  import { join as join54, resolve as resolve7, sep as sep2 } from "path";
87385
87652
  function normaliseTimeoutSeconds(raw) {
@@ -87429,6 +87696,8 @@ function sessionRowOf(info, upstreamRecords = []) {
87429
87696
  activity: terminal ? null : info.activity,
87430
87697
  pane: info.pane,
87431
87698
  recent: info.recent,
87699
+ agent_requested: info.agentRequested ?? null,
87700
+ agent: info.agent ?? null,
87432
87701
  session_id: info.sessionId,
87433
87702
  started_at: info.startedAt,
87434
87703
  completed_at: info.completedAt,
@@ -87466,13 +87735,15 @@ function toMetaRecord(info, cwd) {
87466
87735
  captureSource: info.captureSource,
87467
87736
  turnSource: info.turnSource,
87468
87737
  timeoutSeconds: info.timeoutSeconds,
87738
+ agentRequested: info.agentRequested ?? null,
87739
+ agent: info.agent ?? null,
87469
87740
  cwd
87470
87741
  };
87471
87742
  }
87472
87743
  function writeJsonAtomic(path, value) {
87473
87744
  const tmp = `${path}.tmp`;
87474
- writeFileSync23(tmp, JSON.stringify(value, null, 2), "utf-8");
87475
- renameSync6(tmp, path);
87745
+ writeFileSync22(tmp, JSON.stringify(value, null, 2), "utf-8");
87746
+ renameSync7(tmp, path);
87476
87747
  }
87477
87748
  function anomalyKey(a) {
87478
87749
  const at = a.lastIndexOf(" \xD7");
@@ -87481,7 +87752,7 @@ function anomalyKey(a) {
87481
87752
  function readTailText(path, maxBytes) {
87482
87753
  let fd = null;
87483
87754
  try {
87484
- const size = statSync15(path).size;
87755
+ const size = statSync16(path).size;
87485
87756
  if (size === 0)
87486
87757
  return { text: "", truncated: false };
87487
87758
  const start = Math.max(0, size - maxBytes);
@@ -87512,7 +87783,7 @@ function readTailLines2(path, maxBytes) {
87512
87783
  }
87513
87784
  function fileSize2(path) {
87514
87785
  try {
87515
- return statSync15(path).size;
87786
+ return statSync16(path).size;
87516
87787
  } catch {
87517
87788
  return 0;
87518
87789
  }
@@ -87521,7 +87792,7 @@ function readJsonObject(path, maxBytes) {
87521
87792
  try {
87522
87793
  if (fileSize2(path) > maxBytes)
87523
87794
  return null;
87524
- const parsed = JSON.parse(readFileSync35(path, "utf-8"));
87795
+ const parsed = JSON.parse(readFileSync36(path, "utf-8"));
87525
87796
  if (!parsed || typeof parsed !== "object" || Array.isArray(parsed))
87526
87797
  return null;
87527
87798
  return parsed;
@@ -87625,14 +87896,14 @@ class SessionManager {
87625
87896
  return this._launcherPid;
87626
87897
  }
87627
87898
  recordTeamRun(opts) {
87628
- mkdirSync24(this.sessionsDir, { recursive: true });
87899
+ mkdirSync23(this.sessionsDir, { recursive: true });
87629
87900
  let id = "";
87630
87901
  let dir = "";
87631
87902
  for (let attempt = 0;; attempt++) {
87632
- id = `team-${randomUUID7().replace(/-/g, "").slice(0, 8)}`;
87903
+ id = `team-${randomUUID8().replace(/-/g, "").slice(0, 8)}`;
87633
87904
  dir = join54(this.sessionsDir, id);
87634
87905
  try {
87635
- mkdirSync24(dir);
87906
+ mkdirSync23(dir);
87636
87907
  break;
87637
87908
  } catch (err) {
87638
87909
  if (err?.code !== "EEXIST" || attempt >= 4)
@@ -87756,14 +88027,15 @@ class SessionManager {
87756
88027
  }
87757
88028
  }
87758
88029
  recordSession(opts, inheritedLayer) {
87759
- const sessionId = opts.sessionId ?? randomUUID7().slice(0, 8);
87760
- const claudeSessionId = randomUUID7();
88030
+ const sessionId = opts.sessionId ?? randomUUID8().slice(0, 8);
88031
+ const claudeSessionId = randomUUID8();
87761
88032
  const timeout = normaliseTimeoutSeconds(opts.timeoutSeconds);
88033
+ const agentRequested = requestedAgentOf(opts.claudishFlags ?? []);
87762
88034
  const startedAt = new Date().toISOString();
87763
88035
  const sessionDir = opts.sessionDir ?? join54(this.sessionsDir, sessionId);
87764
- mkdirSync24(sessionDir, { recursive: true });
88036
+ mkdirSync23(sessionDir, { recursive: true });
87765
88037
  if (opts.prompt)
87766
- writeFileSync23(join54(sessionDir, "prompt.md"), opts.prompt, "utf-8");
88038
+ writeFileSync22(join54(sessionDir, "prompt.md"), opts.prompt, "utf-8");
87767
88039
  this.writeSpawnRecord(sessionDir, {
87768
88040
  kind: "session",
87769
88041
  sessionId,
@@ -87772,10 +88044,11 @@ class SessionManager {
87772
88044
  model: opts.model,
87773
88045
  timeoutSeconds: timeout,
87774
88046
  claudeSessionId,
87775
- ...opts.setupFrom ? { setupFrom: opts.setupFrom } : {}
88047
+ ...opts.setupFrom ? { setupFrom: opts.setupFrom } : {},
88048
+ ...agentRequested ? { agentRequested } : {}
87776
88049
  });
87777
88050
  if (inheritedLayer) {
87778
- writeFileSync23(join54(sessionDir, INHERITED_SETTINGS), `${JSON.stringify(inheritedLayer, null, 2)}
88051
+ writeFileSync22(join54(sessionDir, INHERITED_SETTINGS), `${JSON.stringify(inheritedLayer, null, 2)}
87779
88052
  `, { encoding: "utf-8", mode: 384 });
87780
88053
  }
87781
88054
  const cwd = opts.cwd ?? process.cwd();
@@ -87805,6 +88078,8 @@ class SessionManager {
87805
88078
  idleSeconds: null,
87806
88079
  activity: null,
87807
88080
  recent: null,
88081
+ agentRequested,
88082
+ agent: null,
87808
88083
  reason: null,
87809
88084
  detail: null,
87810
88085
  pendingInputs: opts.prompt ? 1 : 0,
@@ -88017,7 +88292,7 @@ class SessionManager {
88017
88292
  try {
88018
88293
  const text = screenLines.join(`
88019
88294
  `).replace(/\s+$/, "");
88020
- writeFileSync23(join54(entry.sessionDir, "screen.txt"), `${redactSecrets(text)}
88295
+ writeFileSync22(join54(entry.sessionDir, "screen.txt"), `${redactSecrets(text)}
88021
88296
  `, "utf-8");
88022
88297
  } catch {}
88023
88298
  }
@@ -88060,6 +88335,7 @@ class SessionManager {
88060
88335
  info.idleSeconds = snap.idleSeconds;
88061
88336
  info.activity = snap.activity;
88062
88337
  info.recent = snap.recent;
88338
+ info.agent = snap.agent ?? info.agent ?? null;
88063
88339
  info.reason = snap.reason;
88064
88340
  info.detail = snap.detail;
88065
88341
  info.pendingInputs = snap.pendingInputs;
@@ -88304,7 +88580,7 @@ class SessionManager {
88304
88580
  return null;
88305
88581
  let dirMtimeMs;
88306
88582
  try {
88307
- const stat = statSync15(sessionDir);
88583
+ const stat = statSync16(sessionDir);
88308
88584
  if (!stat.isDirectory())
88309
88585
  return null;
88310
88586
  dirMtimeMs = stat.mtimeMs;
@@ -88584,6 +88860,8 @@ function diskInfo(d) {
88584
88860
  idleSeconds: null,
88585
88861
  activity: null,
88586
88862
  recent: null,
88863
+ agentRequested: metaString(meta?.agentRequested) ?? metaString(spawnRecord?.agentRequested),
88864
+ agent: metaString(meta?.agent),
88587
88865
  reason,
88588
88866
  detail: meta === null ? NO_TERMINAL_RECORD : metaString(meta.detail),
88589
88867
  pendingInputs: 0,
@@ -88756,7 +89034,7 @@ var init_progress_heartbeat = __esm(() => {
88756
89034
 
88757
89035
  // src/mcp/run-prompt-claude-code.ts
88758
89036
  import { spawn as spawn2 } from "child_process";
88759
- import { mkdirSync as mkdirSync25, mkdtempSync as mkdtempSync3, rmSync as rmSync10, writeFileSync as writeFileSync24 } from "fs";
89037
+ import { mkdirSync as mkdirSync24, mkdtempSync as mkdtempSync3, rmSync as rmSync10, writeFileSync as writeFileSync23 } from "fs";
88760
89038
  import { tmpdir as tmpdir2 } from "os";
88761
89039
  import { join as join55 } from "path";
88762
89040
  function claudeCodePrintArgv(model, systemPromptFile) {
@@ -88879,11 +89157,11 @@ async function runPromptViaClaudeCode(model, prompt, systemPrompt, opts = {}) {
88879
89157
  const root = mkdtempSync3(join55(tmpdir2(), "claudish-run-prompt-"));
88880
89158
  try {
88881
89159
  const cwd = join55(root, "cwd");
88882
- mkdirSync25(cwd, { mode: 448 });
89160
+ mkdirSync24(cwd, { mode: 448 });
88883
89161
  let systemPromptFile;
88884
89162
  if (typeof systemPrompt === "string" && systemPrompt.length > 0) {
88885
89163
  systemPromptFile = join55(root, "system-prompt.txt");
88886
- writeFileSync24(systemPromptFile, systemPrompt, { mode: 384 });
89164
+ writeFileSync23(systemPromptFile, systemPrompt, { mode: 384 });
88887
89165
  }
88888
89166
  const argv = claudeCodePrintArgv(model, systemPromptFile);
88889
89167
  const outcome = await runChild(launch, argv, cwd, claudeCodePrintEnv(parentEnv), prompt, signal);
@@ -89182,14 +89460,14 @@ var init_preflight_chain = __esm(() => {
89182
89460
  });
89183
89461
 
89184
89462
  // src/mcp-server.ts
89185
- import { existsSync as existsSync37, mkdirSync as mkdirSync26, readFileSync as readFileSync36, readdirSync as readdirSync9, writeFileSync as writeFileSync25 } from "fs";
89463
+ import { existsSync as existsSync37, readFileSync as readFileSync37, readdirSync as readdirSync9 } from "fs";
89186
89464
  import { homedir as homedir37 } from "os";
89187
89465
  import { dirname as dirname19, join as join56, resolve as resolve8 } from "path";
89188
89466
  import { fileURLToPath as fileURLToPath3 } from "url";
89189
89467
  async function loadAllModels(forceRefresh = false) {
89190
89468
  if (!forceRefresh && existsSync37(OPENROUTER_MODELS_CACHE_PATH)) {
89191
89469
  try {
89192
- const cacheData = JSON.parse(readFileSync36(OPENROUTER_MODELS_CACHE_PATH, "utf-8"));
89470
+ const cacheData = JSON.parse(readFileSync37(OPENROUTER_MODELS_CACHE_PATH, "utf-8"));
89193
89471
  const lastUpdated = new Date(cacheData.lastUpdated);
89194
89472
  const ageInDays = (Date.now() - lastUpdated.getTime()) / (1000 * 60 * 60 * 24);
89195
89473
  if (ageInDays <= CACHE_MAX_AGE_DAYS) {
@@ -89203,13 +89481,21 @@ async function loadAllModels(forceRefresh = false) {
89203
89481
  throw new Error(`API returned ${response.status}`);
89204
89482
  const data = await response.json();
89205
89483
  const models = data.data || [];
89206
- mkdirSync26(CLAUDISH_CACHE_DIR, { recursive: true });
89207
- writeFileSync25(OPENROUTER_MODELS_CACHE_PATH, JSON.stringify({ lastUpdated: new Date().toISOString(), models }), "utf-8");
89484
+ try {
89485
+ writeFileAtomic(OPENROUTER_MODELS_CACHE_PATH, JSON.stringify({ lastUpdated: new Date().toISOString(), models }));
89486
+ } catch (err) {
89487
+ log(`[mcp] OpenRouter models cache write failed: ${err instanceof Error ? err.message : String(err)}`);
89488
+ }
89208
89489
  return models;
89209
- } catch {
89210
- if (existsSync37(OPENROUTER_MODELS_CACHE_PATH)) {
89211
- const cacheData = JSON.parse(readFileSync36(OPENROUTER_MODELS_CACHE_PATH, "utf-8"));
89212
- return cacheData.models || [];
89490
+ } catch (err) {
89491
+ log(`[mcp] OpenRouter models fetch failed: ${err instanceof Error ? err.message : String(err)}`);
89492
+ try {
89493
+ if (existsSync37(OPENROUTER_MODELS_CACHE_PATH)) {
89494
+ const cacheData = JSON.parse(readFileSync37(OPENROUTER_MODELS_CACHE_PATH, "utf-8"));
89495
+ return cacheData.models || [];
89496
+ }
89497
+ } catch (cacheErr) {
89498
+ log(`[mcp] OpenRouter models cache unreadable: ${cacheErr instanceof Error ? cacheErr.message : String(cacheErr)}`);
89213
89499
  }
89214
89500
  return [];
89215
89501
  }
@@ -89260,7 +89546,7 @@ function parseAnthropicSse(raw) {
89260
89546
  }
89261
89547
  return { text, usage: hasUsage ? { input: inputTokens, output: outputTokens } : undefined };
89262
89548
  }
89263
- async function runPromptViaProxy(model, prompt, systemPrompt) {
89549
+ async function runPromptViaProxy(model, prompt, systemPrompt, effort) {
89264
89550
  const proxy = await getProxy();
89265
89551
  const body = {
89266
89552
  model,
@@ -89270,6 +89556,9 @@ async function runPromptViaProxy(model, prompt, systemPrompt) {
89270
89556
  if (systemPrompt) {
89271
89557
  body.system = systemPrompt;
89272
89558
  }
89559
+ if (effort) {
89560
+ body.output_config = { effort };
89561
+ }
89273
89562
  const response = await fetch(`${proxy.url}/v1/messages`, {
89274
89563
  method: "POST",
89275
89564
  headers: { "Content-Type": "application/json" },
@@ -89286,11 +89575,11 @@ async function runPromptViaProxy(model, prompt, systemPrompt) {
89286
89575
  }
89287
89576
  return { content: parsed.text, usage: parsed.usage };
89288
89577
  }
89289
- async function runPrompt(model, prompt, systemPrompt, signal) {
89578
+ async function runPrompt(model, prompt, systemPrompt, signal, effort) {
89290
89579
  if (nativeRouteFor(model) !== null) {
89291
89580
  return runPromptViaClaudeCode(model, prompt, systemPrompt, { signal });
89292
89581
  }
89293
- return runPromptViaProxy(model, prompt, systemPrompt);
89582
+ return runPromptViaProxy(model, prompt, systemPrompt, effort);
89294
89583
  }
89295
89584
  function formatRunPromptResult(result) {
89296
89585
  const footer = [];
@@ -89336,6 +89625,110 @@ function fmtSize(n) {
89336
89625
  return `${(n / 1024).toFixed(1)}KB`;
89337
89626
  return `${(n / (1024 * 1024)).toFixed(1)}MB`;
89338
89627
  }
89628
+ function effortArg(value) {
89629
+ if (value === undefined || value === null || value === "" || value === KEEP_EFFORT) {
89630
+ return;
89631
+ }
89632
+ if (isEffortLevel(value))
89633
+ return value;
89634
+ throw new Error(`Invalid 'effort': ${JSON.stringify(value)}. Expected one of ${EFFORT_LEVELS.join(", ")} ` + `or "${KEEP_EFFORT}" (list_models shows the recommended level per model and task type).`);
89635
+ }
89636
+ function effortClarification(specs, efforts = latestEffortRecommendations()?.efforts) {
89637
+ if (!efforts)
89638
+ return;
89639
+ const out = {};
89640
+ for (const spec of specs) {
89641
+ if (nativeRouteFor(spec) !== null)
89642
+ continue;
89643
+ const row = efforts[parseModelSpec(spec).model];
89644
+ if (!row)
89645
+ continue;
89646
+ out[spec] = Object.fromEntries(Object.entries(row).map(([task, rec]) => [task, rec.effort]));
89647
+ }
89648
+ return Object.keys(out).length > 0 ? out : undefined;
89649
+ }
89650
+ function needsEffortResult(recommended, how) {
89651
+ return {
89652
+ content: [
89653
+ {
89654
+ type: "text",
89655
+ text: `needs_effort: nothing was started. Map your task to one task type and call again ${how}.
89656
+ ` + `Recommended levels: ${JSON.stringify(recommended, null, 2)}`
89657
+ }
89658
+ ],
89659
+ isError: true
89660
+ };
89661
+ }
89662
+ function modelEffortsArg(value, models) {
89663
+ if (value === undefined || value === null)
89664
+ return;
89665
+ if (typeof value !== "object" || Array.isArray(value)) {
89666
+ throw new Error(`Invalid 'efforts': expected an object like {"<model>": "<level>"}.`);
89667
+ }
89668
+ const out = {};
89669
+ for (const [model, level] of Object.entries(value)) {
89670
+ if (!models.includes(model)) {
89671
+ throw new Error(`Invalid 'efforts': ${JSON.stringify(model)} is not one of 'models' ` + `(${models.join(", ")}). Keys must match a 'models' entry exactly.`);
89672
+ }
89673
+ if (!isEffortLevel(level)) {
89674
+ throw new Error(`Invalid 'efforts' for ${model}: ${JSON.stringify(level)}. ` + `Expected one of ${EFFORT_LEVELS.join(", ")}.`);
89675
+ }
89676
+ out[model] = level;
89677
+ }
89678
+ return Object.keys(out).length > 0 ? out : undefined;
89679
+ }
89680
+ function isCanonicalCatalogModel(id) {
89681
+ return readAllModelsCache()?.entries.some((e) => e.modelId === id) ?? false;
89682
+ }
89683
+ function stripUnrequestedProvider(spec, required, isCatalogModel = isCanonicalCatalogModel) {
89684
+ if (required || parseModelChain(spec).length !== 1)
89685
+ return spec;
89686
+ const parsed = parseModelSpec(spec);
89687
+ if (!parsed.isExplicitProvider || parsed.isLegacySyntax)
89688
+ return spec;
89689
+ const builtin = BUILTIN_PROVIDERS.find((p) => p.name === parsed.provider);
89690
+ if (!builtin || builtin.isLocal || isLocalProviderName(parsed.provider))
89691
+ return spec;
89692
+ if (!isCatalogModel(parsed.model))
89693
+ return spec;
89694
+ return spec.slice(spec.indexOf("@") + 1);
89695
+ }
89696
+ function userRequiredProvidersArg(value, specs) {
89697
+ if (value === undefined || value === null)
89698
+ return new Set;
89699
+ if (!Array.isArray(value) || value.some((v) => typeof v !== "string")) {
89700
+ throw new Error(`Invalid 'user_required_provider': expected an array of model specs.`);
89701
+ }
89702
+ for (const spec of value) {
89703
+ if (!specs.includes(spec)) {
89704
+ throw new Error(`Invalid 'user_required_provider': ${JSON.stringify(spec)} is not one of the ` + `models (${specs.join(", ")}). Entries must match a 'models' or 'judges' entry exactly.`);
89705
+ }
89706
+ }
89707
+ return new Set(value);
89708
+ }
89709
+ function strippedProviders(specs, required, isCatalogModel) {
89710
+ const proposed = specs.map((from) => stripUnrequestedProvider(from, required.has(from), isCatalogModel));
89711
+ const stripped = [];
89712
+ const out = specs.map((from, i) => {
89713
+ const to = proposed[i];
89714
+ if (to === from)
89715
+ return from;
89716
+ const collides = proposed.some((other, j) => j !== i && other === to && specs[j] !== from);
89717
+ if (collides)
89718
+ return from;
89719
+ stripped.push({ from, to });
89720
+ return to;
89721
+ });
89722
+ if (stripped.length > 0) {
89723
+ log(`[mcp] provider removed: ${stripped.map((x) => `${x.from} -> ${x.to}`).join(", ")}`);
89724
+ }
89725
+ return { specs: out, stripped };
89726
+ }
89727
+ function strippedNote(stripped) {
89728
+ if (stripped.length === 0)
89729
+ return;
89730
+ return `Provider removed so claudish routing decides: ${stripped.map((x) => `${x.from} -> ${x.to}`).join(", ")}. ` + "Pass 'user_required_provider' only when the user named the provider.";
89731
+ }
89339
89732
  function buildChildClaudeFlags(agent, claudeFlags) {
89340
89733
  const extra = typeof claudeFlags === "string" ? claudeFlags.split(/\s+/).filter(Boolean) : [];
89341
89734
  const named = typeof agent === "string" ? agent.trim() : "";
@@ -89486,7 +89879,10 @@ function teamStatusAnswer(path, runId) {
89486
89879
  let status;
89487
89880
  try {
89488
89881
  status = getStatus(path);
89489
- } catch {
89882
+ } catch (err) {
89883
+ if (err?.code !== "ENOENT") {
89884
+ log(`[team] unreadable status.json at ${path}: ${err instanceof Error ? err.message : String(err)}`);
89885
+ }
89490
89886
  if (row)
89491
89887
  return { ...contractMeta(), run: row };
89492
89888
  throw new ContractErrorException("unknown_run", `no team run at ${path}: no status.json there and no run held by this server`);
@@ -89551,10 +89947,19 @@ ${block.join(`
89551
89947
  properties: {
89552
89948
  model: {
89553
89949
  type: "string",
89554
- description: "Model name or model spec. A bare name auto-routes to the best provider; " + "'provider@model' pins the provider (e.g. 'google@gemini-4-argon', " + "'or@x-ai/grok-4.7'). A bare Claude name (claude-*, opus, sonnet, haiku) runs on " + "Claude Code's own login."
89950
+ description: "Model name. Pass the bare name (e.g. 'gemini-4-argon'): claudish routing picks " + "the provider from the user's setup. A 'provider@' on a catalog model is removed " + "unless 'user_required_provider' is true. A bare Claude name (claude-*, opus, " + "sonnet, haiku) runs on Claude Code's own login."
89951
+ },
89952
+ user_required_provider: {
89953
+ type: "boolean",
89954
+ description: "True only when the USER named the provider ('use OpenRouter for it'): the " + "'provider@model' spec is then sent as given."
89555
89955
  },
89556
89956
  prompt: { type: "string", description: "The prompt to send to the model" },
89557
- system_prompt: { type: "string", description: "Optional system prompt" }
89957
+ system_prompt: { type: "string", description: "Optional system prompt" },
89958
+ effort: {
89959
+ type: "string",
89960
+ enum: [...EFFORT_LEVELS, KEEP_EFFORT],
89961
+ description: "Reasoning effort for this request. Take it from list_models' " + "'Recommended effort by task type' table: your task's column, this model's row. " + "Omitted for a model that has a row, the call starts nothing and answers " + `'needs_effort' with that row; "${KEEP_EFFORT}" keeps Claude Code's own level. ` + "Mapped onto the levels the model's connection publishes. Ignored for a bare " + "Claude name."
89962
+ }
89558
89963
  },
89559
89964
  required: ["model", "prompt"]
89560
89965
  },
@@ -89562,8 +89967,16 @@ ${block.join(`
89562
89967
  heartbeat: true,
89563
89968
  handler: async (args, ctx) => {
89564
89969
  try {
89565
- const result = await runPrompt(args.model, args.prompt, args.system_prompt, ctx.signal);
89566
- return { content: [{ type: "text", text: formatRunPromptResult(result) }] };
89970
+ const { specs, stripped } = strippedProviders([args.model], new Set(args.user_required_provider === true ? [args.model] : []));
89971
+ const recommended = args.effort === undefined ? effortClarification([args.model]) : undefined;
89972
+ if (recommended) {
89973
+ return needsEffortResult(recommended, `with effort: "<level>" (effort: "${KEEP_EFFORT}" keeps Claude Code's own)`);
89974
+ }
89975
+ const result = await runPrompt(specs[0], args.prompt, args.system_prompt, ctx.signal, effortArg(args.effort));
89976
+ const text = [strippedNote(stripped), formatRunPromptResult(result)].filter(Boolean).join(`
89977
+
89978
+ `);
89979
+ return { content: [{ type: "text", text }] };
89567
89980
  } catch (error) {
89568
89981
  const errMsg = error instanceof Error ? error.message : String(error);
89569
89982
  return {
@@ -89583,41 +89996,35 @@ ${block.join(`
89583
89996
  });
89584
89997
  tools.push({
89585
89998
  name: "list_models",
89586
- description: "List recommended models for coding tasks",
89999
+ description: "List recommended models for coding tasks, and the catalog's recommended reasoning " + "effort per model and task type (pass it as team 'efforts' or create_session / " + "run_prompt 'effort')",
89587
90000
  inputSchema: { type: "object" },
89588
90001
  group: "low-level",
89589
90002
  handler: async () => {
89590
- let doc;
90003
+ let doc = null;
90004
+ let note = "";
89591
90005
  try {
89592
90006
  doc = await getRecommendedModels();
89593
- } catch {
89594
- return {
89595
- content: [
89596
- {
89597
- type: "text",
89598
- text: "No recommended models found. Try search_models instead."
89599
- }
89600
- ]
89601
- };
90007
+ if (!doc.models || doc.models.length === 0) {
90008
+ log("[mcp] list_models: the recommended list is empty");
90009
+ doc = null;
90010
+ }
90011
+ } catch (err) {
90012
+ log(`[mcp] list_models: ${err instanceof Error ? err.message : String(err)}`);
89602
90013
  }
89603
- if (!doc.models || doc.models.length === 0) {
89604
- return {
89605
- content: [
89606
- {
89607
- type: "text",
89608
- text: "No recommended models found. Try search_models instead."
89609
- }
89610
- ]
89611
- };
90014
+ if (!doc) {
90015
+ doc = readLastRecommendedModels();
90016
+ if (doc) {
90017
+ note = "_The live catalog could not be read; this list is from generation " + `${doc.generationId ?? "unknown"}, the last one this machine stored._`;
90018
+ log(`[mcp] list_models: answered from stored generation ${doc.generationId ?? "unknown"}`);
90019
+ }
89612
90020
  }
89613
- return {
89614
- content: [
89615
- {
89616
- type: "text",
89617
- text: renderRecommendedMarkdown(doc, nativeShortcutForVendor)
89618
- }
89619
- ]
89620
- };
90021
+ const efforts = latestEffortRecommendations();
90022
+ const effortTable = efforts ? renderEffortTableMarkdown(efforts.efforts) : "";
90023
+ const listing = doc ? renderRecommendedMarkdown(doc) : "No recommended models found. Try search_models instead.";
90024
+ const text = [note, listing, effortTable].filter(Boolean).join(`
90025
+
90026
+ `);
90027
+ return { content: [{ type: "text", text }] };
89621
90028
  }
89622
90029
  });
89623
90030
  tools.push({
@@ -89878,11 +90285,21 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
89878
90285
  items: { type: "string" },
89879
90286
  description: "Model IDs to run (required for 'run' and 'run-and-judge' modes). " + "Native Claude names ARE runnable slots and belong in this array alongside " + "external models: 'internal'/'default' select the default tier, and " + "'opus'/'sonnet'/'haiku'/'claude-*' select a specific one. They run on the " + "user's Claude subscription through the native passthrough (no API key, no " + "translation), and \u2014 unlike a Task agent \u2014 they are covered by require_pattern, " + "so a native reviewer that never produced the required shape is reported " + "EMPTY 'shape_mismatch' instead of silently succeeding."
89880
90287
  },
90288
+ efforts: {
90289
+ type: "object",
90290
+ additionalProperties: { type: "string", enum: [...EFFORT_LEVELS] },
90291
+ description: "Reasoning effort per model for 'run' and 'run-and-judge', e.g. " + `{"gpt-6-luna": "high", "kimi-k3": "max"}. Keys must match a 'models' ` + "entry exactly. Take each level from list_models' 'Recommended effort by task " + "type' table: your task's column, the model's row. The slot pins that level on " + "every request (claudish --effort-override); a model without an entry keeps " + "Claude Code's own effort. Omitted while a model has a row, nothing starts and " + "the answer is 'needs_effort' with the rows; {} keeps Claude Code's own for all."
90292
+ },
89881
90293
  judges: {
89882
90294
  type: "array",
89883
90295
  items: { type: "string" },
89884
90296
  description: "Model IDs to use as judges (default: same as runners)"
89885
90297
  },
90298
+ user_required_provider: {
90299
+ type: "array",
90300
+ items: { type: "string" },
90301
+ description: "The 'models' or 'judges' entries whose provider the USER named ('run Kimi on " + "OpenRouter'), exactly as written there. Every other 'provider@' on a catalog " + "model is removed so claudish routing picks the provider from the user's setup; " + "pass bare names unless the user asked for a provider."
90302
+ },
89886
90303
  input_file: {
89887
90304
  type: "string",
89888
90305
  description: "PREFERRED. Path to a file holding the task prompt, relative to the working " + "directory. Use this rather than `input` for anything longer than a sentence: " + "a prompt passed inline is echoed verbatim in the caller's terminal, where a " + "200-line review brief buries every other argument and makes the call " + "unreadable. Write the brief to the session directory first (input.md is the " + "conventional name) and point here."
@@ -89923,8 +90340,20 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
89923
90340
  const path = args.path;
89924
90341
  if (typeof path !== "string" || !path)
89925
90342
  throw new Error(`'path' is required for '${mode}'`);
89926
- const models = args.models;
89927
- const judges = args.judges;
90343
+ const givenModels = args.models;
90344
+ const givenJudges = args.judges;
90345
+ const requiredProviders = userRequiredProvidersArg(args.user_required_provider, [
90346
+ ...givenModels ?? [],
90347
+ ...givenJudges ?? []
90348
+ ]);
90349
+ const modelStrip = givenModels ? strippedProviders(givenModels, requiredProviders) : undefined;
90350
+ const judgeStrip = givenJudges ? strippedProviders(givenJudges, requiredProviders) : undefined;
90351
+ const models = modelStrip?.specs;
90352
+ const judges = judgeStrip?.specs;
90353
+ const providerNote = strippedNote([
90354
+ ...modelStrip?.stripped ?? [],
90355
+ ...judgeStrip?.stripped ?? []
90356
+ ]);
89928
90357
  const inlineInput = args.input;
89929
90358
  const inputFile = args.input_file;
89930
90359
  if (inlineInput !== undefined && inputFile !== undefined) {
@@ -89935,10 +90364,16 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
89935
90364
  const minOutputBytes = args.min_output_bytes;
89936
90365
  const childFlags = buildChildClaudeFlags(args.agent, args.claude_flags) ?? [];
89937
90366
  const resolved = validateSessionPath(path);
90367
+ const givenEfforts = givenModels ? modelEffortsArg(args.efforts, givenModels) : undefined;
90368
+ const efforts = givenEfforts ? Object.fromEntries(Object.entries(givenEfforts).map(([m, level]) => [
90369
+ models?.[givenModels?.indexOf(m) ?? -1] ?? m,
90370
+ level
90371
+ ])) : undefined;
89938
90372
  const runOpts = {
89939
90373
  requirePattern,
89940
90374
  minOutputBytes,
89941
90375
  claudeFlags: childFlags,
90376
+ efforts,
89942
90377
  onProgress: (u) => {
89943
90378
  ctx.reportProgress(`team: ${u.phase}`);
89944
90379
  }
@@ -89947,8 +90382,14 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
89947
90382
  if (input !== undefined)
89948
90383
  return input;
89949
90384
  const existing = join56(resolved, "input.md");
89950
- return existsSync37(existing) ? readFileSync36(existing, "utf-8") : undefined;
90385
+ return existsSync37(existing) ? readFileSync37(existing, "utf-8") : undefined;
89951
90386
  };
90387
+ if ((mode === "run" || mode === "run-and-judge") && givenModels && args.efforts === undefined) {
90388
+ const recommended = effortClarification(givenModels);
90389
+ if (recommended) {
90390
+ return needsEffortResult(recommended, `with efforts: {"<model>": "<level>"} (efforts: {} keeps Claude Code's own for every model)`);
90391
+ }
90392
+ }
89952
90393
  switch (mode) {
89953
90394
  case "run": {
89954
90395
  if (!models?.length)
@@ -90008,6 +90449,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90008
90449
  cancel: `team(mode:"cancel", path:"${p}", slot:"<id>")`,
90009
90450
  judge: `team(mode:"judge", path:"${p}") once every slot has finished`
90010
90451
  },
90452
+ ...providerNote ? { provider_note: providerNote } : {},
90011
90453
  note: "Every slot has taken its prompt or failed to. Nothing terminates a " + "working slot on a timer: `status` reports each slot's state, " + "activity and seconds of silence; a slot inside a long build is " + "quiet and working. You decide whether to cancel."
90012
90454
  }, null, 2)
90013
90455
  }
@@ -90016,7 +90458,8 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90016
90458
  }
90017
90459
  case "judge": {
90018
90460
  const verdict = await judgeResponses(resolved, { judges, claudeFlags: childFlags });
90019
- return { content: [{ type: "text", text: JSON.stringify(verdict, null, 2) }] };
90461
+ const out = providerNote ? { ...verdict, provider_note: providerNote } : verdict;
90462
+ return { content: [{ type: "text", text: JSON.stringify(out, null, 2) }] };
90020
90463
  }
90021
90464
  case "run-and-judge": {
90022
90465
  if (!models?.length)
@@ -90037,7 +90480,12 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90037
90480
  content: [
90038
90481
  {
90039
90482
  type: "text",
90040
- text: JSON.stringify({ ...verdict, run_id: handle.runId, run }, null, 2)
90483
+ text: JSON.stringify({
90484
+ ...verdict,
90485
+ run_id: handle.runId,
90486
+ run,
90487
+ ...providerNote ? { provider_note: providerNote } : {}
90488
+ }, null, 2)
90041
90489
  }
90042
90490
  ]
90043
90491
  };
@@ -90097,7 +90545,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90097
90545
  let stderrFull = stderr_snippet || "";
90098
90546
  if (error_log_path) {
90099
90547
  try {
90100
- stderrFull = readFileSync36(error_log_path, "utf-8");
90548
+ stderrFull = readFileSync37(error_log_path, "utf-8");
90101
90549
  } catch {}
90102
90550
  }
90103
90551
  const sessionData = {};
@@ -90105,7 +90553,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90105
90553
  const sp = session_path;
90106
90554
  for (const file of ["status.json", "manifest.json", "input.md"]) {
90107
90555
  try {
90108
- sessionData[file] = readFileSync36(join56(sp, file), "utf-8");
90556
+ sessionData[file] = readFileSync37(join56(sp, file), "utf-8");
90109
90557
  } catch {}
90110
90558
  }
90111
90559
  try {
@@ -90114,7 +90562,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90114
90562
  for (const f of readdirSync9(errorDir)) {
90115
90563
  if (f.endsWith(".log")) {
90116
90564
  try {
90117
- sessionData[`errors/${f}`] = readFileSync36(join56(errorDir, f), "utf-8");
90565
+ sessionData[`errors/${f}`] = readFileSync37(join56(errorDir, f), "utf-8");
90118
90566
  } catch {}
90119
90567
  }
90120
90568
  }
@@ -90124,7 +90572,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90124
90572
  for (const f of readdirSync9(sp)) {
90125
90573
  if (f.startsWith("response-") && f.endsWith(".md")) {
90126
90574
  try {
90127
- const content = readFileSync36(join56(sp, f), "utf-8");
90575
+ const content = readFileSync37(join56(sp, f), "utf-8");
90128
90576
  sessionData[f] = content.slice(0, 200) + (content.length > 200 ? "... (truncated)" : "");
90129
90577
  } catch {}
90130
90578
  }
@@ -90135,7 +90583,7 @@ Use with: run_prompt(model="${suggested}", prompt="your prompt")`;
90135
90583
  try {
90136
90584
  const pkgPath = join56(__dirname3, "../package.json");
90137
90585
  if (existsSync37(pkgPath)) {
90138
- version = JSON.parse(readFileSync36(pkgPath, "utf-8")).version;
90586
+ version = JSON.parse(readFileSync37(pkgPath, "utf-8")).version;
90139
90587
  }
90140
90588
  } catch {}
90141
90589
  const report = {
@@ -90219,7 +90667,11 @@ Report manually at https://github.com/anthropics/claudish/issues${autoSendHint}`
90219
90667
  properties: {
90220
90668
  model: {
90221
90669
  type: "string",
90222
- description: "Model identifier (e.g., 'google@gemini-2.0-flash', 'x-ai/grok-code-fast-1')"
90670
+ description: "Model name. Pass the bare name (e.g. 'gpt-6.1-sol'): claudish routing picks the " + "provider from the user's setup. A 'provider@' on a catalog model is removed " + "unless 'user_required_provider' is true."
90671
+ },
90672
+ user_required_provider: {
90673
+ type: "boolean",
90674
+ description: "True only when the USER named the provider: the 'provider@model' spec is then " + "used as given."
90223
90675
  },
90224
90676
  prompt: {
90225
90677
  type: "string",
@@ -90239,6 +90691,11 @@ Report manually at https://github.com/anthropics/claudish/issues${autoSendHint}`
90239
90691
  type: "string",
90240
90692
  description: "Any other Claude Code / claudish flags and their values, space-separated \u2014 no " + "positional text. Unrecognised flags pass through to the child Claude Code. " + "Flags the pane owns or that only work in print mode are refused. NOTE: split on " + "whitespace, so a flag VALUE containing spaces cannot be expressed here."
90241
90693
  },
90694
+ effort: {
90695
+ type: "string",
90696
+ enum: [...EFFORT_LEVELS, KEEP_EFFORT],
90697
+ description: "Reasoning effort for the whole session. Take it from list_models' " + "'Recommended effort by task type' table: your task's column, this model's row. " + "Pinned on every request (claudish --effort-override), over one in claude_flags. " + "Omitted for a model that has a row, nothing starts and the answer is " + `'needs_effort' with that row; "${KEEP_EFFORT}" keeps Claude Code's own level.`
90698
+ },
90242
90699
  work_dir: {
90243
90700
  type: "string",
90244
90701
  description: "Working directory for the session (default: current directory)"
@@ -90254,11 +90711,19 @@ Report manually at https://github.com/anthropics/claudish/issues${autoSendHint}`
90254
90711
  handler: async (args) => {
90255
90712
  try {
90256
90713
  const claudishFlags = buildChildClaudeFlags(args.agent, args.claude_flags) ?? [];
90714
+ const effort = effortArg(args.effort);
90715
+ if (effort)
90716
+ claudishFlags.push("--effort-override", effort);
90257
90717
  const flagCheck = checkChildFlags(claudishFlags);
90258
90718
  if (!flagCheck.ok)
90259
90719
  throw new Error(`invalid_args: ${flagCheck.message}`);
90260
90720
  await assertMagmuxAvailable();
90261
- const requestedModel = args.model;
90721
+ const { specs, stripped } = strippedProviders([args.model], new Set(args.user_required_provider === true ? [args.model] : []));
90722
+ const requestedModel = specs[0];
90723
+ const recommended = args.effort === undefined ? effortClarification([args.model]) : undefined;
90724
+ if (recommended) {
90725
+ return needsEffortResult(recommended, `with effort: "<level>" (effort: "${KEEP_EFFORT}" keeps Claude Code's own)`);
90726
+ }
90262
90727
  const workDir = args.work_dir;
90263
90728
  const plan = await prehydrateCredentialsForSpawn([requestedModel], {
90264
90729
  pin: workDir === undefined || resolve8(workDir) === process.cwd()
@@ -90282,7 +90747,8 @@ Report manually at https://github.com/anthropics/claudish/issues${autoSendHint}`
90282
90747
  type: "text",
90283
90748
  text: JSON.stringify({
90284
90749
  session_id: sessionId,
90285
- state: sessionManager.getSession(sessionId).state
90750
+ state: sessionManager.getSession(sessionId).state,
90751
+ ...stripped.length > 0 ? { model: requestedModel, note: strippedNote(stripped) } : {}
90286
90752
  })
90287
90753
  }
90288
90754
  ]
@@ -90540,8 +91006,8 @@ function mcpDebugLogEnabled(argv, env) {
90540
91006
  }
90541
91007
  async function main() {
90542
91008
  const iso = isolateProtocolStdout();
90543
- if (mcpDebugLogEnabled(process.argv.slice(2), process.env))
90544
- initLogger(true, "debug", true);
91009
+ const argv = process.argv.slice(2);
91010
+ initLogger(mcpDebugLogEnabled(argv, process.env), "debug", argv.includes("--log-off"), "claudish-mcp", 500);
90545
91011
  if (!iso.active)
90546
91012
  log(`[mcp] protocol stdout not isolated: ${iso.reason ?? "unknown"}`);
90547
91013
  loadHooksOnce({ hostMode: "mcp" });
@@ -90608,9 +91074,7 @@ async function main() {
90608
91074
  await server.connect(transport);
90609
91075
  installMcpShutdown(sessionManager);
90610
91076
  if (!nested)
90611
- ensureSwept(sockRootFor()).catch(() => {
90612
- return;
90613
- });
91077
+ ensureSwept(sockRootFor()).catch((err) => log(`[mcp] stale pane sweep failed: ${err instanceof Error ? err.message : String(err)}`));
90614
91078
  }
90615
91079
  function installMcpShutdown(sessionManager) {
90616
91080
  const before = async () => {
@@ -90650,14 +91114,16 @@ Each session is an interactive Claude Code running the model in its own headless
90650
91114
  5. FAILED or TIMEOUT \u2014 or COMPLETED with an empty or surprising answer \u2014 call get_diagnostics. It returns the child's final screen, the upstream error bodies, the recent state records, the resolved model chain and the paths to the full records. It needs no re-run and no debug flag.
90651
91115
  6. capture_session reads a session's current screen; resize_session sets its terminal size (any time, mid-turn included); cancel_session stops it. Nothing stops a session for being idle: a child inside a long build is silent and working.
90652
91116
 
90653
- The session_id from create_session is the key for every session tool.`, proxyInstance = null, proxyStarting = null, SCORE_TIE_EPSILON = 0.000001, NEXT_STEP, sanitize2, TOOL_MODES;
91117
+ The session_id from create_session is the key for every session tool.`, proxyInstance = null, proxyStarting = null, SCORE_TIE_EPSILON = 0.000001, NEXT_STEP, KEEP_EFFORT = "default", sanitize2, TOOL_MODES;
90654
91118
  var init_mcp_server = __esm(() => {
90655
91119
  init_server2();
90656
91120
  init_stdio2();
90657
91121
  init_types2();
91122
+ init_base_api_format();
90658
91123
  init_model_catalog();
90659
91124
  init_prehydrate();
90660
91125
  init_prompt_role();
91126
+ init_fs_atomic();
90661
91127
  init_hooks();
90662
91128
  init_output_capture();
90663
91129
  init_logger();
@@ -90671,11 +91137,15 @@ var init_mcp_server = __esm(() => {
90671
91137
  init_child_env();
90672
91138
  init_pane();
90673
91139
  init_port_manager();
91140
+ init_all_models_cache();
91141
+ init_effort_recommendations();
90674
91142
  init_endpoint_registration();
91143
+ init_model_parser();
90675
91144
  init_native_route();
90676
91145
  init_onepassword();
90677
91146
  init_preflight_chain();
90678
91147
  init_probe_live();
91148
+ init_provider_definitions();
90679
91149
  init_proxy_server();
90680
91150
  init_recommended_listing();
90681
91151
  init_redact();
@@ -90707,7 +91177,7 @@ var init_mcp_server = __esm(() => {
90707
91177
  });
90708
91178
 
90709
91179
  // src/serve-command.ts
90710
- import { existsSync as existsSync38, readFileSync as readFileSync37 } from "fs";
91180
+ import { existsSync as existsSync38, readFileSync as readFileSync38 } from "fs";
90711
91181
  function parseServeArgs(args) {
90712
91182
  const out = {};
90713
91183
  for (let i = 0;i < args.length; i++) {
@@ -90731,7 +91201,7 @@ function loadModelMap(path) {
90731
91201
  }
90732
91202
  let raw;
90733
91203
  try {
90734
- raw = readFileSync37(path, "utf-8");
91204
+ raw = readFileSync38(path, "utf-8");
90735
91205
  } catch (e) {
90736
91206
  throw new Error(`failed to read --models file ${path}: ${e instanceof Error ? e.message : String(e)}`);
90737
91207
  }
@@ -90812,7 +91282,7 @@ var init_serve_command = __esm(() => {
90812
91282
  var HOOKS_AMBIENT_DTS = '// claudish hook types \u2014 written by `claudish hooks init`. Do not edit: run\n// `claudish hooks init` from a newer claudish to refresh it.\n// With this file beside your hook, `import type { HookDefinition } from\n// "claudish/hooks"` type-checks with nothing installed.\ndeclare module "claudish/hooks" {\n /**\n * claudish/hooks \u2014 the public hook contract.\n *\n * Everything a hook author can import lives here, and nothing else does. This\n * file imports nothing from the rest of claudish and has no side effects, so it\n * can be built on its own into `dist/hooks.js` + `dist/hooks.d.ts` and served to\n * user modules as the `claudish/hooks` virtual module (see `loader.ts`).\n *\n * Every internal hooks module takes its types from here, so the contract has a\n * single source.\n *\n * ## Process isolation\n *\n * A hook module\'s top-level state is PER PROCESS. In the interactive launcher,\n * proxy events (`request` \u2026 `responseEnd`, raw) and session events\n * (`sessionStart` \u2026 `sessionEnd`) run in one process. In `create_session` and\n * team children they do not: proxy events run in the pane child, and session\n * events run in the MCP server or the CLI process that drives the pane. Pass\n * per-turn data from a proxy event to `sessionIdle` with `annotateTurn`, never\n * with module variables.\n *\n * ## Execution: a hook chain\n *\n * The hooks of one event run one after another, in effective order. Each hook\'s\n * actions are applied before the next hook is called, so `ctx.request`,\n * `ctx.tool.args` and `ctx.response` show what the earlier hooks did, and\n * `ctx.prior` lists it. A warn-severity or failing hook changes nothing for the\n * next one. Each event has a budget for all its hooks together; a hook\'s timeout\n * is cut to what is left of it.\n *\n * ## Output\n *\n * Log with `ctx.log`. `console.*` and `process.stdout`/`stderr` writes made by a\n * hook are routed to claudish\'s debug log, never to the terminal or the MCP\n * protocol stream.\n */\n export const HOOK_API_VERSION = 1;\n export type Severity = "off" | "warn" | "fix";\n export type HookOrder = "pre" | "normal" | "post";\n /** native = RouteInfo.native true; foreign = RouteInfo.native false; all = both */\n export type RouteScope = "foreign" | "native" | "all";\n export type HostMode = "interactive" | "pane-child" | "serve" | "mcp" | "other";\n export type JsonValue = string | number | boolean | null | ReadonlyArray<JsonValue> | {\n readonly [k: string]: JsonValue;\n };\n export interface HarnessFacts {\n readonly planModeActive: boolean;\n readonly planFilePath?: string;\n readonly planDir?: string;\n /** Claude Code session id from request metadata */\n readonly sessionId?: string;\n /** empty = no listing found, not "no skills" */\n readonly skills?: ReadonlyArray<{\n name: string;\n description: string;\n }>;\n }\n export interface RouteInfo {\n /** bare model name the handler serves, e.g. "glm-5" */\n readonly modelId: string;\n /** claudish provider name, e.g. "openrouter"; "anthropic" for native */\n readonly provider: string;\n /**\n * true when the request is served by the native Anthropic handler, OR when\n * !forceForeignModel && (/^claude[-.]/i.test(modelId) || provider === "anthropic")\n * where forceForeignModel is the provider profile\'s opt-in override. This is the exact\n * rule the plan-mode built-in has always used (a claude-* uid on an aggregator that sets\n * forceForeignModel is foreign).\n */\n readonly native: boolean;\n }\n export interface ClaudeTool {\n name: string;\n description?: string;\n input_schema?: unknown;\n }\n /** A Claude-format content block. Only `text` blocks are editable by closed actions. */\n export type ClaudeContentBlock = {\n type: "text";\n text: string;\n } | {\n type: "tool_use";\n id: string;\n name: string;\n input: unknown;\n } | {\n type: "tool_result";\n tool_use_id: string;\n content?: unknown;\n is_error?: boolean;\n } | {\n type: "thinking";\n thinking: string;\n signature?: string;\n } | {\n type: string;\n [k: string]: unknown;\n };\n export interface ClaudeMessage {\n role: "user" | "assistant";\n content: string | ReadonlyArray<ClaudeContentBlock>;\n }\n /**\n * In `request`, the request as the earlier steps of the hook chain left it. On\n * the response side and in `claims()`, the request chain\'s final view.\n */\n export interface RequestFacts {\n /** as Claude Code asked for it; frozen */\n readonly model: string;\n /** frozen */\n readonly stream: boolean;\n /** system prompt flattened to text, after earlier steps */\n readonly systemText: string;\n /** read-only view after earlier steps; change it through actions */\n readonly messages: ReadonlyArray<ClaudeMessage>;\n /**\n * read-only view after earlier steps; `description` includes earlier description actions as\n * stage B will apply them to the Claude-format tool (the provider copy may be summarised)\n */\n readonly tools: ReadonlyArray<ClaudeTool>;\n }\n /** Which session a proxy event belongs to, when claudish knows. */\n export interface ProxySessionRef {\n readonly kind: SessionKind;\n readonly id: string;\n readonly role: "slot" | "judge" | null;\n }\n /** One action an earlier step of this hook chain applied or handed on. */\n export interface PriorAction {\n readonly hookId: string;\n readonly action: HookAction;\n }\n interface BaseContext {\n readonly hookId: string;\n /** "warn" or "fix" (an "off" hook is never called) */\n readonly severity: Severity;\n /** writes to claudish\'s debug log; never to the terminal */\n log(message: string): void;\n /**\n * this step\'s own signal: aborted when its step timeout elapses (its own timeout, or the\n * event budget left, whichever is shorter) or when the dispatch is aborted. Never shared\n * with another hook\'s step.\n */\n readonly signal: AbortSignal;\n /**\n * actions earlier steps of this hook chain applied (or, for responseEnd/sessionStart/\n * sessionIdle, handed on), in order. Empty for the first step and in claims()/the toolCall\n * predicate. Never lists warn actions or anything a warn-severity hook returned.\n */\n readonly prior: ReadonlyArray<PriorAction>;\n }\n export interface ProxyContext extends BaseContext {\n readonly host: {\n mode: HostMode;\n };\n readonly route: RouteInfo;\n readonly request: RequestFacts;\n readonly harness: HarnessFacts;\n readonly session: ProxySessionRef | null;\n }\n export interface RequestContext extends ProxyContext {\n readonly event: "request";\n }\n export interface ToolCallContext extends ProxyContext {\n readonly event: "toolCall";\n readonly tool: {\n id: string;\n name: string;\n /** the arguments after every repair earlier hooks in the chain applied */\n args: Readonly<Record<string, unknown>>;\n /** the argument JSON exactly as the model produced it; never rewritten */\n rawArgs: string;\n };\n }\n export type ResponseBlock = {\n type: "text";\n text: string;\n } | {\n type: "thinking";\n thinking: string;\n } | {\n type: "tool_use";\n id: string;\n name: string;\n input: unknown;\n } | {\n type: "other";\n blockType: string;\n };\n export interface ResponseView {\n blocks: ReadonlyArray<ResponseBlock>;\n /** every text block, joined with "\\n\\n" */\n text: string;\n /** every thinking block, joined with "\\n\\n" */\n reasoning: string;\n toolNames: ReadonlyArray<string>;\n /** "tool_use" = an intermediate step of a tool loop; the turn continues after the tool runs */\n stopReason: string | null;\n }\n /** response = the held response after every text action earlier hooks in the chain applied */\n export interface ResponseRewriteContext extends ProxyContext {\n readonly event: "responseRewrite";\n readonly response: ResponseView;\n }\n /** response = the final bytes the client received: after any rewrite AND any raw `response` replacement */\n export interface ResponseEndContext extends ProxyContext {\n readonly event: "responseEnd";\n readonly response: ResponseView;\n }\n export type SessionKind = "interactive" | "channel" | "team";\n export interface SessionInfo {\n kind: SessionKind;\n /** team only; null otherwise */\n role: "slot" | "judge" | null;\n /** channel: the 8-hex session_id \xB7 team: "<run_id>:<slot id>" \xB7 interactive: the Claude Code session id */\n id: string;\n claudeSessionId: string | null;\n /** as the caller asked for it */\n model: string;\n cwd: string;\n /** a one-shot session stays "one-shot" through a hook-extended turn chain */\n shape: "interactive" | "one-shot";\n injection: "available" | "unavailable";\n }\n export interface SessionStartContext extends BaseContext {\n readonly event: "sessionStart";\n readonly session: SessionInfo;\n }\n export interface TurnAnnotation {\n hookId: string;\n key: string;\n value: JsonValue;\n }\n export interface SessionIdleContext extends BaseContext {\n readonly event: "sessionIdle";\n readonly session: SessionInfo;\n readonly turn: {\n /** 1-based within the session; a re-woken turn keeps its index */\n index: number;\n /** this turn\'s assistant text */\n answer: string;\n stopReason: string | null;\n apiError: boolean;\n /** this turn was started by an injection */\n hookCaused: boolean;\n /** annotateTurn actions from this turn\'s responses, in arrival order */\n annotations: ReadonlyArray<TurnAnnotation>;\n };\n readonly consecutiveHookTurns: number;\n /** caller/human input is queued; an injection returned now will be dropped as stale */\n readonly callerInputPending: boolean;\n }\n export interface SessionBlockedContext extends BaseContext {\n readonly event: "sessionBlocked";\n readonly session: SessionInfo;\n readonly block: {\n kind: "question" | "permission";\n text: string;\n };\n }\n export interface SessionEndContext extends BaseContext {\n readonly event: "sessionEnd";\n readonly session: SessionInfo;\n readonly outcome: {\n state: string;\n reason: string | null;\n exitCode: number | null;\n };\n }\n type TextMatch = {\n find: string;\n regex?: boolean;\n flags?: string;\n };\n /** default ["user"] */\n type MessageRoles = {\n roles?: ReadonlyArray<"user" | "assistant">;\n };\n export type InjectSystemNote = {\n type: "injectSystemNote";\n text: string;\n };\n export type AppendUserText = {\n type: "appendUserText";\n text: string;\n };\n export type ReplaceMessageText = {\n type: "replaceMessageText";\n replace: string;\n } & TextMatch & MessageRoles;\n export type RemoveMessageText = {\n type: "removeMessageText";\n } & TextMatch & MessageRoles;\n export type RewriteToolDescription = {\n type: "rewriteToolDescription";\n tool: string;\n append: string;\n };\n export type ReplaceToolDescription = {\n type: "replaceToolDescription";\n tool: string;\n description: string;\n };\n export type ReplaceToolSchema = {\n type: "replaceToolSchema";\n tool: string;\n inputSchema: {\n type: "object";\n [k: string]: unknown;\n };\n };\n export type RemoveTool = {\n type: "removeTool";\n tool: string;\n };\n export type RepairToolArgs = {\n type: "repairToolArgs";\n args: Record<string, unknown>;\n reason: string;\n };\n export type AppendText = {\n type: "appendText";\n text: string;\n };\n export type PrependText = {\n type: "prependText";\n text: string;\n };\n export type ReplaceText = {\n type: "replaceText";\n replace: string;\n } & TextMatch;\n export type RemoveText = {\n type: "removeText";\n } & TextMatch;\n export type InjectUserTurn = {\n type: "injectUserTurn";\n text: string;\n };\n export type AnnotateTurn = {\n type: "annotateTurn";\n key: string;\n value: JsonValue;\n };\n export type Warn = {\n type: "warn";\n message: string;\n };\n export type RequestAction = InjectSystemNote | AppendUserText | ReplaceMessageText | RemoveMessageText | RewriteToolDescription | ReplaceToolDescription | ReplaceToolSchema | RemoveTool | Warn;\n export type ToolCallAction = RepairToolArgs | Warn;\n export type RewriteAction = AppendText | PrependText | ReplaceText | RemoveText | Warn;\n export type ResponseEndAction = InjectSystemNote | InjectUserTurn | AnnotateTurn | Warn;\n export type SessionAction = InjectUserTurn | Warn;\n export type ObserveAction = Warn;\n export type HookAction = RequestAction | ToolCallAction | RewriteAction | ResponseEndAction | SessionAction;\n export type HookResult<A> = A[] | void | Promise<A[] | void>;\n export interface HookHandlers {\n request?(ctx: RequestContext): HookResult<RequestAction>;\n toolCall?: {\n /** tool names whose completed arguments this hook sees; "*" = every tool (costs streaming of all tool input) */\n tools: ReadonlyArray<string>;\n /** synchronous, per request; default true. false = not armed for this request */\n armed?(ctx: RequestContext): boolean;\n /** true = see the call after it was forwarded; can only warn; never holds the stream */\n observe?: boolean;\n handle(ctx: ToolCallContext): HookResult<ToolCallAction>;\n };\n responseRewrite?: {\n /** synchronous, per request, evaluated before the response starts; default true */\n claims?(ctx: RequestContext): boolean;\n handle(ctx: ResponseRewriteContext): HookResult<RewriteAction>;\n };\n responseEnd?(ctx: ResponseEndContext): HookResult<ResponseEndAction>;\n sessionStart?(ctx: SessionStartContext): HookResult<SessionAction>;\n sessionIdle?(ctx: SessionIdleContext): HookResult<SessionAction>;\n sessionBlocked?(ctx: SessionBlockedContext): HookResult<ObserveAction>;\n sessionEnd?(ctx: SessionEndContext): HookResult<ObserveAction>;\n }\n export interface RawProviderRequestContext {\n readonly hookId: string;\n readonly route: RouteInfo;\n claudeRequest: any;\n messages: any[];\n tools: any[];\n }\n export interface RawProviderChunkContext {\n readonly hookId: string;\n readonly route: RouteInfo;\n /** A clone of the parsed provider event. Whatever this field holds when the call returns is\n * what the parser reads from then on, so it may be edited in place or replaced. */\n chunk: any;\n /** The delta object inside `chunk` at call time (Responses wire: `chunk` itself). Edit it in\n * place; assigning a new object to this field has no effect. */\n delta: any;\n /** per-stream, shared across this hook\'s chunk calls; never cloned */\n metadata: Map<string, unknown>;\n }\n export interface RawProviderStreamEndContext {\n readonly hookId: string;\n readonly route: RouteInfo;\n metadata: Map<string, unknown>;\n }\n export interface RawResponseContext {\n readonly hookId: string;\n readonly route: RouteInfo;\n readonly request: RequestFacts;\n /** A replay of the current Claude-format response (SSE, or JSON for stream:false), read at the\n * hook\'s own pace. claudish drains the original itself, so leaving this unread delays nothing. */\n response: Response;\n }\n export interface RawMiddleware {\n /**\n * Receives clones. They replace the live request only when this call returns (or its promise\n * resolves) within its timeout. A throw, a rejection or a timeout discards every change.\n */\n providerRequest?(ctx: RawProviderRequestContext): void | Promise<void>;\n /**\n * MUST be synchronous. Called on the parser\'s loop, on a clone of the chunk. On a normal return\n * of anything but a thenable, the clone (whatever `ctx.chunk` holds then) is committed: it\n * becomes the object the parser reads, deletions included. On a throw nothing is committed.\n * A declared `async` function is rejected at load. Any other thenable return is an invalid\n * invocation: the clone is discarded even if the hook mutated it before returning, the call is\n * journaled `invalid` (`async_return`) and counts toward the circuit breaker, and a rejection\n * handler is attached, so a rejection is journaled `error` and never becomes an\n * unhandledRejection.\n */\n providerChunk?(ctx: RawProviderChunkContext): void;\n providerStreamEnd?(ctx: RawProviderStreamEndContext): void | Promise<void>;\n /**\n * Return a replacement Response, or nothing to keep the current one. A replacement is read\n * whole and forwarded only when it completes cleanly; on any failure the original is forwarded.\n * The client never sees a partial replacement. A replacement must close within this hook\'s\n * timeout after the later of this call\'s return and the end of the original; the original\'s end\n * never depends on whether `ctx.response` is read.\n */\n response?(ctx: RawResponseContext): Response | void | Promise<Response | void>;\n }\n interface HookBase {\n apiVersion: 1;\n id: string;\n description?: string;\n /** default "fix" for user hooks */\n defaultSeverity?: Severity;\n /** default "normal" */\n order?: HookOrder;\n /** globs on RouteInfo.modelId; default "*"; proxy events only */\n models?: string | ReadonlyArray<string>;\n /** default "all"; proxy events only */\n routes?: RouteScope;\n /** per call; clamped to the event\'s maximum and to the event budget left when the hook\'s turn comes */\n timeoutMs?: number;\n on?: HookHandlers;\n }\n export interface SafeHook extends HookBase {\n unsafe?: never;\n raw?: never;\n }\n export interface UnsafeHook extends HookBase {\n unsafe: true;\n raw: RawMiddleware;\n }\n /**\n * One hook. Module-level state is per process: in `create_session` and team\n * children, proxy events run in the pane child and session events in the MCP\n * server or CLI process. Pass per-turn data from proxy events to `sessionIdle`\n * with `annotateTurn`, never with module variables.\n */\n export type HookDefinition = SafeHook | UnsafeHook;\n /** Identity function: gives editor type-checking and inference. */\n export function defineHook<const H extends HookDefinition>(hook: H): H;\n /** Action constructors (plain data; equivalent to writing the object literal). */\n export const act: {\n injectSystemNote(text: string): InjectSystemNote;\n appendUserText(text: string): AppendUserText;\n replaceMessageText(find: string, replace: string, opts?: {\n regex?: boolean;\n flags?: string;\n roles?: ReadonlyArray<"user" | "assistant">;\n }): ReplaceMessageText;\n removeMessageText(find: string, opts?: {\n regex?: boolean;\n flags?: string;\n roles?: ReadonlyArray<"user" | "assistant">;\n }): RemoveMessageText;\n rewriteToolDescription(tool: string, append: string): RewriteToolDescription;\n replaceToolDescription(tool: string, description: string): ReplaceToolDescription;\n replaceToolSchema(tool: string, inputSchema: {\n type: "object";\n [k: string]: unknown;\n }): ReplaceToolSchema;\n removeTool(tool: string): RemoveTool;\n repairToolArgs(args: Record<string, unknown>, reason: string): RepairToolArgs;\n appendText(text: string): AppendText;\n prependText(text: string): PrependText;\n replaceText(find: string, replace: string, opts?: {\n regex?: boolean;\n flags?: string;\n }): ReplaceText;\n removeText(find: string, opts?: {\n regex?: boolean;\n flags?: string;\n }): RemoveText;\n injectUserTurn(text: string): InjectUserTurn;\n annotateTurn(key: string, value: JsonValue): AnnotateTurn;\n warn(message: string): Warn;\n };\n}\n';
90813
91283
 
90814
91284
  // src/hooks/observer/corpus.ts
90815
- import { appendFileSync as appendFileSync8, readFileSync as readFileSync38, readdirSync as readdirSync10, statSync as statSync16 } from "fs";
91285
+ import { appendFileSync as appendFileSync8, readFileSync as readFileSync39, readdirSync as readdirSync10, statSync as statSync17 } from "fs";
90816
91286
  import { homedir as homedir38 } from "os";
90817
91287
  import { join as join57 } from "path";
90818
91288
  function directoryOf2(filePath) {
@@ -90836,7 +91306,7 @@ function writeTargetsOf(row) {
90836
91306
  function replayTranscript(file) {
90837
91307
  let text;
90838
91308
  try {
90839
- text = readFileSync38(file, "utf8");
91309
+ text = readFileSync39(file, "utf8");
90840
91310
  } catch {
90841
91311
  return [];
90842
91312
  }
@@ -90895,7 +91365,7 @@ function listTranscripts(root) {
90895
91365
  for (const project of projects) {
90896
91366
  const dir = join57(root, project);
90897
91367
  try {
90898
- if (!statSync16(dir).isDirectory())
91368
+ if (!statSync17(dir).isDirectory())
90899
91369
  continue;
90900
91370
  for (const f of readdirSync10(dir)) {
90901
91371
  if (f.endsWith(".jsonl"))
@@ -90928,7 +91398,7 @@ var init_corpus = __esm(() => {
90928
91398
  });
90929
91399
 
90930
91400
  // src/hooks-command.ts
90931
- import { existsSync as existsSync39, mkdirSync as mkdirSync27, readFileSync as readFileSync39, writeFileSync as writeFileSync26 } from "fs";
91401
+ import { existsSync as existsSync39, mkdirSync as mkdirSync25, readFileSync as readFileSync40, writeFileSync as writeFileSync24 } from "fs";
90932
91402
  import { homedir as homedir39 } from "os";
90933
91403
  import { join as join58, resolve as resolve9 } from "path";
90934
91404
  function severityColor(sev) {
@@ -91064,9 +91534,9 @@ function init(dirArg) {
91064
91534
  console.error(`${path} already exists; not overwriting it.`);
91065
91535
  return 1;
91066
91536
  }
91067
- mkdirSync27(dir, { recursive: true });
91537
+ mkdirSync25(dir, { recursive: true });
91068
91538
  for (const [path, text] of files)
91069
- writeFileSync26(path, text, { flag: "wx" });
91539
+ writeFileSync24(path, text, { flag: "wx" });
91070
91540
  console.log(`
91071
91541
  wrote ${files.map(([p]) => p).join(`
91072
91542
  wrote `)}
@@ -91132,7 +91602,7 @@ function setTelemetryEnabled(value) {
91132
91602
  let cfg = {};
91133
91603
  try {
91134
91604
  if (existsSync39(path)) {
91135
- const parsed = JSON.parse(readFileSync39(path, "utf-8"));
91605
+ const parsed = JSON.parse(readFileSync40(path, "utf-8"));
91136
91606
  if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) {
91137
91607
  cfg = parsed;
91138
91608
  }
@@ -91141,7 +91611,7 @@ function setTelemetryEnabled(value) {
91141
91611
  const hooks = cfg.hooks && typeof cfg.hooks === "object" && !Array.isArray(cfg.hooks) ? { ...cfg.hooks } : {};
91142
91612
  hooks.telemetry = { enabled: value };
91143
91613
  cfg.hooks = hooks;
91144
- writeFileSync26(path, `${JSON.stringify(cfg, null, 2)}
91614
+ writeFileSync24(path, `${JSON.stringify(cfg, null, 2)}
91145
91615
  `, "utf-8");
91146
91616
  }
91147
91617
  function telemetry(action, json) {
@@ -91152,7 +91622,7 @@ function telemetry(action, json) {
91152
91622
  try {
91153
91623
  const path = outboxPath();
91154
91624
  if (existsSync39(path))
91155
- pending = readFileSync39(path, "utf8").split(`
91625
+ pending = readFileSync40(path, "utf8").split(`
91156
91626
  `).filter(Boolean).length;
91157
91627
  } catch {}
91158
91628
  if (json) {
@@ -91259,7 +91729,7 @@ var init_hooks_command = __esm(() => {
91259
91729
 
91260
91730
  // src/team-grid.ts
91261
91731
  import { spawn as spawn3 } from "child_process";
91262
- import { existsSync as existsSync40, readFileSync as readFileSync40, writeFileSync as writeFileSync27 } from "fs";
91732
+ import { existsSync as existsSync40, readFileSync as readFileSync41, writeFileSync as writeFileSync25 } from "fs";
91263
91733
  import { connect as netConnect2 } from "net";
91264
91734
  import { join as join59 } from "path";
91265
91735
  import { setTimeout as wait } from "timers/promises";
@@ -91412,8 +91882,8 @@ async function runWithGrid(sessionPath, models, input, opts) {
91412
91882
  const manifest = setupSession(sessionPath, models, input);
91413
91883
  const startedAt = new Date().toISOString();
91414
91884
  const gridfilePath = join59(sessionPath, "gridfile.txt");
91415
- const prompt = readFileSync40(join59(sessionPath, "input.md"), "utf-8").replace(/'/g, "'\\''").replace(/\n/g, " ");
91416
- const rawPrompt = readFileSync40(join59(sessionPath, "input.md"), "utf-8");
91885
+ const prompt = readFileSync41(join59(sessionPath, "input.md"), "utf-8").replace(/'/g, "'\\''").replace(/\n/g, " ");
91886
+ const rawPrompt = readFileSync41(join59(sessionPath, "input.md"), "utf-8");
91417
91887
  const usedBannerColors = new Set;
91418
91888
  const routeLines = mode === "interactive" ? new Map : await resolvePaneRouteLines(Object.values(manifest.models).map((entry) => entry.model));
91419
91889
  const gridLines = Object.entries(manifest.models).map(([anonId]) => {
@@ -91425,7 +91895,7 @@ async function runWithGrid(sessionPath, models, input, opts) {
91425
91895
  const header = buildPaneHeader(model, routeLines.get(model) ?? "", rawPrompt, bg);
91426
91896
  return `${header} claudish --model ${model} -y --quiet '${prompt}'`;
91427
91897
  });
91428
- writeFileSync27(gridfilePath, `${gridLines.join(`
91898
+ writeFileSync25(gridfilePath, `${gridLines.join(`
91429
91899
  `)}
91430
91900
  `, "utf-8");
91431
91901
  const magmuxPath = findMagmuxBinary();
@@ -91446,7 +91916,7 @@ async function runWithGrid(sessionPath, models, input, opts) {
91446
91916
  const [{ results }] = await Promise.all([subscription, procExit]);
91447
91917
  const status = buildTeamStatus(manifest, startedAt, results?.panes ?? null);
91448
91918
  const statusPath = join59(sessionPath, "status.json");
91449
- writeFileSync27(statusPath, JSON.stringify(status, null, 2), "utf-8");
91919
+ writeFileSync25(statusPath, JSON.stringify(status, null, 2), "utf-8");
91450
91920
  return status;
91451
91921
  }
91452
91922
  var BANNER_BG_COLORS;
@@ -91465,7 +91935,7 @@ var init_team_grid = __esm(() => {
91465
91935
  });
91466
91936
 
91467
91937
  // src/team-cli.ts
91468
- import { readFileSync as readFileSync41 } from "fs";
91938
+ import { readFileSync as readFileSync42 } from "fs";
91469
91939
  import { join as join60 } from "path";
91470
91940
  async function runPaneTeam(sessionPath, models, input, opts) {
91471
91941
  installPaneShutdownHooks({ exitAfter: true });
@@ -91611,7 +92081,7 @@ async function teamCommand(args) {
91611
92081
  }
91612
92082
  case "judge": {
91613
92083
  await judgeResponses(sessionPath, { judges });
91614
- console.log(readFileSync41(join60(sessionPath, "verdict.md"), "utf-8"));
92084
+ console.log(readFileSync42(join60(sessionPath, "verdict.md"), "utf-8"));
91615
92085
  break;
91616
92086
  }
91617
92087
  case "run-and-judge": {
@@ -91627,7 +92097,7 @@ async function teamCommand(args) {
91627
92097
  });
91628
92098
  printStatus(status);
91629
92099
  await judgeResponses(sessionPath, { judges });
91630
- console.log(readFileSync41(join60(sessionPath, "verdict.md"), "utf-8"));
92100
+ console.log(readFileSync42(join60(sessionPath, "verdict.md"), "utf-8"));
91631
92101
  break;
91632
92102
  }
91633
92103
  case "status": {
@@ -92582,7 +93052,7 @@ var init_subscription_models_command = __esm(() => {
92582
93052
 
92583
93053
  // src/auth/antigravity-oauth.ts
92584
93054
  import { spawnSync as spawnSync2 } from "child_process";
92585
- import { existsSync as existsSync41, unlinkSync as unlinkSync10 } from "fs";
93055
+ import { existsSync as existsSync41, unlinkSync as unlinkSync11 } from "fs";
92586
93056
  import { homedir as homedir40 } from "os";
92587
93057
  import { join as join61 } from "path";
92588
93058
  async function defaultSuggestModel() {
@@ -92705,7 +93175,7 @@ No session detected yet. Starting the Antigravity CLI interactively \u2014
92705
93175
  try {
92706
93176
  const tokenFile = join61(homedir40(), ".gemini", "antigravity-cli", "antigravity-oauth-token");
92707
93177
  if (existsSync41(tokenFile))
92708
- unlinkSync10(tokenFile);
93178
+ unlinkSync11(tokenFile);
92709
93179
  } catch {}
92710
93180
  log("[AntigravityOAuth] Antigravity session cleared (keychain + agy token file)");
92711
93181
  }
@@ -100851,7 +101321,7 @@ var init_own_pane = __esm(() => {
100851
101321
  });
100852
101322
 
100853
101323
  // src/hooks/session/interactive-driver.ts
100854
- import { existsSync as existsSync42, statSync as statSync17 } from "fs";
101324
+ import { existsSync as existsSync42, statSync as statSync18 } from "fs";
100855
101325
  import { join as join62 } from "path";
100856
101326
  function nextDriverPhase(phase, ev) {
100857
101327
  const row = EDGES[phase];
@@ -101615,7 +102085,7 @@ function assertNeverPhase(p) {
101615
102085
  }
101616
102086
  function fileSizeOf(path) {
101617
102087
  try {
101618
- return statSync17(path).size;
102088
+ return statSync18(path).size;
101619
102089
  } catch {
101620
102090
  return 0;
101621
102091
  }
@@ -102169,20 +102639,20 @@ var init_terminal_isolation = __esm(() => {
102169
102639
 
102170
102640
  // src/claude-runner.ts
102171
102641
  import { spawn as spawn4, spawnSync as spawnSync4 } from "child_process";
102172
- import { randomUUID as randomUUID8 } from "crypto";
102642
+ import { randomUUID as randomUUID9 } from "crypto";
102173
102643
  import {
102174
102644
  chmodSync as chmodSync4,
102175
102645
  closeSync as closeSync12,
102176
102646
  existsSync as existsSync44,
102177
- mkdirSync as mkdirSync28,
102647
+ mkdirSync as mkdirSync26,
102178
102648
  mkdtempSync as mkdtempSync4,
102179
102649
  openSync as openSync12,
102180
- readFileSync as readFileSync42,
102650
+ readFileSync as readFileSync43,
102181
102651
  readdirSync as readdirSync11,
102182
102652
  rmSync as rmSync11,
102183
- statSync as statSync18,
102184
- unlinkSync as unlinkSync11,
102185
- writeFileSync as writeFileSync28
102653
+ statSync as statSync19,
102654
+ unlinkSync as unlinkSync12,
102655
+ writeFileSync as writeFileSync26
102186
102656
  } from "fs";
102187
102657
  import { homedir as homedir41, tmpdir as tmpdir3 } from "os";
102188
102658
  import { dirname as dirname20, join as join63 } from "path";
@@ -102352,7 +102822,7 @@ function settingsAuthSource(settings) {
102352
102822
  return null;
102353
102823
  }
102354
102824
  function readableClaudeSettingsLayers(config, env, deps) {
102355
- const readFile = deps.readFile ?? ((path) => readFileSync42(path, "utf-8"));
102825
+ const readFile = deps.readFile ?? ((path) => readFileSync43(path, "utf-8"));
102356
102826
  const home = deps.home ?? homedir41();
102357
102827
  const cwd = deps.cwd ?? process.cwd();
102358
102828
  const files = [
@@ -102399,7 +102869,7 @@ function managedSettingsPath() {
102399
102869
  }
102400
102870
  return "/etc/claude-code/managed-settings.json";
102401
102871
  }
102402
- function managedSettingsForcesClaudeAi(readFile = readFileSync42) {
102872
+ function managedSettingsForcesClaudeAi(readFile = readFileSync43) {
102403
102873
  try {
102404
102874
  const raw = readFile(managedSettingsPath(), "utf-8");
102405
102875
  const parsed = JSON.parse(raw);
@@ -102547,13 +103017,13 @@ process.stdin.on('end', () => {
102547
103017
  }
102548
103018
  });
102549
103019
  `;
102550
- writeFileSync28(scriptPath, script, "utf-8");
103020
+ writeFileSync26(scriptPath, script, "utf-8");
102551
103021
  return scriptPath;
102552
103022
  }
102553
103023
  function initializeTokenFile(tokenFilePath) {
102554
103024
  try {
102555
- mkdirSync28(dirname20(tokenFilePath), { recursive: true });
102556
- writeFileSync28(tokenFilePath, JSON.stringify({
103025
+ mkdirSync26(dirname20(tokenFilePath), { recursive: true });
103026
+ writeFileSync26(tokenFilePath, JSON.stringify({
102557
103027
  input_tokens: 0,
102558
103028
  output_tokens: 0,
102559
103029
  total_tokens: 0,
@@ -102586,9 +103056,9 @@ function cleanupStaleTokenFiles(dir, now = Date.now(), maxAgeMs = STALE_TOKEN_FI
102586
103056
  scanned++;
102587
103057
  const full = join63(dir, name);
102588
103058
  try {
102589
- if (statSync18(full).mtimeMs >= cutoff)
103059
+ if (statSync19(full).mtimeMs >= cutoff)
102590
103060
  continue;
102591
- unlinkSync11(full);
103061
+ unlinkSync12(full);
102592
103062
  removed++;
102593
103063
  } catch {}
102594
103064
  }
@@ -102601,7 +103071,7 @@ function parseSettingsArg(value) {
102601
103071
  if (value.trimStart().startsWith("{")) {
102602
103072
  return JSON.parse(value);
102603
103073
  }
102604
- return JSON.parse(readFileSync42(value, "utf-8"));
103074
+ return JSON.parse(readFileSync43(value, "utf-8"));
102605
103075
  }
102606
103076
  function parseSettingsArgSafe(value) {
102607
103077
  try {
@@ -102658,7 +103128,7 @@ function createTempSettingsFile(_modelDisplay, port, proxyAuthMode, userStatusLi
102658
103128
  const homeDir = process.env.HOME || process.env.USERPROFILE || tmpdir3();
102659
103129
  const claudishDir = join63(homeDir, ".claudish");
102660
103130
  try {
102661
- mkdirSync28(claudishDir, { recursive: true });
103131
+ mkdirSync26(claudishDir, { recursive: true });
102662
103132
  } catch {}
102663
103133
  const tempPath = join63(claudishDir, `settings-${process.pid}-${Date.now()}.json`);
102664
103134
  const assignedFile = assignedTokenFile(process.env) !== null;
@@ -102697,7 +103167,7 @@ function createTempSettingsFile(_modelDisplay, port, proxyAuthMode, userStatusLi
102697
103167
  padding: 0
102698
103168
  };
102699
103169
  const settings = buildClaudishSettingsOverlay(statusLine, proxyAuthMode);
102700
- writeFileSync28(tempPath, JSON.stringify(settings, null, 2), "utf-8");
103170
+ writeFileSync26(tempPath, JSON.stringify(settings, null, 2), "utf-8");
102701
103171
  return { path: tempPath, statusLine, tokenFilePath };
102702
103172
  }
102703
103173
  function scrubChildEnv(env, opts) {
@@ -102740,7 +103210,7 @@ function mergeUserSettingsIfPresent(config, tempSettingsPath, statusLine, proxyA
102740
103210
  if (paneChild) {
102741
103211
  userSettings.editorMode = "normal";
102742
103212
  }
102743
- writeFileSync28(tempSettingsPath, JSON.stringify(userSettings, null, 2), "utf-8");
103213
+ writeFileSync26(tempSettingsPath, JSON.stringify(userSettings, null, 2), "utf-8");
102744
103214
  } catch {
102745
103215
  if (!config.quiet) {
102746
103216
  console.warn(`[claudish] Warning: could not merge user settings: ${userSettingsValue}`);
@@ -103074,7 +103544,7 @@ Or set CLAUDE_PATH to your custom installation:`);
103074
103544
  const sessionFlags = sessionFlagsOf(config.claudeArgs);
103075
103545
  let driverLaunch = null;
103076
103546
  if (surfaces.driver) {
103077
- const minted = sessionFlags.sessionId || sessionFlags.resumes ? null : randomUUID8();
103547
+ const minted = sessionFlags.sessionId || sessionFlags.resumes ? null : randomUUID9();
103078
103548
  const turnDir = mkdtempSync4(join63(tmpdir3(), "claudish-turns-"));
103079
103549
  chmodSync4(turnDir, 448);
103080
103550
  claudeArgs.unshift(...driverLeadingArgs({ mintedSessionId: minted, turnDir }));
@@ -103187,7 +103657,7 @@ Or set CLAUDE_PATH to your custom installation:`);
103187
103657
  log(exitSignal ? `[Claude Code] Exited from ${exitSignal} (exit code ${exitCode})` : `[Claude Code] Exited with code ${exitCode}`);
103188
103658
  releaseTerminalIsolation();
103189
103659
  try {
103190
- unlinkSync11(tempSettingsPath);
103660
+ unlinkSync12(tempSettingsPath);
103191
103661
  } catch {}
103192
103662
  return exitCode;
103193
103663
  }
@@ -103210,7 +103680,7 @@ function setupSignalHandlers(proc, tempSettingsPath, quiet, onCleanup) {
103210
103680
  } catch {}
103211
103681
  }
103212
103682
  try {
103213
- unlinkSync11(tempSettingsPath);
103683
+ unlinkSync12(tempSettingsPath);
103214
103684
  } catch {}
103215
103685
  process.exit(128 + (SIGNAL_EXIT_NUMBERS[signal] ?? 0));
103216
103686
  });
@@ -103338,13 +103808,13 @@ var init_claude_runner = __esm(() => {
103338
103808
  });
103339
103809
 
103340
103810
  // src/diag-output.ts
103341
- import { createWriteStream as createWriteStream2, mkdirSync as mkdirSync29, unlinkSync as unlinkSync12, writeFileSync as writeFileSync29 } from "fs";
103811
+ import { createWriteStream as createWriteStream2, mkdirSync as mkdirSync27, unlinkSync as unlinkSync13, writeFileSync as writeFileSync27 } from "fs";
103342
103812
  import { homedir as homedir42 } from "os";
103343
103813
  import { join as join64 } from "path";
103344
103814
  function getClaudishDir() {
103345
103815
  const dir = join64(homedir42(), ".claudish");
103346
103816
  try {
103347
- mkdirSync29(dir, { recursive: true });
103817
+ mkdirSync27(dir, { recursive: true });
103348
103818
  } catch {}
103349
103819
  return dir;
103350
103820
  }
@@ -103358,7 +103828,7 @@ class LogFileDiagOutput {
103358
103828
  constructor() {
103359
103829
  this.logPath = getDiagLogPath();
103360
103830
  try {
103361
- writeFileSync29(this.logPath, `--- claudish diag session ${new Date().toISOString()} ---
103831
+ writeFileSync27(this.logPath, `--- claudish diag session ${new Date().toISOString()} ---
103362
103832
  `);
103363
103833
  } catch {}
103364
103834
  this.stream = createWriteStream2(this.logPath, { flags: "a" });
@@ -103377,7 +103847,7 @@ class LogFileDiagOutput {
103377
103847
  this.stream.end();
103378
103848
  } catch {}
103379
103849
  try {
103380
- unlinkSync12(this.logPath);
103850
+ unlinkSync13(this.logPath);
103381
103851
  } catch {}
103382
103852
  }
103383
103853
  getLogPath() {
@@ -103914,7 +104384,7 @@ var init_advisor_startup = __esm(() => {
103914
104384
  });
103915
104385
 
103916
104386
  // src/session/conversation.ts
103917
- import { closeSync as closeSync13, openSync as openSync13, readSync as readSync7, statSync as statSync19 } from "fs";
104387
+ import { closeSync as closeSync13, openSync as openSync13, readSync as readSync7, statSync as statSync20 } from "fs";
103918
104388
  import { StringDecoder } from "string_decoder";
103919
104389
  function looksLikeTurn(line) {
103920
104390
  const assistant = line.includes('"type":"assistant"');
@@ -103969,7 +104439,7 @@ function readConversation(file, opts = {}) {
103969
104439
  };
103970
104440
  let fd = null;
103971
104441
  try {
103972
- const size = statSync19(file).size;
104442
+ const size = statSync20(file).size;
103973
104443
  fd = openSync13(file, "r");
103974
104444
  const buf = Buffer.allocUnsafe(chunkBytes);
103975
104445
  const decoder = new StringDecoder("utf-8");
@@ -105628,11 +106098,11 @@ var exports_session_stats = {};
105628
106098
  __export(exports_session_stats, {
105629
106099
  readSessionStats: () => readSessionStats
105630
106100
  });
105631
- import { readFileSync as readFileSync43 } from "fs";
106101
+ import { readFileSync as readFileSync44 } from "fs";
105632
106102
  function readSessionStats(port, opts) {
105633
106103
  let raw;
105634
106104
  try {
105635
- raw = JSON.parse(readFileSync43(resolveTokenFilePath(port), "utf-8"));
106105
+ raw = JSON.parse(readFileSync44(resolveTokenFilePath(port), "utf-8"));
105636
106106
  } catch {
105637
106107
  return null;
105638
106108
  }
@@ -106010,7 +106480,7 @@ init_launch_env();
106010
106480
  init_op_source();
106011
106481
  init_startup_trace();
106012
106482
  init_picker_cancelled();
106013
- import { existsSync as existsSync45, readFileSync as readFileSync44 } from "fs";
106483
+ import { existsSync as existsSync45, readFileSync as readFileSync45 } from "fs";
106014
106484
  import { join as join65, resolve as resolve10 } from "path";
106015
106485
 
106016
106486
  // src/tui/runtime/should-open-picker.ts
@@ -106028,7 +106498,7 @@ function requiresExplicitModel(gate, tty) {
106028
106498
  var autoloadDropped = [...droppedAtLaunch, ...takeLauncherDropped(process.env)];
106029
106499
  var dotenvText;
106030
106500
  try {
106031
- dotenvText = readFileSync44(join65(process.cwd(), ".env"));
106501
+ dotenvText = readFileSync45(join65(process.cwd(), ".env"));
106032
106502
  } catch {}
106033
106503
  if (dotenvText !== undefined) {
106034
106504
  await Promise.resolve().then(() => init_dotenv_allowlist());
@@ -106349,7 +106819,7 @@ async function runCli() {
106349
106819
  if (cliConfig.team && cliConfig.team.length > 0) {
106350
106820
  let prompt = cliConfig.claudeArgs.join(" ");
106351
106821
  if (cliConfig.inputFile) {
106352
- prompt = readFileSync44(cliConfig.inputFile, "utf-8");
106822
+ prompt = readFileSync45(cliConfig.inputFile, "utf-8");
106353
106823
  }
106354
106824
  if (!prompt.trim()) {
106355
106825
  console.error("Error: --team requires a prompt (positional args or -f <file>)");
@@ -106378,7 +106848,7 @@ async function runCli() {
106378
106848
  for (const anonId of Object.keys(status.models)) {
106379
106849
  const responsePath = join65(sessionPath, `response-${anonId}.md`);
106380
106850
  try {
106381
- const raw = readFileSync44(responsePath, "utf-8").trim();
106851
+ const raw = readFileSync45(responsePath, "utf-8").trim();
106382
106852
  try {
106383
106853
  result.responses[anonId] = JSON.parse(raw);
106384
106854
  } catch {