replicas-engine 0.1.649 → 0.1.651

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.
@@ -5922,7 +5922,7 @@ var DEFAULT_CODEX_ARGS = [
5922
5922
  var MIN_CODEX_CLI_VERSION = "0.144.6";
5923
5923
  var CODEX_UPGRADE_TIMEOUT_MS = 12e4;
5924
5924
  var codexCliVersionEnsured = null;
5925
- var ENGINE_PACKAGE_VERSION = "0.1.649";
5925
+ var ENGINE_PACKAGE_VERSION = "0.1.651";
5926
5926
  var INITIALIZE_METHOD = "initialize";
5927
5927
  var INITIALIZED_NOTIFICATION = "initialized";
5928
5928
  var ACCOUNT_LOGIN_START_METHOD = "account/login/start";
@@ -7,7 +7,7 @@ import {
7
7
  isUnsafeMemoryOutput,
8
8
  putPresignedFile,
9
9
  recoverCompletedTurn
10
- } from "./chunk-O5DMGWM7.js";
10
+ } from "./chunk-CJKDLHFP.js";
11
11
 
12
12
  // src/headless-agent.ts
13
13
  import { createHash } from "crypto";
package/dist/src/index.js CHANGED
@@ -172,7 +172,7 @@ import {
172
172
  serializeCanvasContentResponse,
173
173
  shellQuotePosix,
174
174
  stripAgentDiagnosticErrors
175
- } from "./chunk-O5DMGWM7.js";
175
+ } from "./chunk-CJKDLHFP.js";
176
176
 
177
177
  // src/index.ts
178
178
  import { serve } from "@hono/node-server";
@@ -3518,7 +3518,11 @@ var CodingAgentManager = class {
3518
3518
  this.initialized = this.initialize();
3519
3519
  }
3520
3520
  async interrupt() {
3521
- const { queue, isProcessing } = this.drainQueueForInterrupt();
3521
+ const queue = this.messageQueue.drainQueue({
3522
+ maxItems: MAX_INTERRUPT_QUEUE_ITEMS,
3523
+ maxChars: MAX_INTERRUPT_QUEUE_CHARS
3524
+ });
3525
+ const isProcessing = this.isProcessing();
3522
3526
  if (isProcessing) {
3523
3527
  await this.interruptActiveTurn();
3524
3528
  const event = {
@@ -3638,16 +3642,6 @@ var CodingAgentManager = class {
3638
3642
  }
3639
3643
  return parts.length > 0 ? parts.join("\n\n") : void 0;
3640
3644
  }
3641
- drainQueueForInterrupt() {
3642
- const queue = this.messageQueue.drainQueue({
3643
- maxItems: MAX_INTERRUPT_QUEUE_ITEMS,
3644
- maxChars: MAX_INTERRUPT_QUEUE_CHARS
3645
- });
3646
- return {
3647
- queue,
3648
- isProcessing: this.messageQueue.isProcessing()
3649
- };
3650
- }
3651
3645
  emitInterruptedQueueEvent(queue) {
3652
3646
  const linearSessionId = ENGINE_ENV.REPLICAS_LINEAR_SESSION_ID;
3653
3647
  if (!linearSessionId || queue.length === 0) {
@@ -3744,6 +3738,7 @@ function buildClaudeAgentEnv(overrides) {
3744
3738
  env.GH_CONFIG_DIR = void 0;
3745
3739
  env.CLAUDE_CODE_ADDITIONAL_DIRECTORIES_CLAUDE_MD = "1";
3746
3740
  env.CLAUDE_CODE_DISABLE_AUTO_MEMORY = "1";
3741
+ env.CLAUDE_CODE_EMIT_SESSION_STATE_EVENTS = "1";
3747
3742
  return env;
3748
3743
  }
3749
3744
  function shouldStripAnthropicApiKey(isBedrock) {
@@ -4513,6 +4508,9 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
4513
4508
  backgroundContinuationTimer = null;
4514
4509
  pendingInterrupt = false;
4515
4510
  activeBackgroundTasks = /* @__PURE__ */ new Set();
4511
+ // Set when background tasks outlive a turn; cleared once their completion
4512
+ // has been reported through onTurnComplete.
4513
+ pendingBackgroundCompletion = false;
4516
4514
  partialMessageStreams = /* @__PURE__ */ new Map();
4517
4515
  partialMessageFlushTimers = /* @__PURE__ */ new Map();
4518
4516
  systemPromptOverride;
@@ -4581,7 +4579,7 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
4581
4579
  return super.isProcessing() || isClaudeSessionActive(this.sessionActivity) || this.activeBackgroundTasks.size > 0;
4582
4580
  }
4583
4581
  hasActiveBackgroundTasks() {
4584
- return this.activeBackgroundTasks.size > 0;
4582
+ return this.activeBackgroundTasks.size > 0 || this.pendingBackgroundCompletion && isClaudeSessionActive(this.sessionActivity) && !this.messageQueue.isProcessing();
4585
4583
  }
4586
4584
  async listSlashCommands() {
4587
4585
  await this.initialized;
@@ -5189,6 +5187,9 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5189
5187
  if (hadActiveBackgroundTasks && this.activeBackgroundTasks.size === 0) {
5190
5188
  this.startBackgroundContinuationGrace();
5191
5189
  }
5190
+ if (!this.pendingTurn && this.activeBackgroundTasks.size > 0) {
5191
+ this.pendingBackgroundCompletion = true;
5192
+ }
5192
5193
  await this.handleMessage(msg);
5193
5194
  if (linearSessionId && this.sessionLinearForwarder) {
5194
5195
  this.sessionLinearForwarder.processClaudeEventForPlan(msg);
@@ -5199,6 +5200,7 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5199
5200
  this.sessionLinearForwarder?.flushThoughtAsResponse();
5200
5201
  this.resolvePendingTurn();
5201
5202
  }
5203
+ this.maybeCompleteBackgroundTurn();
5202
5204
  }
5203
5205
  } catch (error) {
5204
5206
  loopError = error;
@@ -5219,7 +5221,11 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5219
5221
  }
5220
5222
  this.failPendingTurn(pendingError);
5221
5223
  if (this.activeQuery === response) {
5224
+ const orphanedBackgroundCompletion = this.pendingBackgroundCompletion && !this.messageQueue.isProcessing();
5222
5225
  this.clearSessionState();
5226
+ if (orphanedBackgroundCompletion) {
5227
+ this.notifyBackgroundTurnComplete();
5228
+ }
5223
5229
  }
5224
5230
  }
5225
5231
  }
@@ -5234,6 +5240,7 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5234
5240
  this.clearBackgroundContinuationTimer();
5235
5241
  resetClaudeSessionActivity(this.sessionActivity);
5236
5242
  this.activeBackgroundTasks.clear();
5243
+ this.pendingBackgroundCompletion = false;
5237
5244
  for (const timer of this.partialMessageFlushTimers.values()) {
5238
5245
  clearTimeout(timer);
5239
5246
  }
@@ -5245,8 +5252,19 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5245
5252
  if (!pending) return;
5246
5253
  this.pendingTurn = null;
5247
5254
  this.pendingInterrupt = false;
5255
+ this.pendingBackgroundCompletion = this.activeBackgroundTasks.size > 0;
5248
5256
  pending.resolve();
5249
5257
  }
