replicas-engine 0.1.1295 → 0.1.1297

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.
@@ -3,7 +3,7 @@ import { createRequire as __createRequire } from 'node:module';
3
3
  const require = __createRequire(import.meta.url);
4
4
  import {
5
5
  HOOK_EXEC_MAX_BUFFER_BYTES
6
- } from "./chunk-Q5KCYMUE.js";
6
+ } from "./chunk-FNGZVOD4.js";
7
7
 
8
8
  // src/utils/exec.ts
9
9
  import { exec, execFile } from "child_process";
@@ -5,7 +5,7 @@ import {
5
5
  extractCommandProtectionCommandText,
6
6
  isRecord,
7
7
  parseCodeHostPrUrl
8
- } from "./chunk-Q5KCYMUE.js";
8
+ } from "./chunk-FNGZVOD4.js";
9
9
 
10
10
  // src/services/published-pull-request-urls.ts
11
11
  function publishedPullRequestUrls(result) {
@@ -3,7 +3,7 @@ import { createRequire as __createRequire } from 'node:module';
3
3
  const require = __createRequire(import.meta.url);
4
4
  import {
5
5
  AspClient
6
- } from "./chunk-JBZNUWMJ.js";
6
+ } from "./chunk-64AMDDNX.js";
7
7
  import {
8
8
  ASTER_BASE_URL,
9
9
  ASTER_PROVIDER,
@@ -15,7 +15,7 @@ import {
15
15
  isRecord,
16
16
  readOllamaAuthEnv,
17
17
  readOpenAICompatibleAuthEnv
18
- } from "./chunk-Q5KCYMUE.js";
18
+ } from "./chunk-FNGZVOD4.js";
19
19
 
20
20
  // src/managers/codex-asp/notification-dispatch.ts
21
21
  var TURN_STARTED_METHOD = "turn/started";
@@ -5,14 +5,14 @@ import {
5
5
  getOriginDefaultBranch,
6
6
  monolithRequest,
7
7
  runGitCommand
8
- } from "./chunk-OCOIXNER.js";
8
+ } from "./chunk-45DWBRYV.js";
9
9
  import {
10
10
  extractCommandProtectionCommandText,
11
11
  findCommandProtectionGitLookups,
12
12
  findGitCommitSignals,
13
13
  findPrMergeSignals,
14
14
  parseCommandProtectionRequest
15
- } from "./chunk-Q5KCYMUE.js";
15
+ } from "./chunk-FNGZVOD4.js";
16
16
 
17
17
  // src/services/command-protection-service.ts
18
18
  import { readFile, stat } from "fs/promises";
@@ -3,13 +3,13 @@ import { createRequire as __createRequire } from 'node:module';
3
3
  const require = __createRequire(import.meta.url);
4
4
  import {
5
5
  evaluateCommandProtection
6
- } from "./chunk-7QO3HM4H.js";
7
- import "./chunk-OCOIXNER.js";
8
- import "./chunk-TBKEZB4T.js";
6
+ } from "./chunk-ZJXG4VN4.js";
7
+ import "./chunk-45DWBRYV.js";
8
+ import "./chunk-JXYPBRHP.js";
9
9
  import {
10
10
  isRecord
11
11
  } from "./chunk-UZSNFLDQ.js";
12
- import "./chunk-Q5KCYMUE.js";
12
+ import "./chunk-FNGZVOD4.js";
13
13
  import "./chunk-VEQXQN22.js";
14
14
 
15
15
  // src/command-protection-hook.ts
@@ -14,12 +14,12 @@ import {
14
14
  recoverCompletedTurn,
15
15
  spawnMuseMsp,
16
16
  startMuseSession
17
- } from "./chunk-4YOLKZQK.js";
17
+ } from "./chunk-ZJ5W3MDQ.js";
18
18
  import {
19
19
  AppServerProcess,
20
20
  buildCodexAgentEnv
21
- } from "./chunk-JBZNUWMJ.js";
22
- import "./chunk-TBKEZB4T.js";
21
+ } from "./chunk-64AMDDNX.js";
22
+ import "./chunk-JXYPBRHP.js";
23
23
  import {
24
24
  AGENT,
25
25
  OPENCODE_GO_PROVIDER,
@@ -29,7 +29,7 @@ import {
29
29
  headlessAgentUsagePath,
30
30
  isRecord,
31
31
  withTimeout
32
- } from "./chunk-Q5KCYMUE.js";
32
+ } from "./chunk-FNGZVOD4.js";
33
33
  import "./chunk-VEQXQN22.js";
