@moxt-ai/mobius 0.0.292 → 0.0.294

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (68) hide show
  1. package/dist/acp/harness/codex/agent.d.ts.map +1 -1
  2. package/dist/acp/harness/codex/agent.js +8 -2
  3. package/dist/acp/harness/codex/agent.js.map +1 -1
  4. package/dist/acp/harness/codex/borrowed-agent.d.ts +2 -4
  5. package/dist/acp/harness/codex/borrowed-agent.d.ts.map +1 -1
  6. package/dist/acp/harness/codex/borrowed-agent.js +2 -1
  7. package/dist/acp/harness/codex/borrowed-agent.js.map +1 -1
  8. package/dist/acp/harness/codex/owned-agent.d.ts +1 -0
  9. package/dist/acp/harness/codex/owned-agent.d.ts.map +1 -1
  10. package/dist/acp/harness/codex/owned-agent.js +1 -0
  11. package/dist/acp/harness/codex/owned-agent.js.map +1 -1
  12. package/dist/acp/harness/codex/session-agent.d.ts +1 -0
  13. package/dist/acp/harness/codex/session-agent.d.ts.map +1 -1
  14. package/dist/acp/protocol/session-capabilities.d.ts +2 -0
  15. package/dist/acp/protocol/session-capabilities.d.ts.map +1 -1
  16. package/dist/acp/protocol/session-capabilities.js +11 -0
  17. package/dist/acp/protocol/session-capabilities.js.map +1 -1
  18. package/dist/cli.js +135 -13
  19. package/dist/cli.js.map +4 -4
  20. package/dist/daemon/lifecycle/worker.d.ts.map +1 -1
  21. package/dist/daemon/lifecycle/worker.js +4 -1
  22. package/dist/daemon/lifecycle/worker.js.map +1 -1
  23. package/dist/daemon/upgrades/upgrade.d.ts +2 -1
  24. package/dist/daemon/upgrades/upgrade.d.ts.map +1 -1
  25. package/dist/daemon/upgrades/upgrade.js +101 -10
  26. package/dist/daemon/upgrades/upgrade.js.map +1 -1
  27. package/dist/runtime/command/registry/prompt.d.ts.map +1 -1
  28. package/dist/runtime/command/registry/prompt.js +10 -0
  29. package/dist/runtime/command/registry/prompt.js.map +1 -1
  30. package/dist/runtime/engine.d.ts +2 -0
  31. package/dist/runtime/engine.d.ts.map +1 -1
  32. package/dist/runtime/engine.js +1 -0
  33. package/dist/runtime/engine.js.map +1 -1
  34. package/dist/runtime/relay/run-relay-connection.d.ts.map +1 -1
  35. package/dist/runtime/relay/run-relay-connection.js +2 -0
  36. package/dist/runtime/relay/run-relay-connection.js.map +1 -1
  37. package/dist/runtime/relay/session-event-publisher.d.ts +1 -0
  38. package/dist/runtime/relay/session-event-publisher.d.ts.map +1 -1
  39. package/dist/runtime/relay/session-event-publisher.js +5 -0
  40. package/dist/runtime/relay/session-event-publisher.js.map +1 -1
  41. package/dist/runtime/run.d.ts +2 -0
  42. package/dist/runtime/run.d.ts.map +1 -1
  43. package/dist/runtime/run.js +1 -0
  44. package/dist/runtime/run.js.map +1 -1
  45. package/dist/runtime.js +100 -7
  46. package/dist/runtime.js.map +4 -4
  47. package/dist/session/api/session-layer.d.ts +2 -0
  48. package/dist/session/api/session-layer.d.ts.map +1 -1
  49. package/dist/session/api/session-layer.js +1 -1
  50. package/dist/session/api/session-layer.js.map +1 -1
  51. package/dist/session/live/agent-session-restore.d.ts +1 -0
  52. package/dist/session/live/agent-session-restore.d.ts.map +1 -1
  53. package/dist/session/live/agent-session.d.ts +1 -0
  54. package/dist/session/live/agent-session.d.ts.map +1 -1
  55. package/dist/session/live/agent-session.js +5 -1
  56. package/dist/session/live/agent-session.js.map +1 -1
  57. package/dist/session/live/session-restore.d.ts.map +1 -1
  58. package/dist/session/live/session-restore.js +1 -0
  59. package/dist/session/live/session-restore.js.map +1 -1
  60. package/dist/session/turn/runtime-turn-activity.d.ts +11 -0
  61. package/dist/session/turn/runtime-turn-activity.d.ts.map +1 -0
  62. package/dist/session/turn/runtime-turn-activity.js +45 -0
  63. package/dist/session/turn/runtime-turn-activity.js.map +1 -0
  64. package/dist/session/turn/session-turns.d.ts +3 -1
  65. package/dist/session/turn/session-turns.d.ts.map +1 -1
  66. package/dist/session/turn/session-turns.js +11 -2
  67. package/dist/session/turn/session-turns.js.map +1 -1
  68. package/package.json +1 -1
