adhdev 0.6.57 → 0.6.58

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
@@ -2379,6 +2379,8 @@ var init_chat_history = __esm({
2379
2379
  lastSeenCounts = /* @__PURE__ */ new Map();
2380
2380
  /** Last seen message hash per agent (deduplication) */
2381
2381
  lastSeenHashes = /* @__PURE__ */ new Map();
2382
+ /** Last seen append-only terminal transcript per agent */
2383
+ lastSeenTerminal = /* @__PURE__ */ new Map();
2382
2384
  rotated = false;
2383
2385
  /**
2384
2386
  * Append new messages to history
@@ -2436,10 +2438,51 @@ var init_chat_history = __esm({
2436
2438
  } catch {
2437
2439
  }
2438
2440
  }
2441
+ appendTerminalHistory(agentType, terminalHistory, sessionTitle, instanceId) {
2442
+ const next = String(terminalHistory || "");
2443
+ if (!next.trim()) return;
2444
+ try {
2445
+ const dedupKey = instanceId ? `${agentType}:${instanceId}:terminal` : `${agentType}:terminal`;
2446
+ const prev = this.lastSeenTerminal.get(dedupKey) || "";
2447
+ if (prev === next) return;
2448
+ let delta = "";
2449
+ if (!prev) {
2450
+ delta = next;
2451
+ } else if (next.startsWith(prev)) {
2452
+ delta = next.slice(prev.length);
2453
+ } else if (prev.includes(next)) {
2454
+ this.lastSeenTerminal.set(dedupKey, next);
2455
+ return;
2456
+ } else {
2457
+ delta = `
2458
+
2459
+ [terminal snapshot reset ${(/* @__PURE__ */ new Date()).toISOString()} | ${sessionTitle || agentType}]
2460
+ ${next}`;
2461
+ }
2462
+ if (!delta) {
2463
+ this.lastSeenTerminal.set(dedupKey, next);
2464
+ return;
2465
+ }
2466
+ const dir = path4.join(HISTORY_DIR, this.sanitize(agentType));
2467
+ fs3.mkdirSync(dir, { recursive: true });
2468
+ const date5 = (/* @__PURE__ */ new Date()).toISOString().slice(0, 10);
2469
+ const filePrefix = instanceId ? `${this.sanitize(instanceId)}_` : "";
2470
+ const filePath = path4.join(dir, `${filePrefix}${date5}.terminal.log`);
2471
+ fs3.appendFileSync(filePath, delta, "utf-8");
2472
+ this.lastSeenTerminal.set(dedupKey, next);
2473
+ if (!this.rotated) {
2474
+ this.rotated = true;
2475
+ this.rotateOldFiles().catch(() => {
2476
+ });
2477
+ }
2478
+ } catch {
2479
+ }
2480
+ }
2439
2481
  /** Called when agent session is explicitly changed */
2440
2482
  onSessionChange(agentType) {
2441
2483
  this.lastSeenHashes.delete(agentType);
2442
2484
  this.lastSeenCounts.delete(agentType);
2485
+ this.lastSeenTerminal.delete(`${agentType}:terminal`);
2443
2486
  }
2444
2487
  /** Delete history files older than 30 days */
2445
2488
  async rotateOldFiles() {
@@ -2449,7 +2492,7 @@ var init_chat_history = __esm({
2449
2492
  const agentDirs = fs3.readdirSync(HISTORY_DIR, { withFileTypes: true }).filter((d) => d.isDirectory());
2450
2493
  for (const dir of agentDirs) {
2451
2494
  const dirPath = path4.join(HISTORY_DIR, dir.name);
2452
- const files = fs3.readdirSync(dirPath).filter((f) => f.endsWith(".jsonl"));
2495
+ const files = fs3.readdirSync(dirPath).filter((f) => f.endsWith(".jsonl") || f.endsWith(".terminal.log"));
2453
2496
  for (const file2 of files) {
2454
2497
  const filePath = path4.join(dirPath, file2);
2455
2498
  const stat = fs3.statSync(filePath);
@@ -3196,7 +3239,13 @@ async function handleReadChat(h, args) {
3196
3239
  _log(`${provider.category} adapter: ${adapter.cliType}`);
3197
3240
  const status = adapter.getStatus?.();
3198
3241
  if (status) {
3199
- return { success: true, messages: status.messages || [], status: status.status, activeModal: status.activeModal };
3242
+ return {
3243
+ success: true,
3244
+ messages: status.messages || [],
3245
+ status: status.status,
3246
+ activeModal: status.activeModal,
3247
+ terminalHistory: status.terminalHistory || ""
3248
+ };
3200
3249
  }
3201
3250
  }
3202
3251
  return { success: false, error: `${provider.category} adapter not found` };
@@ -16316,6 +16365,36 @@ function promptLikelyVisible(screenText, promptSnippet) {
16316
16365
  ).length;
16317
16366
  return matched >= required2;
16318
16367
  }
16368
+ function splitHistoryLines(text) {
16369
+ return String(text || "").split("\n").map((line) => line.replace(/\s+$/, ""));
16370
+ }
16371
+ function normalizeHistoryLine(line) {
16372
+ return String(line || "").replace(/\s+/g, " ").trim();
16373
+ }
16374
+ function mergeTerminalHistory(existing, snapshot) {
16375
+ const next = String(snapshot || "").trim();
16376
+ if (!next) return existing;
16377
+ const prev = String(existing || "").trim();
16378
+ if (!prev) return next;
16379
+ if (prev === next || prev.endsWith(next)) return prev;
16380
+ const prevLines = splitHistoryLines(prev);
16381
+ const nextLines = splitHistoryLines(next);
16382
+ const prevNorm = prevLines.map(normalizeHistoryLine);
16383
+ const nextNorm = nextLines.map(normalizeHistoryLine);
16384
+ const maxOverlap = Math.min(prevLines.length, nextLines.length);
16385
+ for (let overlap = maxOverlap; overlap >= 1; overlap -= 1) {
16386
+ const prevTail = prevNorm.slice(prevNorm.length - overlap);
16387
+ const nextHead = nextNorm.slice(0, overlap);
16388
+ if (prevTail.every((line, index) => line === nextHead[index])) {
16389
+ return [...prevLines, ...nextLines.slice(overlap)].join("\n").trim();
16390
+ }
16391
+ }
16392
+ const compactPrev = prevNorm.join("\n");
16393
+ const compactNext = nextNorm.join("\n");
16394
+ if (compactPrev.includes(compactNext)) return prev;
16395
+ return `${prev}
16396
+ ${next}`.trim();
16397
+ }
16319
16398
  function parsePatternEntry(x) {
16320
16399
  if (x instanceof RegExp) return x;
16321
16400
  if (x && typeof x === "object" && typeof x.source === "string") {
@@ -16392,6 +16471,7 @@ var init_provider_cli_adapter = __esm({
16392
16471
  this.approvalKeys = rawKeys && typeof rawKeys === "object" ? rawKeys : {};
16393
16472
  this.sendDelayMs = typeof provider.sendDelayMs === "number" ? Math.max(0, provider.sendDelayMs) : 0;
16394
16473
  this.sendKey = typeof provider.sendKey === "string" && provider.sendKey.length > 0 ? provider.sendKey : "\r";
16474
+ this.submitStrategy = provider.submitStrategy === "immediate" ? "immediate" : "wait_for_echo";
16395
16475
  this.cliScripts = provider.scripts || {};
16396
16476
  const scriptNames = Object.keys(this.cliScripts).filter((k) => typeof this.cliScripts[k] === "function");
16397
16477
  if (scriptNames.length > 0) {
@@ -16406,6 +16486,7 @@ var init_provider_cli_adapter = __esm({
16406
16486
  provider;
16407
16487
  ptyProcess = null;
16408
16488
  messages = [];
16489
+ committedMessages = [];
16409
16490
  structuredMessages = [];
16410
16491
  currentStatus = "starting";
16411
16492
  onStatusChange = null;
@@ -16452,8 +16533,35 @@ var init_provider_cli_adapter = __esm({
16452
16533
  accumulatedRawBuffer = "";
16453
16534
  /** Current visible terminal screen snapshot */
16454
16535
  terminalScreen = new TerminalScreen(40, 120);
16536
+ /** Rolling append-only terminal transcript built from screen snapshots */
16537
+ terminalHistory = "";
16455
16538
  /** Max accumulated buffer size (last 50KB) */
16456
16539
  static MAX_ACCUMULATED_BUFFER = 5e4;
16540
+ currentTurnScope = null;
16541
+ syncMessageViews() {
16542
+ this.messages = [...this.committedMessages];
16543
+ this.structuredMessages = [...this.committedMessages];
16544
+ }
16545
+ sliceFromOffset(text, start) {
16546
+ if (!text) return "";
16547
+ if (!Number.isFinite(start) || start <= 0) return text;
16548
+ if (start >= text.length) return "";
16549
+ return text.slice(start);
16550
+ }
16551
+ buildParseInput(baseMessages, partialResponse, scope) {
16552
+ const buffer = scope ? this.sliceFromOffset(this.terminalHistory, scope.terminalHistoryStart) || this.sliceFromOffset(this.accumulatedBuffer, scope.bufferStart) || this.accumulatedBuffer : this.accumulatedBuffer;
16553
+ const rawBuffer = scope ? this.sliceFromOffset(this.accumulatedRawBuffer, scope.rawBufferStart) || this.accumulatedRawBuffer : this.accumulatedRawBuffer;
16554
+ const terminalHistory = scope ? this.sliceFromOffset(this.terminalHistory, scope.terminalHistoryStart) || this.terminalHistory : this.terminalHistory;
16555
+ return {
16556
+ buffer,
16557
+ rawBuffer,
16558
+ recentBuffer: buffer.slice(-1e3) || this.recentOutputBuffer,
16559
+ screenText: this.terminalScreen.getText(),
16560
+ terminalHistory,
16561
+ messages: [...baseMessages],
16562
+ partialResponse
16563
+ };
16564
+ }
16457
16565
  setStatus(status, trigger) {
16458
16566
  const prev = this.currentStatus;
16459
16567
  if (prev === status) return;
@@ -16468,6 +16576,7 @@ var init_provider_cli_adapter = __esm({
16468
16576
  approvalKeys;
16469
16577
  sendDelayMs;
16470
16578
  sendKey;
16579
+ submitStrategy;
16471
16580
  /** Inject CLI scripts after construction (e.g. when resolved by ProviderLoader) */
16472
16581
  setCliScripts(scripts) {
16473
16582
  this.cliScripts = scripts;
@@ -16563,6 +16672,8 @@ var init_provider_cli_adapter = __esm({
16563
16672
  this.startupParseGate = true;
16564
16673
  this.startupBuffer = "";
16565
16674
  this.terminalScreen.reset(40, 120);
16675
+ this.terminalHistory = "";
16676
+ this.currentTurnScope = null;
16566
16677
  this.ready = false;
16567
16678
  this.setStatus("idle", "pty_ready");
16568
16679
  this.onStatusChange?.();
@@ -16574,6 +16685,7 @@ var init_provider_cli_adapter = __esm({
16574
16685
  this.ptyProcess?.write("\x1B[1;1R");
16575
16686
  }
16576
16687
  this.terminalScreen.write(rawData);
16688
+ this.terminalHistory = mergeTerminalHistory(this.terminalHistory, this.terminalScreen.getText());
16577
16689
  const cleanData = stripAnsi(rawData);
16578
16690
  if (this.isWaitingForResponse && cleanData) {
16579
16691
  this.responseBuffer = (this.responseBuffer + cleanData).slice(-8e3);
@@ -16718,6 +16830,7 @@ var init_provider_cli_adapter = __esm({
16718
16830
  finishResponse() {
16719
16831
  if (this.submitPendingUntil > Date.now()) return;
16720
16832
  if (this.responseSettleIgnoreUntil > Date.now()) return;
16833
+ this.commitCurrentTranscript();
16721
16834
  if (this.responseTimeout) {
16722
16835
  clearTimeout(this.responseTimeout);
16723
16836
  this.responseTimeout = null;
@@ -16739,10 +16852,58 @@ var init_provider_cli_adapter = __esm({
16739
16852
  this.responseSettleIgnoreUntil = 0;
16740
16853
  this.submitRetryUsed = false;
16741
16854
  this.submitRetryPromptSnippet = "";
16855
+ this.currentTurnScope = null;
16742
16856
  this.activeModal = null;
16743
16857
  this.setStatus("idle", "response_finished");
16744
16858
  this.onStatusChange?.();
16745
16859
  }
16860
+ commitCurrentTranscript() {
16861
+ const baseMessages = [...this.committedMessages];
16862
+ const parsed = this.parseCurrentTranscript(baseMessages, "", this.currentTurnScope);
16863
+ if (parsed && Array.isArray(parsed.messages) && parsed.messages.length > 0) {
16864
+ const parsedMessages = parsed.messages.filter((m) => m && (m.role === "user" || m.role === "assistant")).map((m) => ({
16865
+ role: m.role,
16866
+ content: typeof m.content === "string" ? m.content : String(m.content || ""),
16867
+ timestamp: m.timestamp
16868
+ }));
16869
+ const latestAssistant = [...parsedMessages].reverse().find((m) => m.role === "assistant" && m.content.trim());
16870
+ if (latestAssistant) {
16871
+ LOG.info("CLI", `[${this.cliType}] commitCurrentTranscript parsed assistant len=${latestAssistant.content.length} scopePrompt=${JSON.stringify(this.currentTurnScope?.prompt || "").slice(0, 120)}`);
16872
+ const nextMessages = [...baseMessages];
16873
+ const last2 = nextMessages[nextMessages.length - 1];
16874
+ if (last2?.role === "assistant") {
16875
+ last2.content = latestAssistant.content;
16876
+ last2.timestamp = latestAssistant.timestamp || last2.timestamp;
16877
+ } else if (last2?.role === "user") {
16878
+ nextMessages.push({
16879
+ role: "assistant",
16880
+ content: latestAssistant.content,
16881
+ timestamp: latestAssistant.timestamp || Date.now()
16882
+ });
16883
+ } else {
16884
+ nextMessages.push({
16885
+ role: "assistant",
16886
+ content: latestAssistant.content,
16887
+ timestamp: latestAssistant.timestamp || Date.now()
16888
+ });
16889
+ }
16890
+ this.committedMessages = nextMessages;
16891
+ this.syncMessageViews();
16892
+ return;
16893
+ }
16894
+ }
16895
+ const fallback = String(this.responseBuffer || "").trim();
16896
+ LOG.info("CLI", `[${this.cliType}] commitCurrentTranscript fallback len=${fallback.length} scopePrompt=${JSON.stringify(this.currentTurnScope?.prompt || "").slice(0, 120)}`);
16897
+ if (!fallback) return;
16898
+ const last = baseMessages[baseMessages.length - 1];
16899
+ if (last?.role === "assistant") {
16900
+ last.content = fallback;
16901
+ } else {
16902
+ baseMessages.push({ role: "assistant", content: fallback, timestamp: Date.now() });
16903
+ }
16904
+ this.committedMessages = baseMessages;
16905
+ this.syncMessageViews();
16906
+ }
16746
16907
  // ─── Script Execution ──────────────────────────
16747
16908
  runDetectStatus(text) {
16748
16909
  if (!this.cliScripts?.detectStatus) return null;
@@ -16772,24 +16933,12 @@ var init_provider_cli_adapter = __esm({
16772
16933
  }
16773
16934
  // ─── Public API (CliAdapter) ───────────────────
16774
16935
  getStatus() {
16775
- const scriptResult = this.getScriptParsedStatus();
16776
- if (scriptResult) {
16777
- return {
16778
- status: this.currentStatus,
16779
- messages: (scriptResult.messages || []).map((m) => ({
16780
- role: m.role,
16781
- content: m.content,
16782
- timestamp: m.timestamp
16783
- })),
16784
- workingDir: this.workingDir,
16785
- activeModal: this.activeModal
16786
- };
16787
- }
16788
16936
  return {
16789
16937
  status: this.currentStatus,
16790
- messages: [...this.messages],
16938
+ messages: [...this.committedMessages],
16791
16939
  workingDir: this.workingDir,
16792
- activeModal: this.activeModal
16940
+ activeModal: this.activeModal,
16941
+ terminalHistory: this.terminalHistory
16793
16942
  };
16794
16943
  }
16795
16944
  /**
@@ -16797,31 +16946,32 @@ var init_provider_cli_adapter = __esm({
16797
16946
  * Called by command handler / dashboard for rich content rendering.
16798
16947
  */
16799
16948
  getScriptParsedStatus() {
16949
+ const messages = [...this.committedMessages];
16950
+ return {
16951
+ id: "cli_session",
16952
+ status: this.currentStatus,
16953
+ title: this.cliName,
16954
+ terminalHistory: this.terminalHistory,
16955
+ messages: messages.slice(-50).map((message, index) => ({
16956
+ id: `msg_${index}`,
16957
+ role: message.role,
16958
+ content: message.content,
16959
+ timestamp: message.timestamp,
16960
+ index,
16961
+ kind: "standard"
16962
+ })),
16963
+ activeModal: this.activeModal
16964
+ };
16965
+ }
16966
+ parseCurrentTranscript(baseMessages, partialResponse, scope) {
16800
16967
  if (!this.cliScripts?.parseOutput) return null;
16801
16968
  try {
16802
- const input = {
16803
- buffer: this.accumulatedBuffer,
16804
- rawBuffer: this.accumulatedRawBuffer,
16805
- recentBuffer: this.recentOutputBuffer,
16806
- screenText: this.terminalScreen.getText(),
16807
- messages: [...this.structuredMessages.length > 0 ? this.structuredMessages : this.messages],
16808
- partialResponse: this.responseBuffer
16809
- };
16810
- const result = this.cliScripts.parseOutput(input);
16811
- if (result && typeof result === "object") {
16812
- if (Array.isArray(result.messages)) {
16813
- this.structuredMessages = result.messages.map((m) => ({
16814
- role: m.role,
16815
- content: m.content,
16816
- timestamp: m.timestamp
16817
- }));
16818
- }
16819
- return result;
16820
- }
16969
+ const input = this.buildParseInput(baseMessages, partialResponse, scope);
16970
+ return this.cliScripts.parseOutput(input);
16821
16971
  } catch (e) {
16822
16972
  LOG.warn("CLI", `[${this.cliType}] parseOutput error: ${e.message}`);
16973
+ return null;
16823
16974
  }
16824
- return null;
16825
16975
  }
16826
16976
  /** Whether this adapter has CLI scripts loaded */
16827
16977
  hasCliScripts() {
@@ -16861,10 +17011,18 @@ ${data.message || ""}`.trim();
16861
17011
  }
