@moxt-ai/mobius 0.0.156 → 0.0.157

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/cli.js CHANGED
@@ -3381,7 +3381,7 @@ var program = new Command();
3381
3381
  // package.json
3382
3382
  var package_default = {
3383
3383
  name: "@moxt-ai/mobius",
3384
- version: "0.0.156",
3384
+ version: "0.0.157",
3385
3385
  description: "Mobius CLI for pairing and running local AI agent services.",
3386
3386
  type: "module",
3387
3387
  bin: {
@@ -30086,8 +30086,15 @@ var acpSessionUpdateV2Schema = external_exports.discriminatedUnion("sessionUpdat
30086
30086
  }).readonly()
30087
30087
  ]);
30088
30088
  var lifecycleBase = { commandId: identifierStringSchema };
30089
- var sessionEventPayloadV2Schema = external_exports.discriminatedUnion("kind", [
30090
- external_exports.strictObject({ kind: external_exports.literal("acp.session.update"), update: acpSessionUpdateV2Schema }).readonly(),
30089
+ var lifecycleMetadataV2Schema = external_exports.discriminatedUnion("kind", [
30090
+ external_exports.strictObject({ kind: external_exports.literal("session.queue.changed") }).readonly(),
30091
+ external_exports.strictObject({ event: sessionPermissionRequestedEventSchema, kind: external_exports.literal("session.permission.requested") }).readonly(),
30092
+ external_exports.strictObject({ event: sessionPermissionResolvedEventSchema, kind: external_exports.literal("session.permission.resolved") }).readonly(),
30093
+ external_exports.strictObject({
30094
+ event: sessionElicitationRequestedEventSchema,
30095
+ kind: external_exports.literal("session.elicitation.requested")
30096
+ }).readonly(),
30097
+ external_exports.strictObject({ event: sessionElicitationResolvedEventSchema, kind: external_exports.literal("session.elicitation.resolved") }).readonly(),
30091
30098
  external_exports.strictObject({
30092
30099
  ...lifecycleBase,
30093
30100
  content: external_exports.array(contentBlockV2Schema).min(1).max(100).readonly(),
@@ -30109,6 +30116,10 @@ var sessionEventPayloadV2Schema = external_exports.discriminatedUnion("kind", [
30109
30116
  message: external_exports.string().min(1).max(500)
30110
30117
  }).readonly()
30111
30118
  ]);
30119
+ var sessionEventPayloadV2Schema = external_exports.discriminatedUnion("type", [
30120
+ external_exports.strictObject({ payload: acpSessionUpdateV2Schema, type: external_exports.literal("acp") }).readonly(),
30121
+ external_exports.strictObject({ payload: lifecycleMetadataV2Schema, type: external_exports.literal("lifecycle-metadata") }).readonly()
30122
+ ]);
30112
30123
  var positionSchema = external_exports.string().regex(/^(0|[1-9][0-9]*)$/);
30113
30124
  var provenanceSchema = external_exports.discriminatedUnion("kind", [
30114
30125
  external_exports.strictObject({ kind: external_exports.literal("original") }).readonly(),
@@ -30125,13 +30136,62 @@ var provenanceSchema = external_exports.discriminatedUnion("kind", [
30125
30136
  sourceSessionId: identifierStringSchema
30126
30137
  }).readonly()
30127
30138
  ]);
30128
- var sessionEventV2Schema = external_exports.strictObject({
30139
+ var sessionEventFieldsV2 = {
30129
30140
  eventId: identifierStringSchema,
30130
- payload: sessionEventPayloadV2Schema,
30131
30141
  position: positionSchema,
30132
30142
  provenance: provenanceSchema,
30133
30143
  recordedAt: external_exports.iso.datetime({ offset: true }),
30134
30144
  sessionId: identifierStringSchema
30145
+ };
30146
+ var sessionEventV2Schema = external_exports.discriminatedUnion("type", [
30147
+ external_exports.strictObject({ ...sessionEventFieldsV2, payload: acpSessionUpdateV2Schema, type: external_exports.literal("acp") }).readonly(),
30148
+ external_exports.strictObject({
30149
+ ...sessionEventFieldsV2,
30150
+ payload: lifecycleMetadataV2Schema,
30151
+ type: external_exports.literal("lifecycle-metadata")
30152
+ }).readonly()
30153
+ ]);
30154
+ var sessionExportV2Schema = external_exports.strictObject({
30155
+ binding: external_exports.strictObject({
30156
+ bindingId: identifierStringSchema,
30157
+ runtimeId: identifierStringSchema
30158
+ }).readonly(),
30159
+ events: external_exports.array(sessionEventV2Schema).max(MAX_EVENT_COUNT).readonly(),
30160
+ sessionId: identifierStringSchema,
30161
+ truncated: external_exports.boolean()
30162
+ }).readonly().superRefine((session, context) => {
30163
+ let previousPosition = 0n;
30164
+ const eventIds = /* @__PURE__ */ new Set();
30165
+ for (const [index2, event] of session.events.entries()) {
30166
+ if (event.sessionId !== session.sessionId) {
30167
+ context.addIssue({
30168
+ code: "custom",
30169
+ message: "Exported event belongs to a different Session",
30170
+ path: ["events", index2, "sessionId"]
30171
+ });
30172
+ }
30173
+ const position = BigInt(event.position);
30174
+ if (position <= previousPosition) {
30175
+ context.addIssue({
30176
+ code: "custom",
30177
+ message: "Exported events are not in increasing position order",
30178
+ path: ["events", index2, "position"]
30179
+ });
30180
+ }
30181
+ if (eventIds.has(event.eventId)) {
30182
+ context.addIssue({
30183
+ code: "custom",
30184
+ message: "Exported event identities are not unique",
30185
+ path: ["events", index2, "eventId"]
30186
+ });
30187
+ }
30188
+ previousPosition = position;
30189
+ eventIds.add(event.eventId);
30190
+ }
30191
+ });
30192
+ var mobiusSessionExportV2Schema = external_exports.strictObject({
30193
+ formatVersion: external_exports.literal("2"),
30194
+ session: sessionExportV2Schema
30135
30195
  }).readonly();
30136
30196
  var sessionEventEnvelopeV2Schema = external_exports.strictObject({ event: sessionEventV2Schema, kind: external_exports.literal(SESSION_EVENT_V2_KIND) }).readonly();
30137
30197
  var sessionEventLogPageV2Schema = external_exports.strictObject({
@@ -39397,8 +39457,15 @@ var MemoryAcpSessionStore = class {
39397
39457
  #sessions = /* @__PURE__ */ new Map();
39398
39458
  #deleted = /* @__PURE__ */ new Set();
39399
39459
  #eventsV2 = /* @__PURE__ */ new Map();
39400
- appendEventV2 = (event) => {
39401
- this.#eventsV2.set(event.sessionId, [...this.#eventsV2.get(event.sessionId) ?? [], event]);
39460
+ appendExecutingPromptEventV2 = (event) => {
39461
+ const events = this.#eventsV2.get(event.sessionId);
39462
+ if (events === void 0) {
39463
+ throw new Error("The executing prompt event log has not started");
39464
+ }
39465
+ events.push(event);
39466
+ };
39467
+ clearExecutingPromptEventsV2 = (sessionId) => {
39468
+ this.#eventsV2.delete(sessionId);
39402
39469
  };
39403
39470
  close = () => {
39404
39471
  this.#sessions.clear();
@@ -39429,7 +39496,12 @@ var MemoryAcpSessionStore = class {
39429
39496
  this.#sessions.delete(sessionId);
39430
39497
  this.#eventsV2.delete(sessionId);
39431
39498
  };
39432
- readEventsV2 = (sessionId) => this.#eventsV2.get(sessionId) ?? [];
39499
+ readExecutingPromptEventsV2 = (sessionId) => [
39500
+ ...this.#eventsV2.get(sessionId) ?? []
39501
+ ];
39502
+ startExecutingPromptEventsV2 = (sessionId, events) => {
39503
+ this.#eventsV2.set(sessionId, [...events]);
39504
+ };
39433
39505
  write = (session) => {
39434
39506
  this.#sessions.set(session.sessionId, session);
39435
39507
  };
@@ -39497,7 +39569,7 @@ var SqliteAcpSessionStore = class {
39497
39569
  close = () => {
39498
39570
  this.#sqliteDatabase.close();
39499
39571
  };
39500
- appendEventV2 = (event) => {
39572
+ appendExecutingPromptEventV2 = (event) => {
39501
39573
  this.#database.insert(sessionEventV2).values({
39502
39574
  eventId: event.eventId,
39503
39575
  eventJson: JSON.stringify(event),
@@ -39505,6 +39577,22 @@ var SqliteAcpSessionStore = class {
39505
39577
  sessionId: event.sessionId
39506
39578
  }).run();
39507
39579
  };
39580
+ clearExecutingPromptEventsV2 = (sessionId) => {
39581
+ this.#database.delete(sessionEventV2).where(eq(sessionEventV2.sessionId, sessionId)).run();
39582
+ };
39583
+ startExecutingPromptEventsV2 = (sessionId, events) => {
39584
+ this.#database.transaction((transaction) => {
39585
+ transaction.delete(sessionEventV2).where(eq(sessionEventV2.sessionId, sessionId)).run();
39586
+ for (const event of events) {
39587
+ transaction.insert(sessionEventV2).values({
39588
+ eventId: event.eventId,
39589
+ eventJson: JSON.stringify(event),
39590
+ position: Number(event.position),
39591
+ sessionId: event.sessionId
39592
+ }).run();
39593
+ }
39594
+ });
39595
+ };
39508
39596
  findNative = (agentId, nativeSessionId) => this.#database.select().from(acpSession).where(and(eq(acpSession.agentId, agentId), eq(acpSession.nativeSessionId, nativeSessionId))).all().map(decodeStoredSession);
39509
39597
  list = () => this.#database.select().from(acpSession).orderBy(desc(acpSession.updatedAt)).all().map(decodeStoredSession);
39510
39598
  markDeleted = (agentId, nativeSessionId) => {
@@ -39527,7 +39615,7 @@ var SqliteAcpSessionStore = class {
39527
39615
  const row = this.#database.select().from(acpSession).where(eq(acpSession.sessionId, sessionId)).get();
39528
39616
  return row === void 0 ? new MissingAcpStoredSession() : new FoundAcpStoredSession(decodeStoredSession(row));
39529
39617
  };
39530
- readEventsV2 = (sessionId) => this.#database.select({ eventJson: sessionEventV2.eventJson }).from(sessionEventV2).where(eq(sessionEventV2.sessionId, sessionId)).orderBy(asc(sessionEventV2.position)).all().map((row) => decodeSessionEventV2(row.eventJson));
39618
+ readExecutingPromptEventsV2 = (sessionId) => this.#database.select({ eventJson: sessionEventV2.eventJson }).from(sessionEventV2).where(eq(sessionEventV2.sessionId, sessionId)).orderBy(asc(sessionEventV2.position)).all().map((row) => decodeSessionEventV2(row.eventJson));
39531
39619
  remove = (sessionId) => {
39532
39620
  this.#database.transaction((transaction) => {
39533
39621
  transaction.delete(acpSession).where(eq(acpSession.sessionId, sessionId)).run();
@@ -40205,6 +40293,19 @@ var AgentSession = class _AgentSession {
40205
40293
  if (this.#turn.running) {
40206
40294
  throw new AcpExecutionError("Another prompt is already running in this conversation", {}, "session_busy");
40207
40295
  }
40296
+ switch (this.#sessionLoad.kind) {
40297
+ case "not-requested":
40298
+ break;
40299
+ case "loaded":
40300
+ this.#sessionLoad = { kind: "not-requested" };
40301
+ break;
40302
+ case "capturing":
40303
+ throw new AcpExecutionError("Session history is still loading", {}, "session_busy");
40304
+ default: {
40305
+ const unexpected = this.#sessionLoad;
40306
+ throw new Error(`Unexpected Session load state: ${JSON.stringify(unexpected)}`);
40307
+ }
40308
+ }
40208
40309
  const prompt = this.buildPrompt(options);
40209
40310
  if (this.#sessionTitle === null || this.#sessionTitle.length === 0) {
40210
40311
  this.#sessionTitle = truncate(options.prompt, 500);
@@ -40370,7 +40471,7 @@ var AgentSession = class _AgentSession {
40370
40471
  this.assertNativeSession(notification.sessionId);
40371
40472
  const update = notification.update;
40372
40473
  const rawUpdate = decodeAcpSessionUpdateV2(JSON.stringify(update));
40373
- if (this.#sessionLoad.kind !== "not-requested") {
40474
+ if (this.#sessionLoad.kind === "capturing") {
40374
40475
  await this.#sessionLoad.history.record(update, rawUpdate);
40375
40476
  } else {
40376
40477
  const onAcpUpdate = this.#getObserver().onAcpUpdate;
@@ -42721,7 +42822,7 @@ var DaemonAcpObserver = class {
42721
42822
  this.#recordV2 = recordV2;
42722
42823
  }
42723
42824
  onAcpUpdate = (sessionId, update) => {
42724
- this.#recordV2(sessionId, update);
42825
+ this.#recordV2(sessionId, { payload: update, type: "acp" });
42725
42826
  return Promise.resolve();
42726
42827
  };
42727
42828
  onCommands = (event) => {
@@ -42738,10 +42839,18 @@ var DaemonAcpObserver = class {
42738
42839
  };
42739
42840
  onElicitation = (event) => {
42740
42841
  this.#record(event.sessionId, event);
42842
+ this.#recordV2(event.sessionId, {
42843
+ payload: { event, kind: "session.elicitation.requested" },
42844
+ type: "lifecycle-metadata"
42845
+ });
42741
42846
  return Promise.resolve();
42742
42847
  };
42743
42848
  onElicitationResolved = (event) => {
42744
42849
  this.#record(event.sessionId, event);
42850
+ this.#recordV2(event.sessionId, {
42851
+ payload: { event, kind: "session.elicitation.resolved" },
42852
+ type: "lifecycle-metadata"
42853
+ });
42745
42854
  return Promise.resolve();
42746
42855
  };
42747
42856
  onInfo = (event) => {
@@ -42750,10 +42859,18 @@ var DaemonAcpObserver = class {
42750
42859
  };
42751
42860
  onPermission = (event) => {
42752
42861
  this.#record(event.sessionId, event);
42862
+ this.#recordV2(event.sessionId, {
42863
+ payload: { event, kind: "session.permission.requested" },
42864
+ type: "lifecycle-metadata"
42865
+ });
42753
42866
  return Promise.resolve();
42754
42867
  };
42755
42868
  onPermissionResolved = (event) => {
42756
42869
  this.#record(event.sessionId, event);
42870
+ this.#recordV2(event.sessionId, {
42871
+ payload: { event, kind: "session.permission.resolved" },
42872
+ type: "lifecycle-metadata"
42873
+ });
42757
42874
  return Promise.resolve();
42758
42875
  };
42759
42876
  onUsage = (event) => {
@@ -45994,25 +46111,16 @@ function replayEvent(sessionId, position, update) {
45994
46111
  const eventId = `native-${createHash6("sha256").update(sessionId).update(":").update(position.toString()).update(":").update(encoded).digest("hex")}`;
45995
46112
  return {
45996
46113
  eventId,
45997
- payload: { kind: "acp.session.update", update },
46114
+ payload: update,
45998
46115
  position: position.toString(),
45999
46116
  provenance: { kind: "original" },
46000
46117
  recordedAt: "1970-01-01T00:00:00.000Z",
46001
- sessionId
46118
+ sessionId,
46119
+ type: "acp"
46002
46120
  };
46003
46121
  }
46004
- async function executeSessionLiveHistoryV2PageLoad(socket, command, config2, directories, audit, sessions, localRecovery, executingPromptRequest, signal) {
46122
+ async function executeSessionLiveHistoryV2PageLoad(socket, command, config2, directories, audit, sessions, executingPromptRequest, signal) {
46005
46123
  try {
46006
- const local = localRecovery(command.sessionId, command.eventLimit, command.cursor);
46007
- if (local !== null) {
46008
- send(socket, {
46009
- events: local,
46010
- kind: "session.live-history.v2.page.loaded",
46011
- requestId: command.requestId,
46012
- sessionId: command.sessionId
46013
- });
46014
- return;
46015
- }
46016
46124
  const resolved = await resolveSessionDirectories(
46017
46125
  directories,
46018
46126
  config2.bindingId,
@@ -46896,7 +47004,10 @@ function createDaemonCommandHandler({
46896
47004
  timer,
46897
47005
  resolveEnvironment: resolveAgentCatalogEnvironment
46898
47006
  });
46899
- const queueChanged = (sessionId) => publisher.publish(sessionId, { kind: "session.queue.changed", sessionId });
47007
+ const queueChanged = (sessionId) => {
47008
+ publisher.publish(sessionId, { kind: "session.queue.changed", sessionId });
47009
+ eventLogV2.queueChanged(sessionId);
47010
+ };
46900
47011
  const activeTurnRecovery = (sessionId) => activeTurns.recovery((command) => command.sessionId === sessionId);
46901
47012
  const nativeRequestHandler = createNativeSessionRequestHandler({
46902
47013
  audit,
@@ -46946,7 +47057,6 @@ function createDaemonCommandHandler({
46946
47057
  directories,
46947
47058
  audit,
46948
47059
  sessions,
46949
- eventLogV2.recovery,
46950
47060
  eventLogV2.executingPromptRequest,
46951
47061
  signal
46952
47062
  );
@@ -47662,6 +47772,15 @@ var systemDaemonTimer = new SystemDaemonTimer();
47662
47772
 
47663
47773
  // src/session-event-log-v2.ts
47664
47774
  var EXECUTING_PROMPT_EVENT_LIMIT = 1e4;
47775
+ function eventArray(tail) {
47776
+ const reversed = [];
47777
+ let node2 = tail;
47778
+ while (node2 !== null) {
47779
+ reversed.push(node2.event);
47780
+ node2 = node2.previous;
47781
+ }
47782
+ return reversed.reverse();
47783
+ }
47665
47784
  function promptContent(command) {
47666
47785
  const content = [];
47667
47786
  if (command.prompt.length > 0) {
@@ -47685,27 +47804,8 @@ function promptContent(command) {
47685
47804
  }
47686
47805
  return content;
47687
47806
  }
47688
- function encodeLocalEventCursor(cursor) {
47689
- return Buffer.from(JSON.stringify(cursor), "utf8").toString("base64url");
47690
- }
47691
- function decodeLocalEventCursor(sessionId, cursor) {
47692
- try {
47693
- const value = JSON.parse(Buffer.from(cursor, "base64url").toString("utf8"));
47694
- if (typeof value !== "object" || value === null || Array.isArray(value) || Object.keys(value).sort().join(",") !== "endEvent,sessionId" || Reflect.get(value, "sessionId") !== sessionId) {
47695
- throw new Error("Invalid V2 event cursor target");
47696
- }
47697
- const endEvent = Reflect.get(value, "endEvent");
47698
- if (typeof endEvent !== "number" || !Number.isSafeInteger(endEvent) || endEvent < 0) {
47699
- throw new Error("Invalid V2 event cursor boundary");
47700
- }
47701
- return { endEvent, sessionId };
47702
- } catch (cause) {
47703
- throw new AcpExecutionError("The native Session event cursor is invalid", { cause }, "invalid_cursor");
47704
- }
47705
- }
47706
47807
  var DaemonSessionEventLogV2 = class {
47707
47808
  #positions = /* @__PURE__ */ new Map();
47708
- #events = /* @__PURE__ */ new Map();
47709
47809
  #requests = /* @__PURE__ */ new Map();
47710
47810
  #loadedRequestSessions = /* @__PURE__ */ new Set();
47711
47811
  #publisher;
@@ -47714,13 +47814,8 @@ var DaemonSessionEventLogV2 = class {
47714
47814
  this.#publisher = publisher;
47715
47815
  this.#store = store;
47716
47816
  }
47717
- #eventsFor = (sessionId) => {
47718
- const cached2 = this.#events.get(sessionId);
47719
- if (cached2 !== void 0) {
47720
- return cached2;
47721
- }
47722
- const stored = this.#store.readEventsV2(sessionId);
47723
- this.#events.set(sessionId, stored);
47817
+ #loadStoredEvents = (sessionId) => {
47818
+ const stored = this.#store.readExecutingPromptEventsV2(sessionId);
47724
47819
  const lastPosition = stored.at(-1)?.position;
47725
47820
  if (lastPosition !== void 0) {
47726
47821
  this.#positions.set(sessionId, Number(lastPosition));
@@ -47731,25 +47826,37 @@ var DaemonSessionEventLogV2 = class {
47731
47826
  if (this.#loadedRequestSessions.has(sessionId)) {
47732
47827
  return;
47733
47828
  }
47734
- for (const event of this.#eventsFor(sessionId)) {
47829
+ for (const event of this.#loadStoredEvents(sessionId)) {
47830
+ if (event.type === "acp") {
47831
+ const executing = [...this.#requests.values()].find(
47832
+ (request) => request.sessionId === sessionId && request.kind === "executing"
47833
+ );
47834
+ if (executing !== void 0) {
47835
+ this.#requests.set(executing.commandId, {
47836
+ ...executing,
47837
+ eventTail: { event, previous: executing.eventTail }
47838
+ });
47839
+ }
47840
+ continue;
47841
+ }
47735
47842
  const payload = event.payload;
47736
47843
  if (payload.kind === "prompt.requested") {
47737
47844
  this.#requests.set(payload.commandId, {
47738
47845
  commandId: payload.commandId,
47739
- events: [event],
47846
+ eventTail: { event, previous: null },
47740
47847
  kind: "requested",
47741
47848
  sessionId
47742
47849
  });
47743
47850
  continue;
47744
47851
  }
47745
- if (payload.kind === "acp.session.update") {
47852
+ if ("event" in payload) {
47746
47853
  const executing = [...this.#requests.values()].find(
47747
47854
  (request) => request.sessionId === sessionId && request.kind === "executing"
47748
47855
  );
47749
47856
  if (executing !== void 0) {
47750
47857
  this.#requests.set(executing.commandId, {
47751
47858
  ...executing,
47752
- events: [...executing.events, event]
47859
+ eventTail: { event, previous: executing.eventTail }
47753
47860
  });
47754
47861
  }
47755
47862
  continue;
@@ -47761,13 +47868,12 @@ var DaemonSessionEventLogV2 = class {
47761
47868
  if (state === void 0) {
47762
47869
  continue;
47763
47870
  }
47764
- const events = [...state.events, event];
47765
47871
  if (payload.kind === "prompt.started") {
47766
47872
  this.#requests.set(payload.commandId, {
47767
47873
  attemptId: payload.attemptId,
47768
47874
  commandId: payload.commandId,
47769
47875
  epoch: payload.epoch,
47770
- events,
47876
+ eventTail: { event, previous: state.eventTail },
47771
47877
  kind: "executing",
47772
47878
  sessionId
47773
47879
  });
@@ -47778,31 +47884,41 @@ var DaemonSessionEventLogV2 = class {
47778
47884
  this.#loadedRequestSessions.add(sessionId);
47779
47885
  };
47780
47886
  #append = (sessionId, payload) => {
47781
- this.#eventsFor(sessionId);
47887
+ this.#loadRequests(sessionId);
47782
47888
  const position = (this.#positions.get(sessionId) ?? 0) + 1;
47783
47889
  const event = {
47784
47890
  eventId: `event-${crypto.randomUUID()}`,
47785
- payload,
47891
+ ...payload,
47786
47892
  position: position.toString(),
47787
47893
  provenance: { kind: "original" },
47788
47894
  recordedAt: (/* @__PURE__ */ new Date()).toISOString(),
47789
47895
  sessionId
47790
47896
  };
47791
- this.#store.appendEventV2(event);
47792
47897
  this.#positions.set(sessionId, position);
47793
- this.#events.set(sessionId, [...this.#eventsFor(sessionId), event]);
47794
47898
  this.#publisher.publishV2(event);
47795
47899
  return event;
47796
47900
  };
47797
47901
  requested = (command) => {
47902
+ const content = promptContent(command);
47798
47903
  const event = this.#append(command.sessionId, {
47799
- commandId: command.commandId,
47800
- content: promptContent(command),
47801
- kind: "prompt.requested"
47904
+ payload: { commandId: command.commandId, content, kind: "prompt.requested" },
47905
+ type: "lifecycle-metadata"
47802
47906
  });
47907
+ let eventTail = { event, previous: null };
47908
+ for (const block of content) {
47909
+ const userMessageEvent = this.#append(command.sessionId, {
47910
+ payload: {
47911
+ content: block,
47912
+ messageId: command.commandId,
47913
+ sessionUpdate: "user_message_chunk"
47914
+ },
47915
+ type: "acp"
47916
+ });
47917
+ eventTail = { event: userMessageEvent, previous: eventTail };
47918
+ }
47803
47919
  this.#requests.set(command.commandId, {
47804
47920
  commandId: command.commandId,
47805
- events: [event],
47921
+ eventTail,
47806
47922
  kind: "requested",
47807
47923
  sessionId: command.sessionId
47808
47924
  });
@@ -47813,39 +47929,85 @@ var DaemonSessionEventLogV2 = class {
47813
47929
  if (request?.sessionId !== sessionId) {
47814
47930
  return;
47815
47931
  }
47816
- const event = this.#append(sessionId, { attemptId, commandId, epoch, kind: "prompt.started" });
47932
+ const event = this.#append(sessionId, {
47933
+ payload: { attemptId, commandId, epoch, kind: "prompt.started" },
47934
+ type: "lifecycle-metadata"
47935
+ });
47817
47936
  this.#requests.set(commandId, {
47818
47937
  attemptId,
47819
47938
  commandId,
47820
47939
  epoch,
47821
- events: [...request.events, event],
47940
+ eventTail: { event, previous: request.eventTail },
47822
47941
  kind: "executing",
47823
47942
  sessionId
47824
47943
  });
47944
+ this.#store.startExecutingPromptEventsV2(sessionId, eventArray({ event, previous: request.eventTail }));
47825
47945
  };
47826
- acpUpdate = (sessionId, update) => {
47946
+ record = (sessionId, payload) => {
47827
47947
  this.#loadRequests(sessionId);
47828
- const event = this.#append(sessionId, { kind: "acp.session.update", update });
47948
+ const event = this.#append(sessionId, payload);
47949
+ this.#appendToExecutingRequest(sessionId, event);
47950
+ };
47951
+ #appendToExecutingRequest = (sessionId, event) => {
47829
47952
  const executing = [...this.#requests.values()].find(
47830
47953
  (request) => request.sessionId === sessionId && request.kind === "executing"
47831
47954
  );
47832
47955
  if (executing !== void 0) {
47833
- this.#requests.set(executing.commandId, { ...executing, events: [...executing.events, event] });
47956
+ this.#requests.set(executing.commandId, {
47957
+ ...executing,
47958
+ eventTail: { event, previous: executing.eventTail }
47959
+ });
47960
+ this.#store.appendExecutingPromptEventV2(event);
47834
47961
  }
47835
47962
  };
47963
+ queueChanged = (sessionId) => {
47964
+ const event = this.#append(sessionId, {
47965
+ payload: { kind: "session.queue.changed" },
47966
+ type: "lifecycle-metadata"
47967
+ });
47968
+ this.#appendToExecutingRequest(sessionId, event);
47969
+ };
47836
47970
  completed = (sessionId, commandId, stopReason) => {
47837
- this.#append(sessionId, { commandId, kind: "prompt.completed", stopReason });
47971
+ this.#loadRequests(sessionId);
47972
+ const request = this.#requests.get(commandId);
47973
+ const event = this.#append(sessionId, {
47974
+ payload: { commandId, kind: "prompt.completed", stopReason },
47975
+ type: "lifecycle-metadata"
47976
+ });
47838
47977
  this.#requests.delete(commandId);
47978
+ if (request?.kind === "executing" && request.sessionId === sessionId) {
47979
+ this.#store.clearExecutingPromptEventsV2(sessionId);
47980
+ } else {
47981
+ this.#appendToExecutingRequest(sessionId, event);
47982
+ }
47839
47983
  };
47840
47984
  failed = (sessionId, commandId, code, message) => {
47841
47985
  this.#loadRequests(sessionId);
47842
47986
  const request = this.#requests.get(commandId);
47987
+ let event;
47843
47988
  if (request?.kind === "executing" && request.commandId === commandId) {
47844
- this.#append(sessionId, { attemptId: request.attemptId, code, commandId, kind: "prompt.failed", message });
47989
+ event = this.#append(sessionId, {
47990
+ payload: {
47991
+ attemptId: request.attemptId,
47992
+ code,
47993
+ commandId,
47994
+ kind: "prompt.failed",
47995
+ message
47996
+ },
47997
+ type: "lifecycle-metadata"
47998
+ });
47845
47999
  } else {
47846
- this.#append(sessionId, { code, commandId, kind: "prompt.failed-before-start", message });
48000
+ event = this.#append(sessionId, {
48001
+ payload: { code, commandId, kind: "prompt.failed-before-start", message },
48002
+ type: "lifecycle-metadata"
48003
+ });
47847
48004
  }
47848
48005
  this.#requests.delete(commandId);
48006
+ if (request?.kind === "executing" && request.sessionId === sessionId) {
48007
+ this.#store.clearExecutingPromptEventsV2(sessionId);
48008
+ } else {
48009
+ this.#appendToExecutingRequest(sessionId, event);
48010
+ }
47849
48011
  };
47850
48012
  executingPromptRequest = (sessionId) => {
47851
48013
  this.#loadRequests(sessionId);
@@ -47855,42 +48017,15 @@ var DaemonSessionEventLogV2 = class {
47855
48017
  if (request?.kind !== "executing") {
47856
48018
  return null;
47857
48019
  }
47858
- const events = request.events.slice(-EXECUTING_PROMPT_EVENT_LIMIT);
48020
+ const requestEvents = eventArray(request.eventTail);
48021
+ const events = requestEvents.slice(-EXECUTING_PROMPT_EVENT_LIMIT);
47859
48022
  return {
47860
48023
  attemptId: request.attemptId,
47861
48024
  commandId: request.commandId,
47862
48025
  epoch: request.epoch,
47863
48026
  events,
47864
48027
  tailCursor: events.at(-1)?.eventId ?? "",
47865
- truncated: events.length < request.events.length
47866
- };
47867
- };
47868
- recovery = (sessionId, eventLimit, cursor) => {
47869
- const events = this.#eventsFor(sessionId);
47870
- if (events.length === 0) {
47871
- return null;
47872
- }
47873
- const executingPromptRequest = this.executingPromptRequest(sessionId);
47874
- const executingRequestState = [...this.#requests.values()].find(
47875
- (request) => request.sessionId === sessionId && request.kind === "executing"
47876
- );
47877
- const firstExecutingPosition = executingRequestState?.events[0]?.position;
47878
- const historyEvents = firstExecutingPosition === void 0 ? events : events.filter((event) => BigInt(event.position) < BigInt(firstExecutingPosition));
47879
- const endEvent = cursor === null ? historyEvents.length : decodeLocalEventCursor(sessionId, cursor).endEvent;
47880
- if (endEvent > historyEvents.length) {
47881
- throw new AcpExecutionError("The native Session event cursor is invalid", {}, "invalid_cursor");
47882
- }
47883
- const startEvent = Math.max(0, endEvent - eventLimit);
47884
- const pageEvents = historyEvents.slice(startEvent, endEvent);
47885
- return {
47886
- executingPromptRequest,
47887
- history: {
47888
- events: pageEvents,
47889
- nextCursor: startEvent === 0 ? null : encodeLocalEventCursor({ endEvent: startEvent, sessionId }),
47890
- tailCursor: pageEvents.at(-1)?.eventId ?? "",
47891
- truncated: startEvent > 0,
47892
- version: 2
47893
- }
48028
+ truncated: events.length < requestEvents.length
47894
48029
  };
47895
48030
  };
47896
48031
  };
@@ -47972,7 +48107,7 @@ async function runDaemon(config2, audit, signal, timer = systemDaemonTimer, opti
47972
48107
  publisher.publish(sessionId, activeTurns.recordEvent(event));
47973
48108
  };
47974
48109
  const agentRuntime = new AgentRuntimeManager(
47975
- new DaemonAcpObserver(recordSessionEvent, eventLogV2.acpUpdate),
48110
+ new DaemonAcpObserver(recordSessionEvent, eventLogV2.record),
47976
48111
  sessionStore,
47977
48112
  {
47978
48113
  read: async (options2, nativeSessionId, nativeTurn) => options2.agent.id === "codex" ? (await readCodexFullHistory(