@schoolai/shipyard 3.30.0 → 3.31.0-rc.20260915.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.
@@ -12,7 +12,7 @@ import {
12
12
  guardedSubscribe,
13
13
  makeInitialAttemptState,
14
14
  shutdownFileWatcherGuard
15
- } from "./chunk-WO5EM3BP.js";
15
+ } from "./chunk-5ZR72FWA.js";
16
16
  import {
17
17
  TRAILER_SCHEMA_VERSION,
18
18
  appendTrailerToMessage,
@@ -40,13 +40,13 @@ import {
40
40
  startPlanBackfillForDaemon,
41
41
  sync,
42
42
  validatePeerId
43
- } from "./chunk-JM2E5QZ5.js";
43
+ } from "./chunk-KWDGZXQH.js";
44
44
  import {
45
45
  loadAuthToken
46
46
  } from "./chunk-XPYW5WQS.js";
47
47
  import {
48
48
  getDaemonVersion
49
- } from "./chunk-RGVTFZDF.js";
49
+ } from "./chunk-WWO24OO4.js";
50
50
  import {
51
51
  collectPriorCrashDetail,
52
52
  getRecentWasmPanicMessages
@@ -188,7 +188,7 @@ import {
188
188
  unresolveReviewThread,
189
189
  withLabelAsync,
190
190
  writeCursorApiKeyToVault
191
- } from "./chunk-ZSMWOXEN.js";
191
+ } from "./chunk-GRJGV64D.js";
192
192
  import {
193
193
  classifySkill,
194
194
  detectSkills,
@@ -256,7 +256,7 @@ import {
256
256
  createAssetResolver,
257
257
  toSdkContent,
258
258
  toSdkPermissionMode
259
- } from "./chunk-CW2PKTA6.js";
259
+ } from "./chunk-3RWQ7G4S.js";
260
260
  import {
261
261
  AGENT_IDS,
262
262
  AGENT_SYSTEM_CLAUDE_CODE,
@@ -465,7 +465,7 @@ import {
465
465
  unsafeAssertSourceId,
466
466
  vizFileExtension,
467
467
  withPreferredRuntimeAuthMethod
468
- } from "./chunk-22TVFTWD.js";
468
+ } from "./chunk-JTOJZZT2.js";
469
469
  import {
470
470
  AuthGitHubCallbackRequestSchema,
471
471
  AuthGitHubCallbackResponseSchema,
@@ -554,7 +554,7 @@ import "./chunk-2H7UOFLK.js";
554
554
  // src/services/serve.ts
555
555
  import { mkdir as mkdir48, realpath as realpath7 } from "fs/promises";
556
556
  import { homedir as homedir17 } from "os";
557
- import { join as join93 } from "path";
557
+ import { join as join94 } from "path";
558
558
  import { query as query2 } from "@anthropic-ai/claude-agent-sdk";
559
559
 
560
560
  // ../../node_modules/.pnpm/@levischuck+tiny-cbor@0.3.2/node_modules/@levischuck/tiny-cbor/esm/cbor/cbor_internal.js
@@ -6067,7 +6067,7 @@ function nanoid(size = 21) {
6067
6067
  }
6068
6068
 
6069
6069
  // src/services/bootstrap/signaling.ts
6070
- var DAEMON_NPM_VERSION = true ? "3.30.0" : "unknown";
6070
+ var DAEMON_NPM_VERSION = true ? "3.31.0" : "unknown";
6071
6071
  function createDaemonSignaling(config) {
6072
6072
  const agentId = config.agentId ?? nanoid();
6073
6073
  function send(msg) {
@@ -34704,7 +34704,7 @@ function buildCollabRoomManager(deps) {
34704
34704
  // src/services/serve-factory.ts
34705
34705
  import { randomUUID as randomUUID27 } from "crypto";
34706
34706
  import { mkdir as mkdir40 } from "fs/promises";
34707
- import { join as join85 } from "path";
34707
+ import { join as join86 } from "path";
34708
34708
  import { getHeapStatistics } from "v8";
34709
34709
 
34710
34710
  // src/shared/capabilities/cursor-boot-auth.ts
@@ -34758,8 +34758,8 @@ function getCursorHookShimPath() {
34758
34758
  function verifyCursorHookShimPresent(path8) {
34759
34759
  const resolved = path8 ?? getCursorHookShimPath();
34760
34760
  try {
34761
- const stat22 = statSync4(resolved);
34762
- if (!stat22.isFile()) return null;
34761
+ const stat23 = statSync4(resolved);
34762
+ if (!stat23.isFile()) return null;
34763
34763
  return { path: resolved };
34764
34764
  } catch {
34765
34765
  return null;
@@ -86622,9 +86622,135 @@ function buildDeliverableStore(dataDir) {
86622
86622
 
86623
86623
  // src/services/storage/jsonl-conversation-store.ts
86624
86624
  import { createReadStream as createReadStream5 } from "fs";
86625
- import { appendFile as appendFile3, mkdir as mkdir31, open as open4, readFile as readFile40, stat as stat19 } from "fs/promises";
86626
- import { join as join73 } from "path";
86625
+ import { appendFile as appendFile4, mkdir as mkdir31, open as open4, readFile as readFile41, stat as stat20 } from "fs/promises";
86626
+ import { join as join74 } from "path";
86627
86627
  import { createInterface as createInterface5 } from "readline";
86628
+
86629
+ // src/services/storage/jsonl-sdk-uuid-stamps.ts
86630
+ import { appendFile as appendFile3, readFile as readFile40, rm as rm12, stat as stat19 } from "fs/promises";
86631
+ import { join as join73 } from "path";
86632
+ var SdkUuidStampSchema = external_exports.object({
86633
+ messageId: external_exports.string(),
86634
+ sdkUuid: external_exports.string(),
86635
+ batchCorrelationIds: external_exports.array(external_exports.string()).optional()
86636
+ });
86637
+ function recoverAfterTear(line) {
86638
+ for (let i = line.indexOf("{", 1); i !== -1; i = line.indexOf("{", i + 1)) {
86639
+ try {
86640
+ return JSON.parse(line.slice(i));
86641
+ } catch {
86642
+ }
86643
+ }
86644
+ return void 0;
86645
+ }
86646
+ function parseStampLines(raw) {
86647
+ const stamps = [];
86648
+ for (const line of raw.split("\n")) {
86649
+ if (line.length === 0) continue;
86650
+ let json;
86651
+ try {
86652
+ json = JSON.parse(line);
86653
+ } catch {
86654
+ json = recoverAfterTear(line);
86655
+ if (json === void 0) continue;
86656
+ }
86657
+ const parsed = SdkUuidStampSchema.safeParse(json);
86658
+ if (parsed.success) stamps.push(parsed.data);
86659
+ }
86660
+ return stamps;
86661
+ }
86662
+ function serializeStamp(stamp) {
86663
+ return `${JSON.stringify(stamp)}
86664
+ `;
86665
+ }
86666
+ function applySdkUuidStamps(messages, stamps) {
86667
+ if (stamps.length === 0) return messages;
86668
+ const byMessageId = /* @__PURE__ */ new Map();
86669
+ for (const stamp of stamps) byMessageId.set(stamp.messageId, stamp);
86670
+ const overlay = (message) => {
86671
+ const stamp = byMessageId.get(message.messageId);
86672
+ if (!stamp) return null;
86673
+ const patch = {};
86674
+ if (!message.sdkUuid) patch.sdkUuid = stamp.sdkUuid;
86675
+ const batch = stamp.batchCorrelationIds;
86676
+ if (batch && batch.length > 0 && !message.batchCorrelationIds)
86677
+ patch.batchCorrelationIds = [...batch];
86678
+ return Object.keys(patch).length > 0 ? patch : null;
86679
+ };
86680
+ if (!messages.some((message) => overlay(message) !== null)) return messages;
86681
+ return messages.map((message) => {
86682
+ const patch = overlay(message);
86683
+ return patch === null ? message : { ...message, ...patch };
86684
+ });
86685
+ }
86686
+ var EMPTY_STAMPS = Object.freeze([]);
86687
+ var MAX_STAMPS_CACHE_ENTRIES = 512;
86688
+ function createSdkUuidStampSidecar(channelsDir) {
86689
+ const cache2 = /* @__PURE__ */ new Map();
86690
+ function path8(channelId) {
86691
+ return join73(channelsDir, `${channelId}.stamps.jsonl`);
86692
+ }
86693
+ function remember(channelId, entry) {
86694
+ cache2.delete(channelId);
86695
+ cache2.set(channelId, entry);
86696
+ while (cache2.size > MAX_STAMPS_CACHE_ENTRIES) {
86697
+ const oldest = cache2.keys().next();
86698
+ if (oldest.done === true) break;
86699
+ cache2.delete(oldest.value);
86700
+ }
86701
+ }
86702
+ return {
86703
+ path: path8,
86704
+ async read(channelId) {
86705
+ const target = path8(channelId);
86706
+ let fileStat;
86707
+ try {
86708
+ const s2 = await stat19(target);
86709
+ fileStat = { size: s2.size, mtimeMs: s2.mtimeMs };
86710
+ } catch (err3) {
86711
+ if (!isEnoent(err3)) throw err3;
86712
+ cache2.delete(channelId);
86713
+ return { stamps: EMPTY_STAMPS, size: 0, mtimeMs: 0 };
86714
+ }
86715
+ if (fileStat.size === 0) {
86716
+ cache2.delete(channelId);
86717
+ return { stamps: EMPTY_STAMPS, size: 0, mtimeMs: 0 };
86718
+ }
86719
+ const hit = cache2.get(channelId);
86720
+ if (hit && hit.size === fileStat.size && hit.mtimeMs === fileStat.mtimeMs) {
86721
+ return { stamps: hit.stamps, size: hit.size, mtimeMs: hit.mtimeMs };
86722
+ }
86723
+ let raw;
86724
+ try {
86725
+ raw = await readFile40(target, "utf-8");
86726
+ } catch (err3) {
86727
+ if (isEnoent(err3)) return { stamps: EMPTY_STAMPS, size: 0, mtimeMs: 0 };
86728
+ throw err3;
86729
+ }
86730
+ const stamps = parseStampLines(raw);
86731
+ remember(channelId, { size: fileStat.size, mtimeMs: fileStat.mtimeMs, stamps });
86732
+ return { stamps, size: fileStat.size, mtimeMs: fileStat.mtimeMs };
86733
+ },
86734
+ async append(channelId, stamp) {
86735
+ await appendFile3(path8(channelId), serializeStamp(stamp), "utf-8");
86736
+ },
86737
+ async discard(channelId) {
86738
+ cache2.delete(channelId);
86739
+ try {
86740
+ await rm12(path8(channelId));
86741
+ return true;
86742
+ } catch (err3) {
86743
+ if (isEnoent(err3)) return false;
86744
+ throw err3;
86745
+ }
86746
+ },
86747
+ cachedChannelCount() {
86748
+ return cache2.size;
86749
+ }
86750
+ };
86751
+ }
86752
+
86753
+ // src/services/storage/jsonl-conversation-store.ts
86628
86754
  var StoredMessageSchema = MessageSchema.omit({ seqNo: true, channelId: true });
86629
86755
  function logPerf(entry) {
86630
86756
  try {
@@ -86641,7 +86767,7 @@ function computeReadCacheBudgetBytes(heapSizeLimitBytes) {
86641
86767
  return Math.min(READ_CACHE_BUDGET_CAP_BYTES, Math.max(DEFAULT_READ_CACHE_BUDGET_BYTES, scaled));
86642
86768
  }
86643
86769
  function buildJsonlConversationStore(dataDir, opts = {}) {
86644
- const channelsDir = join73(dataDir, "channels");
86770
+ const channelsDir = join74(dataDir, "channels");
86645
86771
  const seqCounters = /* @__PURE__ */ new Map();
86646
86772
  const channelQueues = /* @__PURE__ */ new Map();
86647
86773
  const readCache = /* @__PURE__ */ new Map();
@@ -86686,8 +86812,9 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86686
86812
  }
86687
86813
  const turnCountCache = /* @__PURE__ */ new Map();
86688
86814
  function channelPath(channelId) {
86689
- return join73(channelsDir, `${channelId}.jsonl`);
86815
+ return join74(channelsDir, `${channelId}.jsonl`);
86690
86816
  }
86817
+ const stampSidecar = createSdkUuidStampSidecar(channelsDir);
86691
86818
  function countRuns(messages) {
86692
86819
  let turns = 0;
86693
86820
  let prev = null;
@@ -86747,9 +86874,10 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86747
86874
  async function readLines(channelId) {
86748
86875
  const startedAt = Date.now();
86749
86876
  logPerf({ event: "perf_jsonl_read_start", channelId });
86877
+ const stamps = await stampSidecar.read(channelId);
86750
86878
  let raw;
86751
86879
  try {
86752
- raw = await readFile40(channelPath(channelId), "utf-8");
86880
+ raw = await readFile41(channelPath(channelId), "utf-8");
86753
86881
  } catch (err3) {
86754
86882
  if (!isEnoent(err3)) throw err3;
86755
86883
  logPerf({
@@ -86759,9 +86887,9 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86759
86887
  linesParsed: 0,
86760
86888
  durationMs: Date.now() - startedAt
86761
86889
  });
86762
- return [];
86890
+ return { messages: [], stampsSize: stamps.size, stampsMtimeMs: stamps.mtimeMs };
86763
86891
  }
86764
- const messages = parseJsonlBlob(raw, channelId);
86892
+ const messages = applySdkUuidStamps(parseJsonlBlob(raw, channelId), stamps.stamps);
86765
86893
  logPerf({
86766
86894
  event: "perf_jsonl_read_done",
86767
86895
  channelId,
@@ -86769,7 +86897,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86769
86897
  linesParsed: messages.length,
86770
86898
  durationMs: Date.now() - startedAt
86771
86899
  });
86772
- return messages;
86900
+ return { messages, stampsSize: stamps.size, stampsMtimeMs: stamps.mtimeMs };
86773
86901
  }
86774
86902
  async function countLinesInFile(path8) {
86775
86903
  let fh;
@@ -86858,23 +86986,31 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86858
86986
  const startSeqNo = totalLines - tailLines2.length;
86859
86987
  const messages = parseTailLines(tailLines2, startSeqNo, channelId);
86860
86988
  if (messages === null) return null;
86861
- return { messages, totalLines };
86989
+ const stamps = await stampSidecar.read(channelId);
86990
+ return { messages: applySdkUuidStamps(messages, stamps.stamps), totalLines };
86862
86991
  } finally {
86863
86992
  await fh.close();
86864
86993
  }
86865
86994
  }
86866
86995
  async function statFreshness(path8) {
86867
86996
  try {
86868
- const s2 = await stat19(path8);
86997
+ const s2 = await stat20(path8);
86869
86998
  return { size: s2.size, mtimeMs: s2.mtimeMs };
86870
86999
  } catch (err3) {
86871
87000
  if (isEnoent(err3)) return null;
86872
87001
  throw err3;
86873
87002
  }
86874
87003
  }
86875
- function readTailFromCache(channelId, limit, fileStat) {
87004
+ function isCacheEntryFresh(entry, fileStat, stampsStat) {
87005
+ return entry.size === fileStat.size && entry.mtimeMs === fileStat.mtimeMs && entry.stampsSize === stampsStat.size && entry.stampsMtimeMs === stampsStat.mtimeMs;
87006
+ }
87007
+ function readTailFromCache(channelId, limit, fileStat, stampsStat) {
86876
87008
  const hit = readCache.get(channelId);
86877
- if (!hit || hit.size !== fileStat.size || hit.mtimeMs !== fileStat.mtimeMs) return null;
87009
+ if (!hit) return null;
87010
+ if (!isCacheEntryFresh(hit, fileStat, stampsStat)) {
87011
+ dropCacheEntry(channelId);
87012
+ return null;
87013
+ }
86878
87014
  touchCacheEntry(channelId, hit);
86879
87015
  const tail = hit.messages.length <= limit ? [...hit.messages] : hit.messages.slice(-limit);
86880
87016
  return { messages: tail, totalLines: hit.messages.length };
@@ -86883,7 +87019,8 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86883
87019
  if (limit <= 0) return { messages: [], totalLines: 0 };
86884
87020
  const fileStat = await statFreshness(channelPath(channelId));
86885
87021
  if (fileStat === null || fileStat.size === 0) return { messages: [], totalLines: 0 };
86886
- const cached = readTailFromCache(channelId, limit, fileStat);
87022
+ const stampsStat = await stampSidecar.read(channelId);
87023
+ const cached = readTailFromCache(channelId, limit, fileStat, stampsStat);
86887
87024
  if (cached !== null) return cached;
86888
87025
  if (fileStat.size <= 256 * 1024) {
86889
87026
  const all = await readLinesCached(channelId);
@@ -86896,24 +87033,29 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86896
87033
  const path8 = channelPath(channelId);
86897
87034
  let fileStat = null;
86898
87035
  try {
86899
- const s2 = await stat19(path8);
87036
+ const s2 = await stat20(path8);
86900
87037
  fileStat = { size: s2.size, mtimeMs: s2.mtimeMs };
86901
87038
  } catch (err3) {
86902
87039
  if (isEnoent(err3)) return [];
86903
87040
  throw err3;
86904
87041
  }
87042
+ const stampsStat = await stampSidecar.read(channelId);
86905
87043
  const hit = readCache.get(channelId);
86906
- if (hit && hit.size === fileStat.size && hit.mtimeMs === fileStat.mtimeMs) {
87044
+ if (hit && isCacheEntryFresh(hit, fileStat, stampsStat)) {
86907
87045
  touchCacheEntry(channelId, hit);
86908
87046
  return [...hit.messages];
86909
87047
  }
87048
+ if (hit) dropCacheEntry(channelId);
86910
87049
  const fresh = await readLines(channelId);
87050
+ await opts._testHooks?.onAfterReadBeforeCachePopulate?.();
86911
87051
  setCacheEntry(channelId, {
86912
- messages: fresh,
87052
+ messages: fresh.messages,
86913
87053
  size: fileStat.size,
86914
- mtimeMs: fileStat.mtimeMs
87054
+ mtimeMs: fileStat.mtimeMs,
87055
+ stampsSize: fresh.stampsSize,
87056
+ stampsMtimeMs: fresh.stampsMtimeMs
86915
87057
  });
86916
- return [...fresh];
87058
+ return [...fresh.messages];
86917
87059
  }
86918
87060
  function pushIntoLiveCache(channelId, appended, fileStat) {
86919
87061
  const liveHit = readCache.get(channelId);
@@ -86932,7 +87074,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
86932
87074
  async function refreshCacheAfterAppend(channelId, appended) {
86933
87075
  if (!readCache.get(channelId)) return;
86934
87076
  try {
86935
- const s2 = await stat19(channelPath(channelId));
87077
+ const s2 = await stat20(channelPath(channelId));
86936
87078
  await opts._testHooks?.onAfterStatBeforePush?.();
86937
87079
  pushIntoLiveCache(channelId, appended, { size: s2.size, mtimeMs: s2.mtimeMs });
86938
87080
  } catch (err3) {
@@ -87026,7 +87168,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87026
87168
  seqCounters.set(message.channelId, seqNo);
87027
87169
  const { channelId: _channelId, ...rest } = message;
87028
87170
  const line = JSON.stringify(rest);
87029
- await appendFile3(channelPath(message.channelId), `${line}
87171
+ await appendFile4(channelPath(message.channelId), `${line}
87030
87172
  `, "utf-8");
87031
87173
  await refreshCacheAfterAppend(message.channelId, {
87032
87174
  ...rest,
@@ -87080,7 +87222,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87080
87222
  lines.push(JSON.stringify(rest));
87081
87223
  cacheUpdates.push({ ...rest, channelId, seqNo });
87082
87224
  }
87083
- await appendFile3(channelPath(channelId), `${lines.join("\n")}
87225
+ await appendFile4(channelPath(channelId), `${lines.join("\n")}
87084
87226
  `, "utf-8");
87085
87227
  seqCounters.set(channelId, startSeqNo + messages.length - 1);
87086
87228
  await refreshCacheAfterAppend(channelId, cacheUpdates);
@@ -87125,7 +87267,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87125
87267
  seqCounters.set(message.channelId, decision.seqNo);
87126
87268
  const { channelId: _channelId, ...rest } = message;
87127
87269
  const line = JSON.stringify(rest);
87128
- await appendFile3(channelPath(message.channelId), `${line}
87270
+ await appendFile4(channelPath(message.channelId), `${line}
87129
87271
  `, "utf-8");
87130
87272
  await refreshCacheAfterAppend(message.channelId, {
87131
87273
  ...rest,
@@ -87145,7 +87287,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87145
87287
  channelQueues.set(message.channelId, next);
87146
87288
  return resultPromise;
87147
87289
  },
87148
- async stampSdkUuid(channelId, primaryCorrelationId, sdkUuid, batchCorrelationIds) {
87290
+ async stampSdkUuid(channelId, messageId, sdkUuid, batchCorrelationIds) {
87149
87291
  let resolveVoid;
87150
87292
  let rejectVoid;
87151
87293
  const voidPromise = new Promise((resolve15, reject) => {
@@ -87154,30 +87296,13 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87154
87296
  });
87155
87297
  const prev = channelQueues.get(channelId) ?? Promise.resolve();
87156
87298
  const next = prev.then(async () => {
87157
- const messages = await readLines(channelId);
87158
- const target = messages.find(
87159
- (m2) => m2.senderKind === "human" && m2.correlationId === primaryCorrelationId && !m2.sdkUuid
87160
- );
87161
- if (!target) {
87162
- resolveVoid();
87163
- return;
87164
- }
87299
+ await ensureDir();
87165
87300
  const secondaryIds = batchCorrelationIds && batchCorrelationIds.length > 0 ? batchCorrelationIds : void 0;
87166
- const lines = messages.map((m2) => {
87167
- const { seqNo: _seqNo, channelId: _channelId, ...rest } = m2;
87168
- if (m2.seqNo === target.seqNo) {
87169
- return JSON.stringify({
87170
- ...rest,
87171
- sdkUuid,
87172
- ...secondaryIds ? { batchCorrelationIds: secondaryIds } : {}
87173
- });
87174
- }
87175
- return JSON.stringify(rest);
87301
+ await stampSidecar.append(channelId, {
87302
+ messageId,
87303
+ sdkUuid,
87304
+ ...secondaryIds ? { batchCorrelationIds: secondaryIds } : {}
87176
87305
  });
87177
- const content = lines.length > 0 ? `${lines.join("\n")}
87178
- ` : "";
87179
- const filePath = channelPath(channelId);
87180
- await atomicWriteFile(filePath, content);
87181
87306
  dropCacheEntry(channelId);
87182
87307
  resolveVoid();
87183
87308
  }).catch((err3) => {
@@ -87245,7 +87370,7 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87245
87370
  });
87246
87371
  const prev = channelQueues.get(channelId) ?? Promise.resolve();
87247
87372
  const next = prev.then(async () => {
87248
- const messages = await readLines(channelId);
87373
+ const { messages } = await readLines(channelId);
87249
87374
  const kept = messages.filter((m2) => m2.seqNo <= targetSeqNo);
87250
87375
  const removed = messages.length - kept.length;
87251
87376
  if (removed === 0) {
@@ -87263,6 +87388,13 @@ function buildJsonlConversationStore(dataDir, opts = {}) {
87263
87388
  await atomicWriteFile(filePath, content);
87264
87389
  seqCounters.set(channelId, kept.length > 0 ? kept.length - 1 : -1);
87265
87390
  dropCacheEntry(channelId);
87391
+ const discardedStamps = await stampSidecar.discard(channelId);
87392
+ logPerf({
87393
+ event: "perf_jsonl_stamps_discarded",
87394
+ channelId,
87395
+ existed: discardedStamps,
87396
+ keptLines: kept.length
87397
+ });
87266
87398
  resolveCount(removed);
87267
87399
  }).catch((err3) => {
87268
87400
  dropCacheEntry(channelId);
@@ -87326,8 +87458,8 @@ function buildObservableConversationStore(inner) {
87326
87458
  }
87327
87459
  return result;
87328
87460
  },
87329
- stampSdkUuid(channelId, correlationId, sdkUuid, batchCorrelationIds) {
87330
- return inner.stampSdkUuid(channelId, correlationId, sdkUuid, batchCorrelationIds);
87461
+ stampSdkUuid(channelId, messageId, sdkUuid, batchCorrelationIds) {
87462
+ return inner.stampSdkUuid(channelId, messageId, sdkUuid, batchCorrelationIds);
87331
87463
  },
87332
87464
  countSenderTurns(channelId) {
87333
87465
  return inner.countSenderTurns(channelId);
@@ -87366,7 +87498,7 @@ function buildObservableConversationStore(inner) {
87366
87498
 
87367
87499
  // src/services/storage/projects-store.ts
87368
87500
  import { randomUUID as randomUUID21 } from "crypto";
87369
- import { mkdir as mkdir32, readFile as readFile41 } from "fs/promises";
87501
+ import { mkdir as mkdir32, readFile as readFile42 } from "fs/promises";
87370
87502
  import { dirname as dirname32 } from "path";
87371
87503
  var ProjectsArraySchema = external_exports.array(ProjectSchema);
87372
87504
  function buildProjectsStore(filePath) {
@@ -87388,7 +87520,7 @@ function buildProjectsStore(filePath) {
87388
87520
  async function readStore() {
87389
87521
  if (cache2) return cache2;
87390
87522
  try {
87391
- const raw = await readFile41(filePath, "utf-8");
87523
+ const raw = await readFile42(filePath, "utf-8");
87392
87524
  const parsed = JSON.parse(raw);
87393
87525
  const migrated = migrateProjectsStore(parsed);
87394
87526
  cache2 = migrated.projects;
@@ -87417,7 +87549,7 @@ function buildProjectsStore(filePath) {
87417
87549
  }
87418
87550
  async function readFromDisk() {
87419
87551
  try {
87420
- const raw = await readFile41(filePath, "utf-8");
87552
+ const raw = await readFile42(filePath, "utf-8");
87421
87553
  return migrateProjectsStore(JSON.parse(raw)).projects;
87422
87554
  } catch (err3) {
87423
87555
  if (isEnoent(err3)) return [];
@@ -87538,8 +87670,8 @@ function buildProjectsStore(filePath) {
87538
87670
  }
87539
87671
 
87540
87672
  // src/services/storage/rate-limit-store.ts
87541
- import { mkdir as mkdir33, readFile as readFile42 } from "fs/promises";
87542
- import { dirname as dirname33, join as join74 } from "path";
87673
+ import { mkdir as mkdir33, readFile as readFile43 } from "fs/promises";
87674
+ import { dirname as dirname33, join as join75 } from "path";
87543
87675
  var RATE_LIMIT_STORE_VERSION = 4;
87544
87676
  var RateLimitRecordSchema = external_exports.object({
87545
87677
  info: RateLimitInfoSchema,
@@ -87578,7 +87710,7 @@ function isWindowKey(x2) {
87578
87710
  return x2 !== void 0 && WINDOW_KEYS.has(x2);
87579
87711
  }
87580
87712
  async function buildRateLimitStore(dataDir, opts) {
87581
- const filePath = join74(dataDir, "rate-limits.json");
87713
+ const filePath = join75(dataDir, "rate-limits.json");
87582
87714
  const lockPath2 = `${filePath}.lock`;
87583
87715
  const initial = await loadStoreFile(filePath, opts.logger);
87584
87716
  const records = { ...initial.records };
@@ -87728,7 +87860,7 @@ function mergeEvent(prev, incoming, eventTime) {
87728
87860
  }
87729
87861
  async function loadStoreFile(filePath, logger2) {
87730
87862
  try {
87731
- const raw = await readFile42(filePath, "utf-8");
87863
+ const raw = await readFile43(filePath, "utf-8");
87732
87864
  const parsed = JSON.parse(raw);
87733
87865
  const v4 = StoreFileSchemaV4.safeParse(parsed);
87734
87866
  if (v4.success) return v4.data;
@@ -87831,8 +87963,8 @@ async function atomicWrite4(filePath, data) {
87831
87963
  }
87832
87964
 
87833
87965
  // src/services/storage/schedule-store.ts
87834
- import { mkdir as mkdir34, readFile as readFile43, writeFile as writeFile26 } from "fs/promises";
87835
- import { dirname as dirname34, join as join75 } from "path";
87966
+ import { mkdir as mkdir34, readFile as readFile44, writeFile as writeFile26 } from "fs/promises";
87967
+ import { dirname as dirname34, join as join76 } from "path";
87836
87968
  import properLockfile from "proper-lockfile";
87837
87969
  var STORE_FILE = "schedules.json";
87838
87970
  function emptyState() {
@@ -87874,7 +88006,7 @@ function notify(listeners, event) {
87874
88006
  }
87875
88007
  }
87876
88008
  function buildScheduleStore(dataDir, options = {}) {
87877
- const filePath = join75(dataDir, STORE_FILE);
88009
+ const filePath = join76(dataDir, STORE_FILE);
87878
88010
  const lockPath2 = `${filePath}.automation-lock`;
87879
88011
  const listeners = /* @__PURE__ */ new Set();
87880
88012
  const staleMs = options.lockStaleMs ?? 6e4;
@@ -87917,7 +88049,7 @@ function buildScheduleStore(dataDir, options = {}) {
87917
88049
  async function loadFromDisk() {
87918
88050
  let source;
87919
88051
  try {
87920
- source = await readFile43(filePath, "utf-8");
88052
+ source = await readFile44(filePath, "utf-8");
87921
88053
  } catch (error) {
87922
88054
  if (isEnoent(error)) return { state: emptyState(), source: null, migratedFromVersion: null };
87923
88055
  throw error;
@@ -87942,7 +88074,7 @@ function buildScheduleStore(dataDir, options = {}) {
87942
88074
  if (typeof error !== "object" || error === null || !("code" in error) || error.code !== "EEXIST") {
87943
88075
  throw error;
87944
88076
  }
87945
- const existingBackup = await readFile43(backupPath, "utf-8");
88077
+ const existingBackup = await readFile44(backupPath, "utf-8");
87946
88078
  if (existingBackup !== loaded.source) {
87947
88079
  throw new Error(`Schedule migration backup does not match source: ${backupPath}`);
87948
88080
  }
@@ -88052,8 +88184,8 @@ function buildScheduleStore(dataDir, options = {}) {
88052
88184
  }
88053
88185
 
88054
88186
  // src/services/storage/session-persistence.ts
88055
- import { mkdir as mkdir35, readdir as readdir21, readFile as readFile44, rm as rm12 } from "fs/promises";
88056
- import { join as join76 } from "path";
88187
+ import { mkdir as mkdir35, readdir as readdir21, readFile as readFile45, rm as rm13 } from "fs/promises";
88188
+ import { join as join77 } from "path";
88057
88189
  var PersistedSessionSchema = external_exports.object({
88058
88190
  sessionId: external_exports.string(),
88059
88191
  channelId: external_exports.string(),
@@ -88084,7 +88216,7 @@ var PersistedSessionSchema = external_exports.object({
88084
88216
  }));
88085
88217
  async function loadOneSessionFile(originalPath, corruptionLogger) {
88086
88218
  try {
88087
- const raw = await readFile44(originalPath, "utf-8");
88219
+ const raw = await readFile45(originalPath, "utf-8");
88088
88220
  return PersistedSessionSchema.parse(JSON.parse(raw));
88089
88221
  } catch (err3) {
88090
88222
  if (isCorruptionError(err3)) {
@@ -88110,9 +88242,9 @@ async function loadOneSessionFile(originalPath, corruptionLogger) {
88110
88242
  }
88111
88243
  }
88112
88244
  function buildSessionPersistence(dataDir, corruptionLogger) {
88113
- const channelsDir = join76(dataDir, "channels");
88245
+ const channelsDir = join77(dataDir, "channels");
88114
88246
  function sessionPath(channelId) {
88115
- return join76(channelsDir, `${channelId}.session.json`);
88247
+ return join77(channelsDir, `${channelId}.session.json`);
88116
88248
  }
88117
88249
  async function ensureDir() {
88118
88250
  await mkdir35(channelsDir, { recursive: true });
@@ -88126,7 +88258,7 @@ function buildSessionPersistence(dataDir, corruptionLogger) {
88126
88258
  async load(channelId) {
88127
88259
  const path8 = sessionPath(channelId);
88128
88260
  try {
88129
- const raw = await readFile44(path8, "utf-8");
88261
+ const raw = await readFile45(path8, "utf-8");
88130
88262
  return PersistedSessionSchema.parse(JSON.parse(raw));
88131
88263
  } catch (err3) {
88132
88264
  if (isEnoent(err3)) return null;
@@ -88146,7 +88278,7 @@ function buildSessionPersistence(dataDir, corruptionLogger) {
88146
88278
  },
88147
88279
  async clear(channelId) {
88148
88280
  try {
88149
- await rm12(sessionPath(channelId));
88281
+ await rm13(sessionPath(channelId));
88150
88282
  } catch (err3) {
88151
88283
  if (isEnoent(err3)) return;
88152
88284
  throw err3;
@@ -88170,7 +88302,7 @@ function buildSessionPersistence(dataDir, corruptionLogger) {
88170
88302
  if (i >= sessionEntries.length) return;
88171
88303
  const entry = sessionEntries[i];
88172
88304
  if (!entry) return;
88173
- results[i] = await loadOneSessionFile(join76(channelsDir, entry), corruptionLogger);
88305
+ results[i] = await loadOneSessionFile(join77(channelsDir, entry), corruptionLogger);
88174
88306
  }
88175
88307
  }
88176
88308
  const workers = Array.from(
@@ -88184,12 +88316,12 @@ function buildSessionPersistence(dataDir, corruptionLogger) {
88184
88316
  }
88185
88317
 
88186
88318
  // src/services/storage/template-store.ts
88187
- import { join as join77 } from "path";
88319
+ import { join as join78 } from "path";
88188
88320
  function buildTemplateStore(dataDir) {
88189
88321
  const store = buildJsonDocumentStore({
88190
88322
  storeName: "templates",
88191
88323
  docType: "template",
88192
- filePath: join77(dataDir, "templates.json"),
88324
+ filePath: join78(dataDir, "templates.json"),
88193
88325
  recordSchema: TaskTemplateRecordSchema,
88194
88326
  currentVersion: TEMPLATE_STORE_VERSION,
88195
88327
  migrate(raw) {
@@ -88227,7 +88359,7 @@ function buildTemplateStore(dataDir) {
88227
88359
  }
88228
88360
 
88229
88361
  // src/services/storage/user-settings-store.ts
88230
- import { mkdir as mkdir36, readFile as readFile45 } from "fs/promises";
88362
+ import { mkdir as mkdir36, readFile as readFile46 } from "fs/promises";
88231
88363
  import { dirname as dirname35 } from "path";
88232
88364
  function buildUserSettingsStore(filePath) {
88233
88365
  let cache2 = null;
@@ -88248,7 +88380,7 @@ function buildUserSettingsStore(filePath) {
88248
88380
  async function readStore() {
88249
88381
  if (cache2) return cache2;
88250
88382
  try {
88251
- const raw = await readFile45(filePath, "utf-8");
88383
+ const raw = await readFile46(filePath, "utf-8");
88252
88384
  const parsed = JSON.parse(raw);
88253
88385
  const migrated = migrateUserSettingsStore(parsed);
88254
88386
  cache2 = migrated.settings;
@@ -88295,7 +88427,7 @@ function buildUserSettingsStore(filePath) {
88295
88427
  }
88296
88428
  async function readSettingsFromDisk() {
88297
88429
  try {
88298
- const raw = await readFile45(filePath, "utf-8");
88430
+ const raw = await readFile46(filePath, "utf-8");
88299
88431
  return migrateUserSettingsStore(JSON.parse(raw)).settings;
88300
88432
  } catch (err3) {
88301
88433
  if (isEnoent(err3)) return { ...DEFAULT_USER_SETTINGS };
@@ -93614,7 +93746,11 @@ var ThreadEventProcessor = class {
93614
93746
  }
93615
93747
  this.#deps.callbacks.onMessageStored?.(result.seqNo, echoMsgId, "human", event.mark);
93616
93748
  if (meta?.correlationId) {
93617
- this.#deps.callbacks.onUserMessageConfirmed?.(meta.correlationId, event.mark);
93749
+ this.#deps.callbacks.onUserMessageConfirmed?.(
93750
+ meta.correlationId,
93751
+ event.mark,
93752
+ result.existingMessage?.messageId ?? echoMsgId
93753
+ );
93618
93754
  }
93619
93755
  }
93620
93756
  async #handleInitReceived(event) {
@@ -94847,9 +94983,9 @@ var Thread = class {
94847
94983
  // src/services/plan/plan-handler.ts
94848
94984
  import { randomUUID as randomUUID23 } from "crypto";
94849
94985
  import { existsSync as existsSync11, readdirSync as readdirSync5, statSync as statSync5 } from "fs";
94850
- import { mkdir as mkdir37, readFile as readFile47, writeFile as writeFile28 } from "fs/promises";
94986
+ import { mkdir as mkdir37, readFile as readFile48, writeFile as writeFile28 } from "fs/promises";
94851
94987
  import { homedir as homedir13 } from "os";
94852
- import { dirname as dirname37, join as join79 } from "path";
94988
+ import { dirname as dirname37, join as join80 } from "path";
94853
94989
 
94854
94990
  // src/services/plan-backfill/plan-lazy-rebuild.ts
94855
94991
  var SETTLE_BUDGET_MS = 2e3;
@@ -95022,7 +95158,7 @@ function decideWatchResolved(trigger, snapshot) {
95022
95158
  // src/services/plan/plan-file-bridge.ts
95023
95159
  import { createHash as createHash15, randomUUID as randomUUID22 } from "crypto";
95024
95160
  import { existsSync as existsSync9 } from "fs";
95025
- import { readFile as readFile46, rename as rename18, stat as stat20, writeFile as writeFile27 } from "fs/promises";
95161
+ import { readFile as readFile47, rename as rename18, stat as stat21, writeFile as writeFile27 } from "fs/promises";
95026
95162
  import { basename as basename13, dirname as dirname36 } from "path";
95027
95163
  var FILE_READ_MAX_RETRIES = 3;
95028
95164
  var FILE_READ_RETRY_BASE_MS = 200;
@@ -95439,7 +95575,7 @@ var PlanFileBridge = class _PlanFileBridge {
95439
95575
  async #existingFileSize() {
95440
95576
  if (!this.#filePath) return 0;
95441
95577
  try {
95442
- return (await stat20(this.#filePath)).size;
95578
+ return (await stat21(this.#filePath)).size;
95443
95579
  } catch {
95444
95580
  return 0;
95445
95581
  }
@@ -95448,7 +95584,7 @@ var PlanFileBridge = class _PlanFileBridge {
95448
95584
  let lastError;
95449
95585
  for (let attempt = 0; attempt < FILE_READ_MAX_RETRIES; attempt++) {
95450
95586
  try {
95451
- return await readFile46(filePath, "utf-8");
95587
+ return await readFile47(filePath, "utf-8");
95452
95588
  } catch (err3) {
95453
95589
  lastError = err3;
95454
95590
  const msg = err3 instanceof Error ? err3.message : String(err3);
@@ -95728,8 +95864,8 @@ function greedyLCS(a, b2) {
95728
95864
  // src/services/plan/plan-file-watcher.ts
95729
95865
  import { existsSync as existsSync10 } from "fs";
95730
95866
  import { homedir as homedir12 } from "os";
95731
- import { join as join78 } from "path";
95732
- var DEFAULT_PLANS_DIR = join78(homedir12(), ".claude", "plans");
95867
+ import { join as join79 } from "path";
95868
+ var DEFAULT_PLANS_DIR = join79(homedir12(), ".claude", "plans");
95733
95869
  var PLAN_WATCH_TIMEOUT_MS = 1e4;
95734
95870
  var PLAN_WATCH_DEBOUNCE_MS = 250;
95735
95871
  function createPlanFileWatcher(deps) {
@@ -96364,7 +96500,7 @@ var PlanHandler = class {
96364
96500
  }
96365
96501
  async #readFileForRehydrate(filePath) {
96366
96502
  try {
96367
- return await readFile47(filePath, "utf-8");
96503
+ return await readFile48(filePath, "utf-8");
96368
96504
  } catch (err3) {
96369
96505
  this.#deps.log({
96370
96506
  event: "plan_bridge_rehydrate_read_failed",
@@ -96511,7 +96647,7 @@ var PlanHandler = class {
96511
96647
  * Called when a Write tool result mentions a file in ~/.claude/plans/.
96512
96648
  */
96513
96649
  trackCreatedFile(filePath) {
96514
- const plansDir = join79(homedir13(), ".claude", "plans");
96650
+ const plansDir = join80(homedir13(), ".claude", "plans");
96515
96651
  if (filePath.startsWith(plansDir) && filePath.endsWith(".md")) {
96516
96652
  this.#createdPlanFiles.add(filePath);
96517
96653
  this.#deps.log({
@@ -96605,7 +96741,7 @@ var PlanHandler = class {
96605
96741
  this.#assertNativePlanOwner(threadId);
96606
96742
  this.#nativeThreadId = threadId;
96607
96743
  this.#nativeRevisionPending = true;
96608
- const filePath = join79(getShipyardHome(), "plans", `${this.#deps.taskId}.md`);
96744
+ const filePath = join80(getShipyardHome(), "plans", `${this.#deps.taskId}.md`);
96609
96745
  try {
96610
96746
  await mkdir37(dirname37(filePath), { recursive: true });
96611
96747
  await writeFile28(filePath, content, "utf-8");
@@ -97129,12 +97265,12 @@ var PlanHandler = class {
97129
97265
  }).filter((f2) => f2 !== null).sort((a, b2) => b2.mtime - a.mtime)[0];
97130
97266
  return newest?.path ?? null;
97131
97267
  }
97132
- const plansDir = join79(homedir13(), ".claude", "plans");
97268
+ const plansDir = join80(homedir13(), ".claude", "plans");
97133
97269
  if (!existsSync11(plansDir)) return null;
97134
97270
  try {
97135
97271
  const files = readdirSync5(plansDir).filter((f2) => f2.endsWith(".md")).map((f2) => ({
97136
- path: join79(plansDir, f2),
97137
- mtime: statSync5(join79(plansDir, f2)).mtimeMs
97272
+ path: join80(plansDir, f2),
97273
+ mtime: statSync5(join80(plansDir, f2)).mtimeMs
97138
97274
  })).sort((a, b2) => b2.mtime - a.mtime);
97139
97275
  const recent = files[0];
97140
97276
  if (recent && Date.now() - recent.mtime < 3e4) return recent.path;
@@ -99687,8 +99823,8 @@ var RewindCheckpointHandler = class _RewindCheckpointHandler {
99687
99823
  };
99688
99824
 
99689
99825
  // src/services/task/side-thread-registry.ts
99690
- import { mkdir as mkdir38, readFile as readFile48, rename as rename19, writeFile as writeFile29 } from "fs/promises";
99691
- import { dirname as dirname38, join as join80 } from "path";
99826
+ import { mkdir as mkdir38, readFile as readFile49, rename as rename19, writeFile as writeFile29 } from "fs/promises";
99827
+ import { dirname as dirname38, join as join81 } from "path";
99692
99828
  var ThreadFileSchema = external_exports.object({
99693
99829
  threads: external_exports.record(external_exports.string(), ThreadMetadataSchema)
99694
99830
  });
@@ -100207,7 +100343,7 @@ var SideThreadRegistry = class {
100207
100343
  }
100208
100344
  /** Persistence */
100209
100345
  #filePath() {
100210
- return join80(this.#deps.dataDir, "threads", `${this.#deps.taskId}.json`);
100346
+ return join81(this.#deps.dataDir, "threads", `${this.#deps.taskId}.json`);
100211
100347
  }
100212
100348
  async #ensureLoaded() {
100213
100349
  if (this.#loadedFromDisk.has(this.#deps.taskId)) return;
@@ -100227,7 +100363,7 @@ var SideThreadRegistry = class {
100227
100363
  const filePath = this.#filePath();
100228
100364
  let raw;
100229
100365
  try {
100230
- raw = await readFile48(filePath, "utf-8");
100366
+ raw = await readFile49(filePath, "utf-8");
100231
100367
  } catch (err3) {
100232
100368
  if (isEnoent(err3)) return;
100233
100369
  throw err3;
@@ -103317,9 +103453,9 @@ function buildProfileRewindCapability(resolve15, runtimeId, primary) {
103317
103453
 
103318
103454
  // src/services/task/cc-task-file-store.ts
103319
103455
  import { existsSync as existsSync12 } from "fs";
103320
- import { readdir as readdir22, readFile as readFile49 } from "fs/promises";
103456
+ import { readdir as readdir22, readFile as readFile50 } from "fs/promises";
103321
103457
  import { homedir as homedir14 } from "os";
103322
- import { basename as basename14, dirname as dirname39, join as join81 } from "path";
103458
+ import { basename as basename14, dirname as dirname39, join as join82 } from "path";
103323
103459
  var VALID_STATUSES = /* @__PURE__ */ new Set(["pending", "in_progress", "completed"]);
103324
103460
  var IDLE_DETACH_MS = 5 * 60 * 1e3;
103325
103461
  var IDLE_SWEEP_INTERVAL_MS = 6e4;
@@ -103335,7 +103471,7 @@ function isCCTaskFile(value) {
103335
103471
  }
103336
103472
  function createCCTaskFileWatcher(listId, log) {
103337
103473
  const sanitizedId = sanitize(listId);
103338
- const dir = join81(homedir14(), ".claude", "tasks", sanitizedId);
103474
+ const dir = join82(homedir14(), ".claude", "tasks", sanitizedId);
103339
103475
  const targetDirName = basename14(dir);
103340
103476
  const parentDir = dirname39(dir);
103341
103477
  const watchState = {
@@ -103371,9 +103507,9 @@ function createCCTaskFileWatcher(listId, log) {
103371
103507
  return tasks;
103372
103508
  }
103373
103509
  async function readTask(taskId) {
103374
- const filePath = join81(dir, `${taskId}.json`);
103510
+ const filePath = join82(dir, `${taskId}.json`);
103375
103511
  try {
103376
- const raw = await readFile49(filePath, "utf-8");
103512
+ const raw = await readFile50(filePath, "utf-8");
103377
103513
  const parsed = JSON.parse(raw);
103378
103514
  if (isCCTaskFile(parsed)) return parsed;
103379
103515
  log?.({
@@ -103438,7 +103574,7 @@ function createCCTaskFileWatcher(listId, log) {
103438
103574
  watchState.parentSub = null;
103439
103575
  return;
103440
103576
  }
103441
- if (ev.path.endsWith(targetDirName) || ev.path === join81(parentDir, targetDirName)) {
103577
+ if (ev.path.endsWith(targetDirName) || ev.path === join82(parentDir, targetDirName)) {
103442
103578
  void ensureDirWatcher();
103443
103579
  break;
103444
103580
  }
@@ -103555,7 +103691,7 @@ function createCCTaskFileWatcher(listId, log) {
103555
103691
  // src/services/task/cc-task-file-writer.ts
103556
103692
  import { createHash as createHash16 } from "crypto";
103557
103693
  import { mkdir as mkdir39, readdir as readdir23, rename as rename20, unlink as unlink14, writeFile as writeFile30 } from "fs/promises";
103558
- import { join as join82 } from "path";
103694
+ import { join as join83 } from "path";
103559
103695
  function contentHash2(data) {
103560
103696
  return createHash16("sha256").update(data).digest("hex").slice(0, 16);
103561
103697
  }
@@ -103571,7 +103707,7 @@ async function writeTasks(dir, tasks, hashes) {
103571
103707
  const json = JSON.stringify(structuredTaskToCCFile(task), null, 2);
103572
103708
  const hash = contentHash2(json);
103573
103709
  if (hashes.get(id) === hash) continue;
103574
- await atomicWriteFile2(join82(dir, `${id}.json`), json);
103710
+ await atomicWriteFile2(join83(dir, `${id}.json`), json);
103575
103711
  hashes.set(id, hash);
103576
103712
  }
103577
103713
  return targetIds;
@@ -103587,7 +103723,7 @@ async function removeStaleFiles(dir, targetIds, hashes) {
103587
103723
  if (!entry.endsWith(".json")) continue;
103588
103724
  const id = entry.slice(0, -".json".length);
103589
103725
  if (!targetIds.has(id) && hashes.has(id)) {
103590
- await unlink14(join82(dir, entry)).catch(() => {
103726
+ await unlink14(join83(dir, entry)).catch(() => {
103591
103727
  });
103592
103728
  hashes.delete(id);
103593
103729
  }
@@ -104219,10 +104355,10 @@ var StructuredTaskTracker = class {
104219
104355
  import { unwatchFile, watchFile } from "fs";
104220
104356
  import { open as open5 } from "fs/promises";
104221
104357
  import { homedir as homedir15 } from "os";
104222
- import { join as join83 } from "path";
104358
+ import { join as join84 } from "path";
104223
104359
  function computeTranscriptPath(cwd, sessionId, taskId) {
104224
104360
  const cwdSlug = cwd.replace(/[^a-zA-Z0-9]/g, "-").slice(0, 200);
104225
- return join83(
104361
+ return join84(
104226
104362
  homedir15(),
104227
104363
  ".claude",
104228
104364
  "projects",
@@ -104403,9 +104539,9 @@ var SubagentTranscriptWatcher = class {
104403
104539
  let fh = null;
104404
104540
  try {
104405
104541
  fh = await open5(this.#config.transcriptPath, "r");
104406
- const stat22 = await fh.stat();
104407
- if (stat22.size <= this.#bytesRead) return;
104408
- const bytesToRead = stat22.size - this.#bytesRead;
104542
+ const stat23 = await fh.stat();
104543
+ if (stat23.size <= this.#bytesRead) return;
104544
+ const bytesToRead = stat23.size - this.#bytesRead;
104409
104545
  const buffer = Buffer.alloc(bytesToRead);
104410
104546
  const { bytesRead } = await fh.read(buffer, 0, bytesToRead, this.#bytesRead);
104411
104547
  this.#bytesRead += bytesRead;
@@ -104955,13 +105091,40 @@ function trackPlanFileCreation(content, onPlanFile) {
104955
105091
  }
104956
105092
  }
104957
105093
 
105094
+ // src/services/task/orchestrator/task-unpushed-selection.ts
105095
+ function isUnconfirmedHuman(message, excludeCorrelationIds) {
105096
+ if (message.senderKind !== "human") return false;
105097
+ const { correlationId } = message;
105098
+ if (!correlationId) return false;
105099
+ if (message.sdkUuid) return false;
105100
+ return !excludeCorrelationIds?.has(correlationId);
105101
+ }
105102
+ function selectUnpushedMessages(messages, excludeCorrelationIds) {
105103
+ let lastAgentIndex = -1;
105104
+ for (let i = messages.length - 1; i >= 0; i--) {
105105
+ if (messages[i]?.senderKind === "agent") {
105106
+ lastAgentIndex = i;
105107
+ break;
105108
+ }
105109
+ }
105110
+ const selected = [];
105111
+ let supersededByAgentReply = 0;
105112
+ for (let i = 0; i < messages.length; i++) {
105113
+ const message = messages[i];
105114
+ if (message === void 0 || !isUnconfirmedHuman(message, excludeCorrelationIds)) continue;
105115
+ if (i < lastAgentIndex) supersededByAgentReply++;
105116
+ else selected.push(message);
105117
+ }
105118
+ return { messages: selected, supersededByAgentReply };
105119
+ }
105120
+
104958
105121
  // src/services/token-counter.ts
104959
105122
  import { spawn as spawn13 } from "child_process";
104960
105123
  import { createHash as createHash17 } from "crypto";
104961
105124
  import { unlink as unlink15, writeFile as writeFile31 } from "fs/promises";
104962
105125
  import { createRequire as createRequire4 } from "module";
104963
105126
  import { tmpdir as tmpdir2 } from "os";
104964
- import { join as join84 } from "path";
105127
+ import { join as join85 } from "path";
104965
105128
  function spawnCollect(bin, args, opts) {
104966
105129
  return new Promise((resolve15, reject) => {
104967
105130
  const child = spawn13(bin, args, {
@@ -105019,7 +105182,7 @@ function resolveDaemonNodeModules(log) {
105019
105182
  } catch {
105020
105183
  }
105021
105184
  try {
105022
- const cwdRequire = createRequire4(join84(process.cwd(), "package.json"));
105185
+ const cwdRequire = createRequire4(join85(process.cwd(), "package.json"));
105023
105186
  const sdkPath = cwdRequire.resolve("@modelcontextprotocol/sdk/server/mcp.js");
105024
105187
  const idx = sdkPath.lastIndexOf("node_modules");
105025
105188
  if (idx >= 0) return sdkPath.slice(0, idx + "node_modules".length);
@@ -105029,7 +105192,7 @@ function resolveDaemonNodeModules(log) {
105029
105192
  error: err3 instanceof Error ? err3.message : String(err3)
105030
105193
  });
105031
105194
  }
105032
- return join84(process.cwd(), "node_modules");
105195
+ return join85(process.cwd(), "node_modules");
105033
105196
  }
105034
105197
  function planTokenCount(systemPrompt, metadata, cwd, model, mcpServers) {
105035
105198
  return {
@@ -105228,7 +105391,7 @@ async function serializeMcpConfig(servers, allToolNames, daemonNodeModules, rese
105228
105391
  if (isReservedMcpServerName(serverName, reservedServerNames)) continue;
105229
105392
  const script = buildStubServerScript(serverName, tools);
105230
105393
  if (!script) continue;
105231
- const stubPath = join84(tmpdir2(), `shipyard-mcp-stub-${serverName}-${Date.now()}.cjs`);
105394
+ const stubPath = join85(tmpdir2(), `shipyard-mcp-stub-${serverName}-${Date.now()}.cjs`);
105232
105395
  await writeFile31(stubPath, script, "utf-8");
105233
105396
  stubPaths.push(stubPath);
105234
105397
  mcpServers[serverName] = {
@@ -105254,7 +105417,7 @@ async function prepareTokenCountArgs(plan, log, reservedServerNames = SDK_RESERV
105254
105417
  reservedServerNames
105255
105418
  );
105256
105419
  if (!serialized.config) return { args, mcpConfigPath: null, stubPaths: serialized.stubPaths };
105257
- const mcpConfigPath = join84(tmpdir2(), `shipyard-mcp-${Date.now()}.json`);
105420
+ const mcpConfigPath = join85(tmpdir2(), `shipyard-mcp-${Date.now()}.json`);
105258
105421
  await writeFile31(mcpConfigPath, JSON.stringify(serialized.config), "utf-8");
105259
105422
  args.push("--mcp-config", mcpConfigPath);
105260
105423
  return { args, mcpConfigPath, stubPaths: serialized.stubPaths };
@@ -105816,22 +105979,21 @@ var Task = class {
105816
105979
  correlationId: meta?.correlationIds[0]
105817
105980
  };
105818
105981
  },
105819
- onUserMessageConfirmed: (correlationId, mark) => {
105982
+ onUserMessageConfirmed: (correlationId, mark, storedMessageId) => {
105820
105983
  const currentMeta = this.#pendingMessageMeta[0];
105821
105984
  const idsToAck = currentMeta?.correlationIds ?? [correlationId];
105822
105985
  if (mark) {
105823
- const [primary, ...secondary] = idsToAck;
105824
- const primaryId = primary ?? correlationId;
105986
+ const [, ...secondary] = idsToAck;
105825
105987
  this.#deps.store.stampSdkUuid(
105826
105988
  this.#deps.channelId,
105827
- primaryId,
105989
+ storedMessageId,
105828
105990
  mark.ref,
105829
105991
  secondary.length > 0 ? secondary : void 0
105830
105992
  ).catch((err3) => {
105831
105993
  this.#deps.log({
105832
105994
  event: "stamp_sdk_uuid_failed",
105833
105995
  taskId: this.#deps.taskId,
105834
- correlationId: primaryId,
105996
+ messageId: storedMessageId,
105835
105997
  error: err3 instanceof Error ? err3.message : String(err3)
105836
105998
  });
105837
105999
  });
@@ -106692,21 +106854,23 @@ var Task = class {
106692
106854
  }
106693
106855
  /**
106694
106856
  * Sub-phase 7b: Rehydrate persisted-but-unpushed user messages after daemon restart.
106695
- *
106696
- * Scans the JSONL store for rows where correlationId is set but sdkUuid is null
106697
- * (persisted but not confirmed by SDK). Re-injects them as pushMessage content
106698
- * so the next subprocess spawn receives them in order.
106699
- *
106700
- * Pass excludeCorrelationIds to skip messages already handled by rehydrateCollabQueue,
106701
- * preventing double-send of the same message to the subprocess.
106702
- *
106703
- * Returns the number of messages re-injected.
106857
+ * Bounded to the trailing human segment — selectUnpushedMessages explains why
106858
+ * an agent reply outranks a missing sdkUuid. Pass excludeCorrelationIds to skip
106859
+ * messages already handled by rehydrateCollabQueue. Returns the count injected.
106704
106860
  */
106705
106861
  async rehydrateUnpushedMessages(excludeCorrelationIds) {
106706
106862
  const messages = await this.#deps.store.getMessages(this.#deps.channelId);
106707
- const unpushed = messages.filter(
106708
- (m2) => m2.senderKind === "human" && m2.correlationId && !m2.sdkUuid && !(excludeCorrelationIds && m2.correlationId && excludeCorrelationIds.has(m2.correlationId))
106863
+ const { messages: unpushed, supersededByAgentReply } = selectUnpushedMessages(
106864
+ messages,
106865
+ excludeCorrelationIds
106709
106866
  );
106867
+ if (supersededByAgentReply > 0) {
106868
+ this.#deps.log({
106869
+ event: "unpushed_messages_superseded",
106870
+ taskId: this.#deps.taskId,
106871
+ count: supersededByAgentReply
106872
+ });
106873
+ }
106710
106874
  if (unpushed.length === 0) return 0;
106711
106875
  this.#ensureFileWatcherAttached();
106712
106876
  for (const msg of unpushed) {
@@ -111877,7 +112041,7 @@ async function createDaemon(deps) {
111877
112041
  const annotationStore = buildAnnotationStore(deps.dataDir);
111878
112042
  const deliverableStore = buildDeliverableStore(deps.dataDir);
111879
112043
  const resourceRegistry = createResourceRegistry();
111880
- const assetStore = buildAssetStore(join85(deps.dataDir, "assets"));
112044
+ const assetStore = buildAssetStore(join86(deps.dataDir, "assets"));
111881
112045
  const shipyardResolver = createShipyardResolver();
111882
112046
  shipyardResolver.addSubResolver("asset", createAssetResolver(assetStore));
111883
112047
  const pluginResourceResolver = new PluginResourceResolver(deps.log);
@@ -111908,10 +112072,10 @@ async function createDaemon(deps) {
111908
112072
  workspaceRoot: deps.workspaceRoot,
111909
112073
  log: deps.log
111910
112074
  });
111911
- const userSettingsStore = buildUserSettingsStore(join85(deps.dataDir, "user-settings.json"));
111912
- const projectsStore = buildProjectsStore(join85(deps.dataDir, "projects.json"));
112075
+ const userSettingsStore = buildUserSettingsStore(join86(deps.dataDir, "user-settings.json"));
112076
+ const projectsStore = buildProjectsStore(join86(deps.dataDir, "projects.json"));
111913
112077
  const credentialsVaultStore = buildCredentialsVaultStore(
111914
- join85(deps.dataDir, "credentials-vault.json")
112078
+ join86(deps.dataDir, "credentials-vault.json")
111915
112079
  );
111916
112080
  const cursorVaultKeyRef = { current: null };
111917
112081
  let resolveCursorVaultKey;
@@ -112379,7 +112543,7 @@ async function createDaemon(deps) {
112379
112543
  taskId: args.taskId,
112380
112544
  agentSystem: args.agentSystem,
112381
112545
  environmentKey: args.cwd,
112382
- pluginsDir: join85(deps.shipyardHome, "plugins"),
112546
+ pluginsDir: join86(deps.shipyardHome, "plugins"),
112383
112547
  vizWatcher: getOrCreateVizWatcher(args.taskId).watcher,
112384
112548
  mode: "task",
112385
112549
  ownerUserId: deps.auth.userId,
@@ -112517,7 +112681,7 @@ async function createDaemon(deps) {
112517
112681
  /** Claude in-process harness — Codex uses the HTTP path with 'codex' above. */
112518
112682
  agentSystem: AGENT_SYSTEM_CLAUDE_CODE,
112519
112683
  environmentKey: args.cwd,
112520
- pluginsDir: join85(deps.shipyardHome, "plugins"),
112684
+ pluginsDir: join86(deps.shipyardHome, "plugins"),
112521
112685
  vizWatcher: args.vizWatcher,
112522
112686
  mode: args.mode ?? "task",
112523
112687
  ownerUserId: deps.auth.userId,
@@ -113596,7 +113760,7 @@ async function createDaemon(deps) {
113596
113760
  deps.metricsCollector
113597
113761
  );
113598
113762
  const planDocGapReporter = startPlanDocPersistenceGapReporter({
113599
- loroDir: join85(deps.dataDir, "loro"),
113763
+ loroDir: join86(deps.dataDir, "loro"),
113600
113764
  listTasks: () => taskStateStore.listTasks(),
113601
113765
  log: deps.log,
113602
113766
  metricsCollector: deps.metricsCollector
@@ -113612,7 +113776,7 @@ async function createDaemon(deps) {
113612
113776
  const stallProfilerConfig = getStallProfilerConfig();
113613
113777
  const stallProfiler = new StallProfiler({
113614
113778
  log: deps.log,
113615
- outDir: join85(deps.dataDir, "stall-profiles"),
113779
+ outDir: join86(deps.dataDir, "stall-profiles"),
113616
113780
  thresholdMs: stallProfilerConfig.thresholdMs,
113617
113781
  captureMs: stallProfilerConfig.captureMs,
113618
113782
  rateLimitMs: stallProfilerConfig.rateLimitMs
@@ -114264,8 +114428,8 @@ import { existsSync as existsSync14 } from "fs";
114264
114428
  // src/services/bootstrap/self-update.ts
114265
114429
  import { execFile as execFile13, spawn as spawn14 } from "child_process";
114266
114430
  import { createHash as createHash18 } from "crypto";
114267
- import { chmod as chmod4, mkdir as mkdir41, readFile as readFile50, rename as rename21, unlink as unlink16, writeFile as writeFile32 } from "fs/promises";
114268
- import { join as join86 } from "path";
114431
+ import { chmod as chmod4, mkdir as mkdir41, readFile as readFile51, rename as rename21, unlink as unlink16, writeFile as writeFile32 } from "fs/promises";
114432
+ import { join as join87 } from "path";
114269
114433
 
114270
114434
  // src/services/bootstrap/self-update-installer-scripts.ts
114271
114435
  function buildPosixInstallerScript(params) {
@@ -114667,7 +114831,7 @@ async function downloadTarball(url2, destPath, fetchFn) {
114667
114831
  throw new Error(`download failed: HTTP ${response.status} ${response.statusText}`);
114668
114832
  }
114669
114833
  const bytes = new Uint8Array(await response.arrayBuffer());
114670
- await mkdir41(join86(destPath, ".."), { recursive: true });
114834
+ await mkdir41(join87(destPath, ".."), { recursive: true });
114671
114835
  try {
114672
114836
  await writeFile32(tmpPath, bytes);
114673
114837
  await rename21(tmpPath, destPath);
@@ -114686,7 +114850,7 @@ async function downloadTarball(url2, destPath, fetchFn) {
114686
114850
  }
114687
114851
  async function verifyChecksum(path8, expectedHash) {
114688
114852
  const algo = expectedHash.length === 40 ? "sha1" : "sha256";
114689
- const raw = await readFile50(path8);
114853
+ const raw = await readFile51(path8);
114690
114854
  const actual = createHash18(algo).update(raw).digest("hex");
114691
114855
  if (actual !== expectedHash) {
114692
114856
  try {
@@ -114697,7 +114861,7 @@ async function verifyChecksum(path8, expectedHash) {
114697
114861
  }
114698
114862
  }
114699
114863
  async function stageInstallerScript(scriptPath, params) {
114700
- await mkdir41(join86(scriptPath, ".."), { recursive: true });
114864
+ await mkdir41(join87(scriptPath, ".."), { recursive: true });
114701
114865
  const body = process.platform === "win32" ? buildWindowsInstallerScript(params) : buildPosixInstallerScript(params);
114702
114866
  await writeFile32(scriptPath, body);
114703
114867
  await chmod4(scriptPath, 493);
@@ -114747,16 +114911,16 @@ function buildInstallerParams(state, deps) {
114747
114911
  targetVersion: state.resolved.version,
114748
114912
  previousVersion: deps.currentVersion,
114749
114913
  parentPid: deps.pid,
114750
- statusFilePath: join86(deps.shipyardHome, "update-status.json"),
114751
- pidFilePath: join86(deps.shipyardHome, "daemon.pid"),
114752
- logPath: join86(deps.shipyardHome, "updates", `install-${deps.pid}.log`),
114753
- snapshotPath: join86(deps.shipyardHome, "updates", `rollback-${deps.currentVersion}`),
114914
+ statusFilePath: join87(deps.shipyardHome, "update-status.json"),
114915
+ pidFilePath: join87(deps.shipyardHome, "daemon.pid"),
114916
+ logPath: join87(deps.shipyardHome, "updates", `install-${deps.pid}.log`),
114917
+ snapshotPath: join87(deps.shipyardHome, "updates", `rollback-${deps.currentVersion}`),
114754
114918
  npmBin: "npm"
114755
114919
  };
114756
114920
  }
114757
114921
  function tarballPathFor(shipyardHome, version, shasum) {
114758
114922
  const shaPrefix = shasum.slice(0, 12);
114759
- return join86(shipyardHome, "updates", `${version}-${shaPrefix}.tgz`);
114923
+ return join87(shipyardHome, "updates", `${version}-${shaPrefix}.tgz`);
114760
114924
  }
114761
114925
  async function runResolveStep(step, state, deps) {
114762
114926
  const resolver = deps.resolveVersion ?? defaultResolveVersion;
@@ -115804,8 +115968,8 @@ function buildLocalDirectChannelCallbacks(deps) {
115804
115968
  }
115805
115969
 
115806
115970
  // src/services/skills-cache/codex-skills-cache.ts
115807
- import { mkdir as mkdir42, readFile as readFile51, rename as rename22, writeFile as writeFile33 } from "fs/promises";
115808
- import { dirname as dirname41, join as join87 } from "path";
115971
+ import { mkdir as mkdir42, readFile as readFile52, rename as rename22, writeFile as writeFile33 } from "fs/promises";
115972
+ import { dirname as dirname41, join as join88 } from "path";
115809
115973
  var CACHE_FILENAME = "codex-skills-cache.json";
115810
115974
  var SkillInfoCacheEntrySchema = external_exports.object({
115811
115975
  name: external_exports.string(),
@@ -115822,12 +115986,12 @@ var CodexSkillsCacheFileSchema = external_exports.object({
115822
115986
  skills: external_exports.array(SkillInfoCacheEntrySchema)
115823
115987
  });
115824
115988
  function defaultCodexSkillsCachePath(shipyardHome) {
115825
- return join87(shipyardHome, "state", CACHE_FILENAME);
115989
+ return join88(shipyardHome, "state", CACHE_FILENAME);
115826
115990
  }
115827
115991
  async function loadCodexSkillsCache(path8) {
115828
115992
  let raw;
115829
115993
  try {
115830
- raw = await readFile51(path8, "utf-8");
115994
+ raw = await readFile52(path8, "utf-8");
115831
115995
  } catch (err3) {
115832
115996
  if (isEnoent(err3)) return null;
115833
115997
  logger.warn(
@@ -115884,13 +116048,13 @@ async function saveCodexSkillsCache(path8, cache2) {
115884
116048
  }
115885
116049
 
115886
116050
  // src/services/skills-mirror/manager.ts
115887
- import { lstat as lstat6, mkdir as mkdir44, readlink, stat as stat21, symlink, unlink as unlink18 } from "fs/promises";
116051
+ import { lstat as lstat6, mkdir as mkdir44, readlink, stat as stat22, symlink, unlink as unlink18 } from "fs/promises";
115888
116052
  import { homedir as homedir16 } from "os";
115889
- import { dirname as dirname43, join as join89 } from "path";
116053
+ import { dirname as dirname43, join as join90 } from "path";
115890
116054
 
115891
116055
  // src/services/skills-mirror/manifest.ts
115892
- import { mkdir as mkdir43, readFile as readFile52, rename as rename23, unlink as unlink17, writeFile as writeFile34 } from "fs/promises";
115893
- import { dirname as dirname42, join as join88 } from "path";
116056
+ import { mkdir as mkdir43, readFile as readFile53, rename as rename23, unlink as unlink17, writeFile as writeFile34 } from "fs/promises";
116057
+ import { dirname as dirname42, join as join89 } from "path";
115894
116058
  var MANIFEST_VERSION = 1;
115895
116059
  var ManifestEntrySchema = external_exports.object({
115896
116060
  /** Display name of the skill (e.g. `qa`, or `plugin:name` when namespaced). */
@@ -115910,11 +116074,11 @@ function emptyManifest() {
115910
116074
  return { version: MANIFEST_VERSION, entries: [] };
115911
116075
  }
115912
116076
  function defaultManifestPath(shipyardHome) {
115913
- return join88(shipyardHome, "state", "skill-mirror-manifest.json");
116077
+ return join89(shipyardHome, "state", "skill-mirror-manifest.json");
115914
116078
  }
115915
116079
  async function loadManifest(path8) {
115916
116080
  try {
115917
- const raw = await readFile52(path8, "utf-8");
116081
+ const raw = await readFile53(path8, "utf-8");
115918
116082
  const parsed = ManifestFileSchema.safeParse(JSON.parse(raw));
115919
116083
  if (!parsed.success) return emptyManifest();
115920
116084
  return parsed.data;
@@ -115941,15 +116105,15 @@ async function deleteManifest(path8) {
115941
116105
  function defaultPaths() {
115942
116106
  const home = homedir16();
115943
116107
  return {
115944
- claudeSkillsDir: join89(home, ".claude", "skills"),
115945
- codexSkillsDir: join89(home, ".agents", "skills"),
116108
+ claudeSkillsDir: join90(home, ".claude", "skills"),
116109
+ codexSkillsDir: join90(home, ".agents", "skills"),
115946
116110
  manifestPath: defaultManifestPath(getShipyardHome())
115947
116111
  };
115948
116112
  }
115949
116113
  function plannedSymlinkPath(skill, paths) {
115950
116114
  const linkName = skill.namespace ? `${skill.namespace}:${skill.name}` : skill.name;
115951
- if (skill.sourceAgent === "claude-code") return join89(paths.codexSkillsDir, linkName);
115952
- if (skill.sourceAgent === "codex") return join89(paths.claudeSkillsDir, linkName);
116115
+ if (skill.sourceAgent === "claude-code") return join90(paths.codexSkillsDir, linkName);
116116
+ if (skill.sourceAgent === "codex") return join90(paths.claudeSkillsDir, linkName);
115953
116117
  return null;
115954
116118
  }
115955
116119
  function isPermissionError(err3) {
@@ -116096,7 +116260,7 @@ function planMirrorActions(skills, paths) {
116096
116260
  }
116097
116261
  async function classifyManifestEntry(entry) {
116098
116262
  try {
116099
- await stat21(entry.target);
116263
+ await stat22(entry.target);
116100
116264
  return "retain";
116101
116265
  } catch (err3) {
116102
116266
  if (isEnoent(err3)) return "sweep-dangling";
@@ -116161,8 +116325,8 @@ async function ensureMirror(skills, config, paths = defaultPaths()) {
116161
116325
  }
116162
116326
 
116163
116327
  // src/services/skills-mirror/prefs.ts
116164
- import { mkdir as mkdir45, readFile as readFile53, rename as rename24, writeFile as writeFile35 } from "fs/promises";
116165
- import { dirname as dirname44, join as join90 } from "path";
116328
+ import { mkdir as mkdir45, readFile as readFile54, rename as rename24, writeFile as writeFile35 } from "fs/promises";
116329
+ import { dirname as dirname44, join as join91 } from "path";
116166
116330
  var SkillsMirrorPrefsSchema = external_exports.object({
116167
116331
  enabled: external_exports.boolean().default(false)
116168
116332
  });
@@ -116171,11 +116335,11 @@ function defaultSkillsMirrorPrefs() {
116171
116335
  return { enabled: false };
116172
116336
  }
116173
116337
  function prefsPath(dataDir) {
116174
- return join90(dataDir, FILENAME);
116338
+ return join91(dataDir, FILENAME);
116175
116339
  }
116176
116340
  async function loadSkillsMirrorPrefs(dataDir) {
116177
116341
  try {
116178
- const raw = await readFile53(prefsPath(dataDir), "utf-8");
116342
+ const raw = await readFile54(prefsPath(dataDir), "utf-8");
116179
116343
  const parsed = SkillsMirrorPrefsSchema.safeParse(JSON.parse(raw));
116180
116344
  if (!parsed.success) return defaultSkillsMirrorPrefs();
116181
116345
  return parsed.data;
@@ -116219,8 +116383,8 @@ async function reconcileSkillsMirror(args) {
116219
116383
 
116220
116384
  // src/services/storage/daemon-settings-store.ts
116221
116385
  import { createHash as createHash19 } from "crypto";
116222
- import { mkdir as mkdir46, readFile as readFile54 } from "fs/promises";
116223
- import { join as join91 } from "path";
116386
+ import { mkdir as mkdir46, readFile as readFile55 } from "fs/promises";
116387
+ import { join as join92 } from "path";
116224
116388
  var ProjectSettingsSchema = external_exports.object({
116225
116389
  disabledMcpServers: external_exports.array(external_exports.string()).optional(),
116226
116390
  previewMigrationV36Done: external_exports.boolean().default(false)
@@ -116229,9 +116393,9 @@ function hashProjectPath(projectPath) {
116229
116393
  return createHash19("sha256").update(projectPath).digest("hex").slice(0, 16);
116230
116394
  }
116231
116395
  function buildDaemonSettingsStore(dataDir) {
116232
- const settingsDir = join91(dataDir, "settings");
116396
+ const settingsDir = join92(dataDir, "settings");
116233
116397
  function settingsPath(projectPath) {
116234
- return join91(settingsDir, `${hashProjectPath(projectPath)}.json`);
116398
+ return join92(settingsDir, `${hashProjectPath(projectPath)}.json`);
116235
116399
  }
116236
116400
  async function ensureDir() {
116237
116401
  await mkdir46(settingsDir, { recursive: true });
@@ -116239,7 +116403,7 @@ function buildDaemonSettingsStore(dataDir) {
116239
116403
  return {
116240
116404
  async load(projectPath) {
116241
116405
  try {
116242
- const raw = await readFile54(settingsPath(projectPath), "utf-8");
116406
+ const raw = await readFile55(settingsPath(projectPath), "utf-8");
116243
116407
  return ProjectSettingsSchema.parse(JSON.parse(raw));
116244
116408
  } catch (err3) {
116245
116409
  if (isEnoent(err3)) return ProjectSettingsSchema.parse({});
@@ -116255,18 +116419,18 @@ function buildDaemonSettingsStore(dataDir) {
116255
116419
  }
116256
116420
 
116257
116421
  // src/services/storage/plugin-config-store.ts
116258
- import { mkdir as mkdir47, readFile as readFile55 } from "fs/promises";
116259
- import { join as join92 } from "path";
116422
+ import { mkdir as mkdir47, readFile as readFile56 } from "fs/promises";
116423
+ import { join as join93 } from "path";
116260
116424
  function buildPluginConfigStore(pluginsDir) {
116261
116425
  const cache2 = /* @__PURE__ */ new Map();
116262
116426
  const writeQueues = /* @__PURE__ */ new Map();
116263
116427
  function configPath(pluginId) {
116264
- return join92(pluginsDir, pluginId, "config.json");
116428
+ return join93(pluginsDir, pluginId, "config.json");
116265
116429
  }
116266
116430
  async function readConfigFromDisk(pluginId) {
116267
116431
  const fp = configPath(pluginId);
116268
116432
  try {
116269
- const raw = await readFile55(fp, "utf-8");
116433
+ const raw = await readFile56(fp, "utf-8");
116270
116434
  const parsed = JSON.parse(raw);
116271
116435
  if (typeof parsed === "object" && parsed !== null && !Array.isArray(parsed)) {
116272
116436
  return Object.fromEntries(Object.entries(parsed));
@@ -116315,7 +116479,7 @@ function buildPluginConfigStore(pluginsDir) {
116315
116479
  const fresh = await readConfigFromDisk(pluginId);
116316
116480
  fresh[key] = value;
116317
116481
  cache2.set(pluginId, fresh);
116318
- await mkdir47(join92(pluginsDir, pluginId), { recursive: true });
116482
+ await mkdir47(join93(pluginsDir, pluginId), { recursive: true });
116319
116483
  await atomicWriteFile(configPath(pluginId), JSON.stringify(fresh, null, 2));
116320
116484
  })
116321
116485
  );
@@ -116543,7 +116707,7 @@ async function serve(options = {}) {
116543
116707
  }
116544
116708
  async function runServeBody(options, captureRefs) {
116545
116709
  const shipyardHome = options.shipyardHome ?? getShipyardHome();
116546
- const dataDir = join93(shipyardHome, options.isDev ? "data-dev" : "data");
116710
+ const dataDir = join94(shipyardHome, options.isDev ? "data-dev" : "data");
116547
116711
  const log = createChildLogger({ mode: "serve" });
116548
116712
  log.info(
116549
116713
  { event: "daemon_start", version: getDaemonVersion(), pid: process.pid },
@@ -116551,7 +116715,7 @@ async function runServeBody(options, captureRefs) {
116551
116715
  );
116552
116716
  const { workspaceRoot, unscopedWorkspace, unscopedReason } = await resolveWorkspaceScope();
116553
116717
  registerBuiltinPlugins();
116554
- const pluginConfigStore = buildPluginConfigStore(join93(dataDir, "plugins"));
116718
+ const pluginConfigStore = buildPluginConfigStore(join94(dataDir, "plugins"));
116555
116719
  await mkdir48(dataDir, { recursive: true });
116556
116720
  log.info(
116557
116721
  {
@@ -116644,9 +116808,9 @@ async function runServeBody(options, captureRefs) {
116644
116808
  await bootstrapPhase("pid_sweep_orphans", () => pidTracker.sweepOrphans(logAdapter));
116645
116809
  await bootstrapPhase(
116646
116810
  "legacy_epoch_prune",
116647
- () => pruneOldEpochData(join93(dataDir, "loro"), logAdapter)
116811
+ () => pruneOldEpochData(join94(dataDir, "loro"), logAdapter)
116648
116812
  );
116649
- const storage = new FileStorageAdapter(join93(dataDir, "loro"));
116813
+ const storage = new FileStorageAdapter(join94(dataDir, "loro"));
116650
116814
  const personalWebrtcAdapter = new WebRtcDataChannelAdapter();
116651
116815
  const peerRoleRegistry = createPeerRoleRegistry();
116652
116816
  const presencePoolRef = { pool: {} };
@@ -116754,14 +116918,14 @@ async function runServeBody(options, captureRefs) {
116754
116918
  current: []
116755
116919
  };
116756
116920
  const terminalPtys = /* @__PURE__ */ new Map();
116757
- const terminalLogsDir = join93(shipyardHome, "data", "terminals");
116921
+ const terminalLogsDir = join94(shipyardHome, "data", "terminals");
116758
116922
  await mkdir48(terminalLogsDir, { recursive: true, mode: 448 });
116759
116923
  const publishedArtifactStore = createPublishedArtifactStore({
116760
- rootDir: join93(dataDir, "published"),
116924
+ rootDir: join94(dataDir, "published"),
116761
116925
  log: logAdapter
116762
116926
  });
116763
116927
  const previewStateStore = createPreviewStateStore({
116764
- rootDir: join93(dataDir, "preview-state"),
116928
+ rootDir: join94(dataDir, "preview-state"),
116765
116929
  logger: log
116766
116930
  });
116767
116931
  let codexSkillsApplyScopedPatchRef = null;
@@ -116845,7 +117009,7 @@ async function runServeBody(options, captureRefs) {
116845
117009
  daemon.healthMetrics.start();
116846
117010
  publishedArtifactStore.setSendControlMessage((msg) => daemon.taskManager.broadcastControl(msg));
116847
117011
  previewStateStore.setSendControlMessage((msg) => daemon.taskManager.broadcastControl(msg));
116848
- const pluginsDir = join93(shipyardHome, "plugins");
117012
+ const pluginsDir = join94(shipyardHome, "plugins");
116849
117013
  await mkdir48(pluginsDir, { recursive: true });
116850
117014
  let loadedPlugins = [];
116851
117015
  const loadedPluginsRef = {
@@ -117410,4 +117574,4 @@ export {
117410
117574
  decideWorkspaceScope,
117411
117575
  serve
117412
117576
  };
117413
- //# sourceMappingURL=serve-3TQOIJID.js.map
117577
+ //# sourceMappingURL=serve-JEU6SMZX.js.map