16862
17012
  if (!this.ready) throw new Error(`${this.cliName} not ready (status: ${this.currentStatus})`);
16863
17013
  if (this.isWaitingForResponse) return;
16864
- this.messages.push({ role: "user", content: text, timestamp: Date.now() });
16865
- this.structuredMessages.push({ role: "user", content: text, timestamp: Date.now() });
17014
+ this.committedMessages.push({ role: "user", content: text, timestamp: Date.now() });
17015
+ this.syncMessageViews();
16866
17016
  this.isWaitingForResponse = true;
16867
17017
  this.responseBuffer = "";
17018
+ this.currentTurnScope = {
17019
+ prompt: text,
17020
+ startedAt: Date.now(),
17021
+ bufferStart: this.accumulatedBuffer.length,
17022
+ rawBufferStart: this.accumulatedRawBuffer.length,
17023
+ terminalHistoryStart: this.terminalHistory.length
17024
+ };
17025
+ LOG.info("CLI", `[${this.cliType}] sendMessage turn scope buffer=${this.currentTurnScope.bufferStart} raw=${this.currentTurnScope.rawBufferStart} terminal=${this.currentTurnScope.terminalHistoryStart} prompt=${JSON.stringify(text).slice(0, 120)}`);
16868
17026
  this.submitRetryUsed = false;