package/dist/cli.js CHANGED
@@ -5398,7 +5398,7 @@ var program = new Command();
5398
5398
  // package.json
5399
5399
  var package_default = {
5400
5400
  name: "@moxt-ai/mobius",
5401
- version: "0.0.292",
5401
+ version: "0.0.294",
5402
5402
  description: "Mobius CLI for pairing and running local AI agent services.",
5403
5403
  type: "module",
5404
5404
  bin: {
@@ -70684,6 +70684,7 @@ var queuePageSchema = external_exports.object({
70684
70684
  nextCursor: external_exports.string().nullish()
70685
70685
  });
70686
70686
  var CodexBorrowedAcpAgent = class {
70687
+ steeringSupported = false;
70687
70688
  #client;
70688
70689
  #threadId;
70689
70690
  #emit;
@@ -70905,7 +70906,7 @@ var CodexBorrowedAcpAgent = class {
70905
70906
  nativeTurnId = () => null;
70906
70907
  steer = async (_params, signal) => {
70907
70908
  signal.throwIfAborted();
70908
- return { outcome: "promptRequired", reason: "noRunningTurn" };
70909
+ throw new AcpExecutionError("This Codex session only supports queued input", {}, "steering_unsupported");
70909
70910
  };
70910
70911
  // The reader connection cannot receive or control the owner's live turn.
70911
70912
  onNotification = async (_method, _params) => {
@@ -71045,6 +71046,7 @@ function userInputSchema(questions) {
71045
71046
  return { properties, required: required2, type: "object" };
71046
71047
  }
71047
71048
  var CodexOwnedAcpAgent = class {
71049
+ steeringSupported = true;
71048
71050
  #context;
71049
71051
  #appServer;
71050
71052
  #settings;
@@ -73967,7 +73969,10 @@ var CodexAcpAgent = class {
73967
73969
  await this.#resume(context.params.sessionId, context.params.cwd, context.signal);
73968
73970
  await this.#replaySavedHistory(context.signal);
73969
73971
  this.#advertiseCompactCommand();
73970
- return { configOptions: this.#settings.configOptions() };
73972
+ return {
73973
+ _meta: { steering: { supported: this.#sessionAgent.steeringSupported } },
73974
+ configOptions: this.#settings.configOptions()
73975
+ };
73971
73976
  }).onRequest(methods3.agent.session.fork, async (context) => {
73972
73977
  const forked = threadForkResponseSchema.parse(
73973
73978
  await this.#appServer.request(
@@ -73990,7 +73995,10 @@ var CodexAcpAgent = class {
73990
73995
  }).onRequest(methods3.agent.session.resume, async (context) => {
73991
73996
  await this.#resume(context.params.sessionId, context.params.cwd, context.signal);
73992
73997
  this.#advertiseCompactCommand();
73993
- return { configOptions: this.#settings.configOptions() };
73998
+ return {
73999
+ _meta: { steering: { supported: this.#sessionAgent.steeringSupported } },
74000
+ configOptions: this.#settings.configOptions()
74001
+ };
73994
74002
  }).onRequest(methods3.agent.session.prompt, async (context) => {
73995
74003
  if (isCompactCommand(context.params.prompt)) {
73996
74004
  return await this.#sessionAgent.compact(context.signal);
@@ -78310,6 +78318,16 @@ function normalizeAcpCapabilities(initialized) {
78310
78318
  unstableForkSession: session?.fork != null
78311
78319
  });
78312
78320
  }
78321
+ function restrictAcpSessionCapabilities(capabilities, response) {
78322
+ if (!isRecord3(response) || !isRecord3(response["_meta"])) {
78323
+ return capabilities;
78324
+ }
78325
+ const steering = response["_meta"]["steering"];
78326
+ if (!isRecord3(steering) || steering["supported"] !== false) {
78327
+ return capabilities;
78328
+ }
78329
+ return Object.freeze({ ...capabilities, steering: false });
78330
+ }
78313
78331
 
78314
78332
  // src/acp/agent/agent-definition.ts
78315
78333
  var AgentDefinition = class {
@@ -90333,6 +90351,7 @@ async function restoreSession(session, signal, recovery, origin) {
90333
90351
  session.setNativeHistoryOwnership({ kind: "fresh-session" });
90334
90352
  lifecycleResponse2 = created;
90335
90353
  }
90354
+ session.restrictSessionCapabilities(lifecycleResponse2);
90336
90355
  session.setConfigOptions(session.sessionConfigProtocol.normalizeLifecycle(lifecycleResponse2));
90337
90356
  if (stored instanceof FoundStoredSession && session.restored) {
90338
90357
  await session.restoreStoredConfigurations(stored.session, signal);
@@ -90585,6 +90604,9 @@ var AgentSession = class _AgentSession {
90585
90604
  signal
90586
90605
  );
90587
90606
  };
90607
+ restrictSessionCapabilities = (response) => {
90608
+ this.#capabilities = restrictAcpSessionCapabilities(this.#capabilities, response);
90609
+ };
90588
90610
  prepared = () => new PreparedSession(
90589
90611
  this.#agentName,
90590
90612
  this.#agentVersion,
@@ -90658,6 +90680,7 @@ var AgentSession = class _AgentSession {
90658
90680
  );
90659
90681
  await this.#updates.drained();
90660
90682
  signal.throwIfAborted();
90683
+ this.restrictSessionCapabilities(response);
90661
90684
  const loaded = { history, kind: "loaded", response };
90662
90685
  this.#sessionLoad = loaded;
90663
90686
  return loaded;
@@ -93239,6 +93262,50 @@ var ExecutionReceipts = class {
93239
93262
  };
93240
93263
  };
93241
93264
 
93265
+ // src/session/turn/runtime-turn-activity.ts
93266
+ var RuntimeTurnActivity = class {
93267
+ #turns = /* @__PURE__ */ new Set();
93268
+ #admission = { kind: "open" };
93269
+ acceptsPrompts = () => this.#admission.kind !== "reserved";
93270
+ count = () => this.#turns.size;
93271
+ start = (turn) => {
93272
+ this.#turns.add(turn);
93273
+ };
93274
+ finish = (turn) => {
93275
+ this.#turns.delete(turn);
93276
+ if (this.#turns.size === 0 && this.#admission.kind === "waiting") {
93277
+ this.#admission.reserve();
93278
+ }
93279
+ };
93280
+ reserveWhenIdle = (signal) => {
93281
+ signal.throwIfAborted();
93282
+ if (this.#admission.kind !== "open") {
93283
+ throw new Error("A daemon upgrade already owns admission");
93284
+ }
93285
+ return new Promise((resolve20, reject2) => {
93286
+ const abort = () => {
93287
+ this.#admission = { kind: "open" };
93288
+ signal.removeEventListener("abort", abort);
93289
+ reject2(signal.reason);
93290
+ };
93291
+ const reserve = () => {
93292
+ this.#admission = { kind: "reserved" };
93293
+ signal.removeEventListener("abort", abort);
93294
+ resolve20({
93295
+ [Symbol.dispose]: () => {
93296
+ this.#admission = { kind: "open" };
93297
+ }
93298
+ });
93299
+ };
93300
+ this.#admission = { kind: "waiting", reserve };
93301
+ signal.addEventListener("abort", abort, { once: true });
93302
+ if (this.#turns.size === 0) {
93303
+ reserve();
93304
+ }
93305
+ });
93306
+ };
93307
+ };
93308
+
93242
93309
  // src/session/turn/active-turn.ts
93243
93310
  import { randomUUID as randomUUID15 } from "node:crypto";
93244
93311
  var ActiveRuntimeTurn = class {
@@ -93455,9 +93522,12 @@ var SessionExecutionState = class {
93455
93522
  var SessionTurns = class {
93456
93523
  #bySessionId = /* @__PURE__ */ new Map();
93457
93524
  #operations;
93458
- constructor(operations) {
93525
+ #activity;
93526
+ constructor(operations, activity2 = new RuntimeTurnActivity()) {
93459
93527
  this.#operations = operations;
93528
+ this.#activity = activity2;
93460
93529
  }
93530
+ acceptsPrompts = () => this.#activity.acceptsPrompts();
93461
93531
  session = (sessionId) => {
93462
93532
  let session = this.#bySessionId.get(sessionId);
93463
93533
  if (session === void 0) {
@@ -93467,10 +93537,15 @@ var SessionTurns = class {
93467
93537
  return session;
93468
93538
  };
93469
93539
  get = (commandId, sessionId) => this.#bySessionId.get(sessionId)?.get(commandId);
93470
- start = (command, attemptId) => this.session(command.sessionId).start(command, attemptId);
93540
+ start = (command, attemptId) => {
93541
+ const turn = this.session(command.sessionId).start(command, attemptId);
93542
+ this.#activity.start(turn);
93543
+ return turn;
93544
+ };
93471
93545
  finish = (turn) => {
93472
93546
  this.#bySessionId.get(turn.command.sessionId)?.finish(turn);
93473
93547
  this.sweep();
93548
+ this.#activity.finish(turn);
93474
93549
  };
93475
93550
  recordEvent = (event) => "sessionId" in event ? this.#bySessionId.get(event.sessionId)?.recordEvent(event) ?? event : event;
93476
93551
  recordSessionEvent = (event) => {
@@ -93712,7 +93787,7 @@ function buildSessionLayer(options) {
93712
93787
  const sessionStore = new SqliteSessionStore(new AcpSessionTable(sessionDatabase), events);
93713
93788
  const externalContent = new LocalExternalContentStore(stateDirectory);
93714
93789
  const operations = new ExecutionReceipts();
93715
- const activeSessions = new SessionTurns(operations);
93790
+ const activeSessions = new SessionTurns(operations, options.turnActivity);
93716
93791
  const directories = new WorkspaceDirectoryService(bindingId, defaultWorkspace);
93717
93792
  const manager = new SessionManager2({
93718
93793
  observer: new SessionLayerObserver((event) => eventProjection.record(event), sink.publishInfo),
@@ -95685,6 +95760,16 @@ var sessionPromptCommand = {
95685
95760
  if (message.kind !== SESSION_PROMPT_KIND) {
95686
95761
  throw new Error("Command kind mismatch");
95687
95762
  }
95763
+ if (!context.sessionTurns.acceptsPrompts()) {
95764
+ send(context.socket, {
95765
+ code: "runtime_upgrading",
95766
+ requestId: message.commandId,
95767
+ kind: "session.operation.failed",
95768
+ message: "The Runtime is upgrading. Retry after it reconnects.",
95769
+ sessionId: message.sessionId
95770
+ });
95771
+ return;
95772
+ }
95688
95773
  const receipt = context.operations.claimExecution(
95689
95774
  message.commandId,
95690
95775
  message.sessionId,
@@ -96490,6 +96575,7 @@ async function runRelayConnection({
96490
96575
  reject2(failure2);
96491
96576
  };
96492
96577
  const stop = () => {
96578
+ publisher.flush();
96493
96579
  diagnostics.connectionClosed(connectionEpoch, 1e3, "Daemon stopped", "daemon_stop");
96494
96580
  closeRelaySocket(socket, 1e3, "Daemon stopped");
96495
96581
  resolveConnection();
@@ -96645,6 +96731,11 @@ var RuntimeSessionEventPublisher = class {
96645
96731
  this.#socket = null;
96646
96732
  this.dropPendingEvents();
96647
96733
  };
96734
+ flush = () => {
96735
+ if (this.#socket !== null) {
96736
+ this.flushEvents(this.#socket);
96737
+ }
96738
+ };
96648
96739
  publishOperationFailure = (sessionId, requestId, code, message) => {
96649
96740
  this.#send({ kind: "session.operation.failed", sessionId, requestId, code, message });
96650
96741
  };
@@ -96778,6 +96869,7 @@ async function runRuntime(config2, parentSignal, timer = systemTimer, options =
96778
96869
  );
96779
96870
  const publisher = new RuntimeSessionEventPublisher(timer);
96780
96871
  const layer = buildSessionLayer({
96872
+ ...options.turnActivity === void 0 ? {} : { turnActivity: options.turnActivity },
96781
96873
  bindingId: config2.bindingId,
96782
96874
  channelId: config2.channelId,
96783
96875
  defaultWorkspace: config2.defaultWorkspace,
@@ -96947,6 +97039,7 @@ var MobiusRuntimeEngine = class {
96947
97039
  this.#state = new RunningMobiusRuntimeState();
96948
97040
  try {
96949
97041
  await runRuntime(this.#config, signal, void 0, {
97042
+ ...this.#options.turnActivity === void 0 ? {} : { turnActivity: this.#options.turnActivity },
96950
97043
  ...this.#options.onConnectionStatus === void 0 ? {} : { onConnectionStatus: this.#options.onConnectionStatus },
96951
97044
  ...this.#options.reportUpgradeAvailability === void 0 ? {} : { reportUpgradeAvailability: this.#options.reportUpgradeAvailability },
96952
97045
  ...this.#options.processLogsDirectory === void 0 ? {} : { processLogsDirectory: this.#options.processLogsDirectory }
@@ -97095,11 +97188,11 @@ async function reportDaemonUpgradeAvailability(send2, signal) {
97095
97188
  send2({ ...base, kind: "runtime.upgrade.result", outcome: { status: "succeeded" } });
97096
97189
  }
97097
97190
  }
97098
- async function runDaemonReleaseUpgrades(signal) {
97191
+ async function runDaemonReleaseUpgrades(signal, activity2) {
97099
97192
  try {
97100
97193
  for await (const _tick of setInterval2(36e5, void 0, { signal })) {
97101
97194
  try {
97102
- await checkDaemonReleaseUpgrade(signal);
97195
+ await checkDaemonReleaseUpgrade(signal, activity2);
97103
97196
  } catch (cause) {
97104
97197
  signal.throwIfAborted();
97105
97198
  console.error("Daemon npm upgrade check failed", cause);
@@ -97117,6 +97210,9 @@ async function requestDaemonReleaseUpgrade(stateDirectory, currentVersion, signa
97117
97210
  return { kind: "current" };
97118
97211
  }
97119
97212
  const launch = await installDaemonReleaseVersion(version2, signal);
97213
+ return await requestInstalledDaemonReleaseSwitch(stateDirectory, launch, signal);
97214
+ }
97215
+ async function requestInstalledDaemonReleaseSwitch(stateDirectory, launch, signal) {
97120
97216
  const id = randomUUID17();
97121
97217
  const response = lifecycleResponse.parse(
97122
97218
  await sendLocalRequest(stateDirectory, "manager", { kind: "switch", id, context: "npm", launch }, signal)
@@ -97127,7 +97223,7 @@ async function requestDaemonReleaseUpgrade(stateDirectory, currentVersion, signa
97127
97223
  if (response.kind !== "switching") {
97128
97224
  throw new DaemonReleaseUpgradeError("manager_incompatible", "The manager does not support daemon switching");
97129
97225
  }
97130
- return { kind: "requested", id, version: version2 };
97226
+ return { kind: "requested", id, version: launch.version };
97131
97227
  }
97132
97228
  async function awaitDaemonReleaseSwitch(stateDirectory, id, signal) {
97133
97229
  const deadline = AbortSignal.any([signal, AbortSignal.timeout(SWITCH_COMPLETION_MILLISECONDS)]);
@@ -97158,13 +97254,37 @@ async function awaitDaemonReleaseSwitch(stateDirectory, id, signal) {
97158
97254
  }
97159
97255
  return outcome;
97160
97256
  }
97161
- async function checkDaemonReleaseUpgrade(signal) {
97257
+ async function checkDaemonReleaseUpgrade(signal, activity2) {
97162
97258
  const control = await openMobiusControlInstallation(signal, process.env);
97163
97259
  const transition2 = await readSwitchStatus(control.stateDirectory, signal);
97164
97260
  if (transition2?.kind === "switching" || transition2?.kind === "rolled-back" && transition2.retryAfter > Date.now()) {
97165
97261
  return;
97166
97262
  }
97167
- await requestDaemonReleaseUpgrade(control.stateDirectory, package_default.version, signal);
97263
+ const version2 = await findNewDaemonReleaseVersion(package_default.version, signal);
97264
+ if (version2 === null) {
97265
+ return;
97266
+ }
97267
+ const launch = await installDaemonReleaseVersion(version2, signal);
97268
+ if (activity2.count() > 0) {
97269
+ new RuntimeDiagnosticLog(control.stateDirectory).record(
97270
+ `Mobius daemon diagnostic ${JSON.stringify({
97271
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
97272
+ event: "daemon_upgrade_deferred",
97273
+ version: version2,
97274
+ activeTurns: activity2.count()
97275
+ })}`
97276
+ );
97277
+ }
97278
+ using _reservation = await activity2.reserveWhenIdle(signal);
97279
+ signal.throwIfAborted();
97280
+ await requestInstalledDaemonReleaseSwitch(control.stateDirectory, launch, signal);
97281
+ await new Promise((resolve20) => {
97282
+ if (signal.aborted) {
97283
+ resolve20();
97284
+ } else {
97285
+ signal.addEventListener("abort", () => resolve20(), { once: true });
97286
+ }
97287
+ });
97168
97288
  }
97169
97289
 
97170
97290
  // src/daemon/lifecycle/worker.ts
@@ -97220,6 +97340,7 @@ async function runWorkerRuntime(version2, combined, shutdown, rejectionGuard) {
97220
97340
  }
97221
97341
  }
97222
97342
  rejectionGuard.bindStateDirectory(control.stateDirectory);
97343
+ const turnActivity = new RuntimeTurnActivity();
97223
97344
  const active = /* @__PURE__ */ new Map();
97224
97345
  const fail = (connectionId2, cause) => {
97225
97346
  console.error(`Runtime ${connectionId2} failed; stopping the daemon`, cause);
@@ -97247,6 +97368,7 @@ async function runWorkerRuntime(version2, combined, shutdown, rejectionGuard) {
97247
97368
  const controller = new AbortController();
97248
97369
  const engine = new MobiusRuntimeEngine(paired.config, {
97249
97370
  processLogsDirectory: control.stateDirectory,
97371
+ turnActivity,
97250
97372
  reportUpgradeAvailability: reportDaemonUpgradeAvailability
97251
97373
  });
97252
97374
  const completion = engine.run(AbortSignal.any([combined, controller.signal])).then(
@@ -97289,7 +97411,7 @@ async function runWorkerRuntime(version2, combined, shutdown, rejectionGuard) {
97289
97411
  async () => {
97290
97412
  combined.throwIfAborted();
97291
97413
  await recordCurrentData(version2, combined);
97292
- upgrades = runDaemonReleaseUpgrades(combined);
97414
+ upgrades = runDaemonReleaseUpgrades(combined, turnActivity);
97293
97415
  if (process.connected) {
97294
97416
  process.send?.({ kind: "worker-ready", version: version2 }, () => void 0);
97295
97417
  }