5258
+ maybeCompleteBackgroundTurn() {
5259
+ if (!this.pendingBackgroundCompletion || this.pendingTurn || this.messageQueue.isProcessing() || this.activeBackgroundTasks.size > 0 || isClaudeSessionActive(this.sessionActivity)) return;
5260
+ this.pendingBackgroundCompletion = false;
5261
+ this.notifyBackgroundTurnComplete();
5262
+ }
5263
+ notifyBackgroundTurnComplete() {
5264
+ void this.historyFile.flush().then(() => this.onTurnComplete()).catch((error) => {
5265
+ console.error("[ClaudeManager] Background turn completion failed:", error);
5266
+ });
5267
+ }
5250
5268
  failPendingTurn(err) {
5251
5269
  const pending = this.pendingTurn;
5252
5270
  if (!pending) return;
@@ -5261,6 +5279,7 @@ var ClaudeManager = class _ClaudeManager extends CodingAgentManager {
5261
5279
  this.backgroundContinuationTimer = null;
5262
5280
  if (this.activeBackgroundTasks.size > 0 || !expireClaudeSessionFallbackContinuation(this.sessionActivity)) return;
5263
5281
  this.emitSyntheticEvent(CLAUDE_ACTIVITY_STATUS_EVENT_TYPE, { state: "idle" });
5282
+ this.maybeCompleteBackgroundTurn();
5264
5283
  }, CLAUDE_BACKGROUND_CONTINUATION_GRACE_MS);
5265
5284
  }
5266
5285
  clearBackgroundContinuationTimer() {
@@ -10684,7 +10703,7 @@ function hasActiveAgentWork(chat) {
10684
10703
  return chat.provider.isProcessing() || (chat.provider.hasActiveBackgroundTasks?.() ?? false);
10685
10704
  }
10686
10705
  function hasActiveChatTurn(chat) {
10687
- return chat.hasActiveTurn || chat.pendingMessageIds.length > 0;
10706
+ return chat.hasActiveTurn || chat.pendingMessageIds.length > 0 || (chat.provider.hasActiveBackgroundTasks?.() ?? false);
10688
10707
  }
10689
10708
  function isPersistedChat(value) {
10690
10709
  if (!isRecord2(value)) {
@@ -11431,17 +11450,13 @@ var ChatService = class {
11431
11450
  if (!chat.hasActiveTurn) {
11432
11451
  const queuedMessageIds = new Set(chat.provider.getQueue().map((message) => message.id));
11433
11452
  const completedMessageId = chat.pendingMessageIds.find((messageId) => !queuedMessageIds.has(messageId));
11434
- if (!completedMessageId) {
11435
- await this.publishAgentTurnCompleteWebhook(chat);
11436
- return;
11437
- }
11438
11453
  chat.pendingMessageIds = chat.pendingMessageIds.filter((messageId) => messageId !== completedMessageId);
11439
11454
  }
11440
11455
  chat.hasActiveTurn = false;
11441
11456
  chat.activeMessageId = null;
11442
11457
  this.agentChatActivityTrackerService.noteTurnEnded(chatId);
11443
11458
  const completedAt = (/* @__PURE__ */ new Date()).toISOString();
11444
- const processing = chat.provider.getQueue().length > 0;
11459
+ const processing = chat.provider.getQueue().length > 0 || (chat.provider.hasActiveBackgroundTasks?.() ?? false);
11445
11460
  this.publish({
11446
11461
  type: "chat.turn.completed",
11447
11462
  payload: {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "replicas-engine",
3
- "version": "0.1.649",
3
+ "version": "0.1.651",
4
4
  "description": "Lightweight API server for Replicas workspaces",
5
5
  "type": "module",
6
6
  "main": "dist/src/index.js",