16869
17027
  this.submitRetryPromptSnippet = extractPromptRetrySnippet(text);
16870
17028
  const normalizedPromptSnippet = normalizePromptText(this.submitRetryPromptSnippet);
@@ -16884,10 +17042,12 @@ ${data.message || ""}`.trim();
16884
17042
  this.responseSettleIgnoreUntil = Date.now() + submitDelayMs + this.timeouts.outputSettle + 250;
16885
17043
  this.setStatus("generating", "sendMessage");
16886
17044
  this.onStatusChange?.();
16887
- if (submitDelayMs > 0) {
16888
- this.submitPendingUntil = Date.now() + submitDelayMs;
16889
- }
16890
- this.ptyProcess.write(text);
17045
+ const startResponseTimeout = () => {
17046
+ if (this.responseTimeout) clearTimeout(this.responseTimeout);
17047
+ this.responseTimeout = setTimeout(() => {
17048
+ if (this.isWaitingForResponse) this.finishResponse();
17049
+ }, this.timeouts.maxResponse);
17050
+ };
16891
17051
  const submit = () => {
16892
17052
  if (!this.ptyProcess) return;
16893
17053
  this.submitPendingUntil = 0;
@@ -16910,10 +17070,30 @@ ${data.message || ""}`.trim();
16910
17070
  this.submitRetryTimer = setTimeout(() => retrySubmitIfStuck(attempt + 1), retryDelayMs);