34
34
 
35
35
  // src/headless-agent.ts
package/dist/src/index.js CHANGED
@@ -27,7 +27,7 @@ import {
27
27
  evaluateCommandProtection,
28
28
  extractToolCommand,
29
29
  reportCommandProtectionBlock
30
- } from "./chunk-7QO3HM4H.js";
30
+ } from "./chunk-ZJXG4VN4.js";
31
31
  import {
32
32
  ACCOUNT_RATE_LIMITS_UPDATED_METHOD,
33
33
  AGENT_MESSAGE_DELTA_METHOD,
@@ -65,10 +65,10 @@ import {
65
65
  spawnMuseMsp,
66
66
  startMuseSession,
67
67
  uuidV7
68
- } from "./chunk-4YOLKZQK.js";
68
+ } from "./chunk-ZJ5W3MDQ.js";
69
69
  import {
70
70
  publishedPullRequestUrls
71
- } from "./chunk-EBKIWJLA.js";
71
+ } from "./chunk-Z46UUGHD.js";
72
72
  import {
73
73
  ACCOUNT_RATE_LIMITS_READ_METHOD,
74
74
  AsyncLock,
@@ -143,7 +143,7 @@ import {
143
143
  timestampFromSeconds,
144
144
  upsertCredentialFileLines,
145
145
  writeSecureCredentialFile
146
- } from "./chunk-WC72KGDL.js";
146
+ } from "./chunk-CULXAMHI.js";
147
147
  import {
148
148
  ENGINE_ENV,
149
149
  monolithRequest,
@@ -153,15 +153,15 @@ import {
153
153
  resolveDiffBase,
154
154
  setAgentCredentialSnapshot,
155
155
  setLinearSessionId
156
- } from "./chunk-OCOIXNER.js";
156
+ } from "./chunk-45DWBRYV.js";
157
157
  import {
158
158
  getCodexModelProvider
159
- } from "./chunk-JBZNUWMJ.js";
159
+ } from "./chunk-64AMDDNX.js";
160
160
  import {
161
161
  SUBPROCESS_MAX_BUFFER,
162
162
  execAsync,
163
163
  execFileAsync
164
- } from "./chunk-TBKEZB4T.js";
164
+ } from "./chunk-JXYPBRHP.js";
165
165
  import {
166
166
  isRecord as isRecord2
167
167
  } from "./chunk-UZSNFLDQ.js";
@@ -411,7 +411,7 @@ import {
411
411
  workspaceTokenRequestSchema,
412
412
  workspaceTokenResponseSchema,
413
413
  wrapInTag
414
- } from "./chunk-Q5KCYMUE.js";
414
+ } from "./chunk-FNGZVOD4.js";
415
415
  import {
416
416
  cloneMcpConfig,
417
417
  ensureCompatibilityImports,
@@ -11666,7 +11666,7 @@ function toQueuedMessageInfo(message) {
11666
11666
  };
11667
11667
  }
11668
11668
  var subagentMcpConfigRequest = null;