16911
17071
  };
16912
17072
  this.submitRetryTimer = setTimeout(() => retrySubmitIfStuck(1), retryDelayMs);
16913
- this.responseTimeout = setTimeout(() => {
16914
- if (this.isWaitingForResponse) this.finishResponse();
16915
- }, this.timeouts.maxResponse);
17073
+ startResponseTimeout();
16916
17074
  };
17075
+ if (this.submitStrategy === "immediate") {
17076
+ this.submitPendingUntil = 0;
17077
+ this.ptyProcess.write(text + this.sendKey);
17078
+ this.submitRetryTimer = setTimeout(() => {
17079
+ this.submitRetryTimer = null;
17080
+ if (!this.ptyProcess || !this.isWaitingForResponse || this.submitRetryUsed) return;
17081
+ if (this.currentStatus !== "generating") return;
17082
+ if ((this.responseBuffer || "").trim()) return;
17083
+ const screenText = this.terminalScreen.getText();
17084
+ if (!promptLikelyVisible(screenText, normalizedPromptSnippet)) return;
17085
+ LOG.info("CLI", `[${this.cliType}] Retrying submit key for stuck prompt (attempt 1)`);
17086
+ this.responseSettleIgnoreUntil = Date.now() + this.timeouts.outputSettle + 400;
17087
+ this.ptyProcess.write(this.sendKey);
17088
+ this.submitRetryUsed = true;
17089
+ }, retryDelayMs);
17090
+ startResponseTimeout();
17091
+ return;
17092
+ }
17093
+ if (submitDelayMs > 0) {
17094
+ this.submitPendingUntil = Date.now() + submitDelayMs;
17095
+ }
17096
+ this.ptyProcess.write(text);
16917
17097
  const submitStartedAt = Date.now();
16918
17098
  let lastNormalizedScreen = "";
16919
17099
  let lastScreenChangeAt = submitStartedAt;
@@ -16980,10 +17160,12 @@ ${data.message || ""}`.trim();
16980
17160
  }
16981
17161
  }
16982
17162
  clearHistory() {
16983
- this.messages = [];
16984
- this.structuredMessages = [];
17163
+ this.committedMessages = [];
17164
+ this.syncMessageViews();
16985
17165
  this.accumulatedBuffer = "";
16986
17166
  this.accumulatedRawBuffer = "";
17167
+ this.terminalHistory = "";
17168
+ this.currentTurnScope = null;
16987
17169
  this.submitRetryUsed = false;
16988
17170
  this.submitRetryPromptSnippet = "";
16989
17171
  this.terminalScreen.reset();
@@ -17037,9 +17219,12 @@ ${data.message || ""}`.trim();
17037
17219
  spawnAt: this.spawnAt,
17038
17220
  workingDir: this.workingDir,
17039
17221
  messages: this.messages.slice(-20),
17222
+ committedMessages: this.committedMessages.slice(-20),
17040
17223
  structuredMessages: this.structuredMessages.slice(-20),
17041
- messageCount: this.messages.length,
17224
+ messageCount: this.committedMessages.length,
17042
17225
  screenText: this.terminalScreen.getText().slice(-4e3),