11669
- var CodingAgentManager = class {
11669
+ var CodingAgentManager = class _CodingAgentManager {
11670
11670
  workingDirectory;
11671
11671
  messageQueue;
11672
11672
  initialized;
@@ -11691,6 +11691,10 @@ var CodingAgentManager = class {
11691
11691
  unreadSteers = /* @__PURE__ */ new Map();
11692
11692
  steersInFlight = /* @__PURE__ */ new Map();
11693
11693
  steerSettlements = /* @__PURE__ */ new Set();
11694
+ earlySteers = [];
11695
+ withdrawnSteers = /* @__PURE__ */ new WeakSet();
11696
+ earlySteerDelivery = new AsyncLock();
11697
+ turnOpen = false;
11694
11698
  lastSenderKey;
11695
11699
  // Unset until this process sends a turn, so a restart can't mistake the first one for a change.
11696
11700
  sentTurn = false;
@@ -11783,22 +11787,36 @@ var CodingAgentManager = class {
11783
11787
  initializeManager(processMessage) {
11784
11788
  this.messageQueue = new MessageQueueService(
11785
11789
  async (request, signal) => {
11786
- await Promise.all([this.refreshSubagentMcp(), this.refreshAutoCompactTokens()]);
11787
- const { request: delivered, senderKey } = this.withSenderLine(request);
11788
- const stopped = signal.aborted;
11789
- if (stopped && (request.engineTurn || !await this.keepStoppedRequest(delivered))) return;
11790
- await this.saveLastSenderKey(senderKey);
11791
- if (stopped) return;
11792
- const instructionsChanged = this.sentTurn && this.lastCustomInstructions !== request.customInstructions && !request.goalMode && !request.message.trimStart().startsWith("/");
11793
- this.sentTurn = true;
11794
- this.lastCustomInstructions = request.customInstructions;
11795
- const note = wrapInTag("Your instructions changed since your previous turn. Earlier turns followed the old version: follow the current instructions from here on, and leave earlier replies as they are.", REPLICAS_INSTRUCTIONS_TAG);
11796
- await processMessage(instructionsChanged ? { ...delivered, message: `${delivered.message}
11790
+ this.turnOpen = true;
11791
+ try {
11792
+ await Promise.all([this.refreshSubagentMcp(), this.refreshAutoCompactTokens()]);
11793
+ const { request: delivered, senderKey } = this.withSenderLine(request);
11794
+ const stopped = signal.aborted;
11795
+ if (stopped && (request.engineTurn || !await this.keepStoppedRequest(delivered))) return;
11796
+ await this.saveLastSenderKey(senderKey);
11797
+ if (stopped) return;
11798
+ const instructionsChanged = this.sentTurn && this.lastCustomInstructions !== request.customInstructions && !request.goalMode && !request.message.trimStart().startsWith("/");
11799
+ this.sentTurn = true;
11800
+ this.lastCustomInstructions = request.customInstructions;
11801
+ const note = wrapInTag("Your instructions changed since your previous turn. Earlier turns followed the old version: follow the current instructions from here on, and leave earlier replies as they are.", REPLICAS_INSTRUCTIONS_TAG);
11802
+ await processMessage(instructionsChanged ? { ...delivered, message: `${delivered.message}
11797
11803
 
11798
11804
  ${note}` } : delivered, signal);
11805
+ } finally {
11806
+ this.closeTurn();
11807
+ }
11799
11808
  },
11800
11809
  this.onProcessingChanged,
11801
- this.onMessageStarted,
11810
+ // Opened before the turn-start event persists, since a follow-up can arrive while it does.
11811
+ async (message) => {
11812
+ this.turnOpen = true;
11813
+ try {
11814
+ await this.onMessageStarted(message);
11815
+ } catch (error) {
11816
+ this.closeTurn();
11817
+ throw error;
11818
+ }
11819
+ },
11802
11820
  this.onQueueChanged
11803
11821
  );
11804
11822
  this.initialized = this.initialize();
@@ -11856,6 +11874,8 @@ ${request.message}` }, senderKey };
11856
11874
  async interrupt(persistRemoval) {
11857
11875
  const queuedMessages = this.messageQueue.drainQueue();
11858
11876
  const unreadSteers = [...this.unreadSteers.values()];
11877
+ const earlySteers = this.earlySteers.splice(0);
11878
+ for (const steer of earlySteers) this.withdrawnSteers.add(steer);
11859
11879
  this.unreadSteers.clear();
11860
11880
  this.onQueueChanged();
11861
11881
  this.messageQueue.cancelActiveTurn();
@@ -11865,6 +11885,8 @@ ${request.message}` }, senderKey };
11865
11885
  await this.interruptActiveTurn();
11866
11886
  } catch (error) {
11867
11887
  for (const steer of unreadSteers) this.unreadSteers.set(steer.message.id, steer);
11888
+ for (const steer of earlySteers) this.withdrawnSteers.delete(steer);
11889
+ this.earlySteers.push(...earlySteers);
11868
11890
  this.onQueueChanged();
11869
11891
  this.restoreQueuedMessages(queuedMessages.map((message, index) => ({ message, index })));
11870
11892
  throw error;
@@ -11967,11 +11989,17 @@ ${request.message}` }, senderKey };
11967
11989
  let steered = false;
11968
11990
  const { request: withSender, senderKey } = this.withSenderLine(taken.message);
11969
11991
  const note = wrapInTag("You received this message while working. The chat folds everything before your last message of this turn, so that message must answer it too, even if you already did earlier.", REPLICAS_INSTRUCTIONS_TAG);
11970
- const delivered = withSender.goalMode || withSender.message.trimStart().startsWith("/") ? withSender : { ...withSender, message: `${withSender.message}
11992
+ const command = withSender.goalMode || withSender.message.trimStart().startsWith("/");
11993
+ const delivered = command ? withSender : { ...withSender, message: `${withSender.message}
11971
11994
 
11972
11995
  ${note}` };
11973
11996
  try {
11974
- steered = await this.steerRequest(delivered);
11997
+ steered = this.earlySteers.length === 0 && await this.steerRequest(delivered);
11998
+ if (!steered && this.turnOpen && !command && this.steerRequest !== _CodingAgentManager.prototype.steerRequest) {
11999
+ this.earlySteers.push(delivered);
12000
+ steered = true;
12001
+ void this.deliverEarlySteers();
12002
+ }
11975
12003
  if (steered) await this.saveLastSenderKey(senderKey);
11976
12004
  } catch (error) {
11977
12005
  console.error("[CodingAgentManager] steerRequest threw, keeping message queued:", error);
@@ -12007,9 +12035,14 @@ ${note}` };
12007
12035
  }
12008
12036
  return { success: true, queue: this.getQueue() };
12009
12037
  }
12038
+ closeTurn() {
12039
+ this.turnOpen = false;
12040
+ if (this.earlySteers.length > 0) this.requeueUnreadSteers();
12041
+ }
12010
12042
  requeueUnreadSteers() {
12011
12043
  const steers = [...this.unreadSteers.values()].map(({ message }) => message);
12012
12044
  this.unreadSteers.clear();
12045
+ for (const steer of this.earlySteers.splice(0)) this.withdrawnSteers.add(steer);
12013
12046
  this.onQueueChanged();
12014
12047
  this.restoreQueuedMessages(steers.map((message) => ({ message, index: 0 })));
12015
12048
  if (steers.length > 0) {
@@ -12032,6 +12065,18 @@ ${note}` };
12032
12065
  steerRequest(_request) {
12033
12066
  return Promise.resolve(false);
12034
12067
  }
12068
+ // A held steer withdrawn by a stop or a turn ending must not reach a later turn, even mid-request.
12069
+ isSteerWithdrawn(request) {
12070
+ return this.withdrawnSteers.has(request);
12071
+ }
12072
+ deliverEarlySteers() {
12073
+ return this.earlySteerDelivery.run(async () => {
12074
+ for (let next = this.earlySteers[0]; next && await this.steerRequest(next).catch(() => false); next = this.earlySteers[0]) {
12075
+ if (this.earlySteers[0] !== next) return;
12076
+ this.earlySteers.shift();
12077
+ }
12078
+ });
12079
+ }
12035
12080
  emitContextUsage(payload) {
12036
12081
  const event = {
12037
12082
  timestamp: (/* @__PURE__ */ new Date()).toISOString(),
@@ -13703,6 +13748,7 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
13703
13748
  };
13704
13749
  promptStream.push({ ...userMessage, message: { role: "user", content } });
13705
13750
  for (const { userMessage: steer } of steers.values()) promptStream.push({ ...steer, priority: "next" });
13751
+ void this.deliverEarlySteers();
13706
13752
  });
13707
13753
  } finally {
13708
13754
  if (this.turnPromptRecorded) this.unreadPrompt = null;
@@ -14762,10 +14808,13 @@ var CodexAspManager = class extends CodingAgentManager {
14762
14808
  const result = await this.requestActiveTurnWithReconciliation(
14763
14809
  "steer",
14764
14810
  expectedTurnId,
14765
- (host, turnId) => host.client.request(
14766
- TURN_STEER_METHOD,
14767
- { threadId, expectedTurnId: turnId, input, clientUserMessageId: request.id }
14768
- )
14811
+ (host, turnId) => {
14812
+ if (this.isSteerWithdrawn(request)) throw new Error("Steer was withdrawn");
14813
+ return host.client.request(
14814
+ TURN_STEER_METHOD,
14815
+ { threadId, expectedTurnId: turnId, input, clientUserMessageId: request.id }
14816
+ );
14817
+ }
14769
14818
  );
14770
14819
  if (!result.ok) {
14771
14820
  await removeTempImageFiles(tempImagePaths);
@@ -15344,6 +15393,7 @@ ${text.slice(-24e3)}`
15344
15393
  [THREAD_COMPACTED_METHOD]: (notification) => {
15345
15394
  if (!matchesTurn(notification.params.threadId, notification.params.turnId)) return;
15346
15395
  this.compacting = false;
15396
+ void this.deliverEarlySteers();
15347
15397
  },
15348
15398
  [TURN_STARTED_METHOD]: (notification) => {
15349
15399
  if (notification.params.threadId !== threadId) return;
@@ -15351,6 +15401,7 @@ ${text.slice(-24e3)}`
15351
15401
  observedTurnIds.add(notification.params.turn.id);
15352
15402
  this.activeTurnId = notification.params.turn.id;
15353
15403
  this.onCodexTurnStarted?.(threadId, notification.params.turn.id);
15404
+ void this.deliverEarlySteers();
15354
15405
  lastCompletedTurn = null;
15355
15406
  completedItems.length = 0;
15356
15407
  agentMessageDeltas.clear();
@@ -15378,7 +15429,10 @@ ${text.slice(-24e3)}`
15378
15429
  [ITEM_COMPLETED_METHOD]: (notification) => {
15379
15430
  if (!matchesTurn(notification.params.threadId, notification.params.turnId)) return;
15380
15431
  completedItems.push(notification.params.item);
15381
- if (notification.params.item.type === "contextCompaction") this.compacting = false;
15432
+ if (notification.params.item.type === "contextCompaction") {
15433
+ this.compacting = false;
15434
+ void this.deliverEarlySteers();
15435
+ }
15382
15436
  const itemFailed = notification.params.item.type === "commandExecution" && typeof notification.params.item.exitCode === "number" && notification.params.item.exitCode !== 0;
15383
15437
  this.completeItem(
15384
15438
  notification.params.turnId,
@@ -15471,6 +15525,7 @@ ${text.slice(-24e3)}`
15471
15525
  observedTurnIds.add(started.turn.id);
15472
15526
  this.activeTurnId = started.turn.id;
15473
15527
  this.onCodexTurnStarted?.(threadId, started.turn.id);
15528
+ void this.deliverEarlySteers();
15474
15529
  this.startTurn(started.turn);
15475
15530
  interruptIfStopped();
15476
15531
  }
@@ -16187,6 +16242,7 @@ var CursorManager = class extends CodingAgentManager {
16187
16242
  }
16188
16243
  }, this.workingDirectory);
16189
16244
  this.activeRun = run;
16245
+ void this.deliverEarlySteers();
16190
16246
  const events = run.stream()[Symbol.asyncIterator]();
16191
16247
  let interrupted = false;
16192
16248
  while (true) {
@@ -3,13 +3,13 @@ import { createRequire as __createRequire } from 'node:module';
3
3
  const require = __createRequire(import.meta.url);
4
4
  import {
5
5
  publishedPullRequestUrls
6
- } from "./chunk-EBKIWJLA.js";
6
+ } from "./chunk-Z46UUGHD.js";
7
7
  import {
8
8
  isRecord
9
9
  } from "./chunk-UZSNFLDQ.js";
10
10
  import {
11
11
  shouldRefreshPullRequests
12
- } from "./chunk-Q5KCYMUE.js";
12
+ } from "./chunk-FNGZVOD4.js";
13
13
  import "./chunk-VEQXQN22.js";
14
14
 
15
15
  // src/services/post-tool-pr-notifier.ts
@@ -11,7 +11,7 @@ import {
11
11
  spawnSubagentRequestSchema,
12
12
  subagentResponseSchema,
13
13
  waitSubagentRequestSchema
14
- } from "./chunk-Q5KCYMUE.js";
14
+ } from "./chunk-FNGZVOD4.js";
15
15
  import "./chunk-VEQXQN22.js";
16
16
 
17
17
  // src/subagent-mcp.ts
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "replicas-engine",
3
- "version": "0.1.1295",
3
+ "version": "0.1.1297",
4
4
  "description": "Lightweight API server for Replicas workspaces",
5
5
  "type": "module",
6
6
  "main": "dist/src/index.js",