17226
+ terminalHistory: this.terminalHistory.slice(-8e3),
17227
+ currentTurnScope: this.currentTurnScope,
17043
17228
  startupBuffer: this.startupBuffer.slice(-4e3),
17044
17229
  recentOutputBuffer: this.recentOutputBuffer.slice(-500),
17045
17230
  settledBuffer: this.settledBuffer.slice(-500),
@@ -17052,6 +17237,7 @@ ${data.message || ""}`.trim();
17052
17237
  lastApprovalResolvedAt: this.lastApprovalResolvedAt,
17053
17238
  sendDelayMs: this.sendDelayMs,
17054
17239
  sendKey: this.sendKey,
17240
+ submitStrategy: this.submitStrategy,
17055
17241
  submitPendingUntil: this.submitPendingUntil,
17056
17242
  responseSettleIgnoreUntil: this.responseSettleIgnoreUntil,
17057
17243
  resizeSuppressUntil: this.resizeSuppressUntil,
@@ -17124,31 +17310,12 @@ var init_cli_provider_instance = __esm({
17124
17310
  async onTick() {
17125
17311
  }
17126
17312
  getState() {
17127
- const rawStatus = this.adapter.getStatus();
17128
- const parsedStatus = this.adapter.getScriptParsedStatus();
17129
- const adapterStatus = parsedStatus ? {
17130
- ...rawStatus,
17131
- messages: parsedStatus.messages || rawStatus.messages,
17132
- activeModal: parsedStatus.activeModal || rawStatus.activeModal
17133
- } : rawStatus;
17313
+ const adapterStatus = this.adapter.getStatus();
17134
17314
  const dirName = this.workingDir.split("/").filter(Boolean).pop() || "session";
17135
17315
  const recentMessages = adapterStatus.messages.slice(-50).map((m) => {
17136
17316
  const content = typeof m.content === "string" && m.content.length > 8e3 ? m.content.slice(0, 8e3) + "\n... (truncated)" : m.content;
17137
17317
  return { ...m, content };
17138
17318
  });
17139
- const partial2 = this.adapter.getPartialResponse();
17140
- const shouldAppendRawPartial = !parsedStatus;
17141
- if (shouldAppendRawPartial && adapterStatus.status === "generating" && partial2) {
17142
- const cleaned = partial2.trim();
17143
- if (cleaned && cleaned !== "(generating...)") {
17144
- recentMessages.push({
17145
- role: "assistant",
17146
- content: (cleaned.length > 8e3 ? cleaned.slice(0, 8e3) + "..." : cleaned) + "...",
17147
- timestamp: Date.now(),
17148
- meta: { streaming: true }
17149
- });
17150
- }
17151
- }
17152
17319
  if (recentMessages.length > 0) {
17153
17320
  const dirName2 = this.workingDir.split("/").filter(Boolean).pop() || "session";
17154
17321
  this.historyWriter.appendNewMessages(
@@ -17158,6 +17325,14 @@ var init_cli_provider_instance = __esm({
17158
17325
  this.instanceId
17159
17326
  );
17160
17327
  }
17328
+ if (adapterStatus.terminalHistory?.trim()) {
17329
+ this.historyWriter.appendTerminalHistory(
17330
+ this.type,
17331
+ adapterStatus.terminalHistory,
17332
+ `${this.provider.name} \xB7 ${dirName}`,
17333
+ this.instanceId
17334
+ );
17335
+ }
17161
17336
  return {
17162
17337
  type: this.type,
17163
17338
  name: this.provider.name,
@@ -17170,6 +17345,7 @@ var init_cli_provider_instance = __esm({
17170
17345
  status: adapterStatus.status,
17171
17346
  messages: recentMessages,
17172
17347
  activeModal: adapterStatus.activeModal,
17348
+ terminalHistory: adapterStatus.terminalHistory,
17173
17349
  inputContent: ""
17174
17350
  },
17175
17351
  workspace: this.workingDir,
@@ -35652,7 +35828,8 @@ async function detectAllVersions(loader, archive) {
35652
35828
  binary: null,
35653
35829
  detectedAt: (/* @__PURE__ */ new Date()).toISOString()
35654
35830
  };
35655
- const versionCommand = provider.versionCommand;
35831
+ const verCmdConfig = provider.versionCommand;
35832
+ const versionCommand = typeof verCmdConfig === "object" && verCmdConfig !== null ? verCmdConfig[currentOs] : verCmdConfig;
35656
35833
  if (provider.category === "ide") {
35657
35834
  const osPaths = provider.paths?.[currentOs] || [];
35658
35835
  const appPath = checkPathExists2(osPaths);
@@ -37137,11 +37314,7 @@ var init_dev_server = __esm({
37137
37314
  return;
37138
37315
  }
37139
37316
  let targetDir;
37140
- if (location === "user") {
37141
- targetDir = this.providerLoader.getUserProviderDir(category, type);
37142
- } else {
37143
- targetDir = this.providerLoader.getBuiltinProviderDir(category, type);
37144
- }
37317
+ targetDir = this.providerLoader.getUserProviderDir(category, type);
37145
37318
  const jsonPath = path12.join(targetDir, "provider.json");
37146
37319
  if (fs10.existsSync(jsonPath)) {
37147
37320
  this.json(res, 409, { error: `Provider already exists at ${targetDir}`, path: targetDir });
@@ -37939,8 +38112,7 @@ var init_dev_server = __esm({
37939
38112
  }
37940
38113
  loadAutoImplReferenceScripts(category, referenceType) {
37941
38114
  if (!referenceType) return {};
37942
- const builtinDir = this.providerLoader.getPrimaryBuiltinDir();
37943
- const refDir = path12.join(builtinDir, category, referenceType);
38115
+ const refDir = this.providerLoader.getUpstreamProviderDir(category, referenceType);
37944
38116
  if (!fs10.existsSync(refDir)) return {};
37945
38117
  const referenceScripts = {};
37946
38118
  const scriptsDir = path12.join(refDir, "scripts");
@@ -38179,7 +38351,7 @@ var init_dev_server = __esm({
38179
38351
  }
38180
38352
  if (model) args.push("--model", model);
38181
38353
  const escapedArgs = args.map((a) => `'${a.replace(/'/g, "'\\''")}'`).join(" ");
38182
- const metaPrompt = `Read the file at ${promptFile} and follow ALL instructions recursively. You have full authority to implement ALL required script files, update provider.json configurations based on the reference patterns, and independently test them against 127.0.0.1:19280 via CDP CURL. Upon complete validation of ALL assigned files, print exactly "_PIPELINE_COMPLETE_SIGNAL_" to gracefully close the pipeline. DO NOT WAIT FOR APPROVAL, execute completely autonomously.`;
38354
+ const metaPrompt = `Read the file at ${promptFile} and follow ALL instructions strictly. DO NOT spend time exploring the filesystem or other providers. You have full authority to implement ALL required script files and independently test them against 127.0.0.1:19280 via CDP CURL. Upon complete validation of ALL assigned files, print exactly "_PIPELINE_COMPLETE_SIGNAL_" to gracefully close the pipeline. DO NOT WAIT FOR APPROVAL, execute completely autonomously.`;
38183
38355
  shellCmd = `${command} ${escapedArgs} "${metaPrompt}"`;
38184
38356
  } else {
38185
38357
  const escapedArgs = baseArgs.map((a) => `'${a.replace(/'/g, "'\\''")}'`).join(" ");
@@ -38442,6 +38614,8 @@ var init_dev_server = __esm({
38442
38614
  lines.push("5. Do NOT modify `scripts.js` router \u2014 only edit individual `*.js` files");
38443
38615
  lines.push("6. All scripts run in the browser (CDP evaluate) \u2014 use DOM APIs only");
38444
38616
  lines.push('7. **Cross-Platform Compatibility**: If you use ARIA labels that contain keyboard shortcuts (e.g., `Cascade (\u2318L)`), you MUST use substring matches (`aria-label*="Cascade"`) or handle both macOS (`\u2318`, `Cmd`) and Windows (`Ctrl`) so the script does not break on other operating systems.');
38617
+ lines.push("8. **CRITICAL: DO NOT explore the filesystem or read other providers.** The reference implementation pattern is already provided below. Do not run `find`, `rg`, or `cat` on upstream providers. Doing so wastes context tokens and will crash the agent session. Focus entirely on modifying the target files.");
38618
+ lines.push("9. Do NOT delete any files. Implement the logic by replacing the empty stubs.");
38445
38619
  lines.push("");
38446
38620
  lines.push("## Required Return Format");
38447
38621
  lines.push("| Function | Return JSON |");
@@ -40586,7 +40760,7 @@ var init_adhdev_daemon = __esm({
40586
40760
  fs12 = __toESM(require("fs"));
40587
40761
  path14 = __toESM(require("path"));
40588
40762
  import_chalk2 = __toESM(require("chalk"));
40589
- pkgVersion = "0.6.57";
40763
+ pkgVersion = "0.6.58";
40590
40764
  if (pkgVersion === "unknown") {
40591
40765
  try {
40592
40766
  const possiblePaths = [