switchroom 0.16.9 → 0.16.10

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.
@@ -51674,8 +51674,8 @@ import { existsSync, readFileSync } from "node:fs";
51674
51674
  import { dirname, join } from "node:path";
51675
51675
 
51676
51676
  // src/build-info.ts
51677
- var VERSION = "0.16.9";
51678
- var COMMIT_SHA = "1a926737";
51677
+ var VERSION = "0.16.10";
51678
+ var COMMIT_SHA = "8af198e9";
51679
51679
 
51680
51680
  // src/cli/resolve-version.ts
51681
51681
  function readPackageVersion() {
@@ -22587,7 +22587,7 @@ import { existsSync as existsSync6, readFileSync as readFileSync4 } from "node:f
22587
22587
  import { dirname as dirname4, join as join2 } from "node:path";
22588
22588
 
22589
22589
  // src/build-info.ts
22590
- var VERSION = "0.16.9";
22590
+ var VERSION = "0.16.10";
22591
22591
 
22592
22592
  // src/cli/resolve-version.ts
22593
22593
  function readPackageVersion() {
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "switchroom",
3
- "version": "0.16.9",
4
- "description": "Run Claude Code 24/7 on your Claude Pro/Max subscription over Telegram. Open-source alternative to OpenClaw and NanoClaw \u2014 no API keys.",
3
+ "version": "0.16.10",
4
+ "description": "Run Claude Code 24/7 on your Claude Pro/Max subscription over Telegram. Open-source alternative to OpenClaw and NanoClaw no API keys.",
5
5
  "type": "module",
6
6
  "bin": {
7
7
  "switchroom": "./dist/cli/switchroom.js"
@@ -56047,10 +56047,10 @@ function readTurnActiveMarkerAgeMs(stateDir, now) {
56047
56047
  }
56048
56048
 
56049
56049
  // ../src/build-info.ts
56050
- var VERSION = "0.16.9";
56051
- var COMMIT_SHA = "1a926737";
56052
- var COMMIT_DATE = "2026-06-28T06:20:58Z";
56053
- var LATEST_PR = 2622;
56050
+ var VERSION = "0.16.10";
56051
+ var COMMIT_SHA = "8af198e9";
56052
+ var COMMIT_DATE = "2026-06-28T07:14:15Z";
56053
+ var LATEST_PR = 2625;
56054
56054
  var COMMITS_AHEAD_OF_TAG = 0;
56055
56055
 
56056
56056
  // gateway/boot-version.ts
@@ -58534,7 +58534,7 @@ function endCurrentTurnAtomic(turn) {
58534
58534
  `);
58535
58535
  }
58536
58536
  if (OBLIGATION_LEDGER_ENABLED) {
58537
- if (turn.finalAnswerDelivered) {
58537
+ if (turn.finalAnswerDelivered || turn.replyCalled) {
58538
58538
  obligationLedger.close(turn.turnId);
58539
58539
  } else {
58540
58540
  obligationLedger.noteTurnEnded(turn.turnId, Date.now());
@@ -3375,15 +3375,24 @@ function endCurrentTurnAtomic(turn: CurrentTurn): void {
3375
3375
  // finalAnswerDelivered===false → stays open → re-presented (the intended
3376
3376
  // catch). close() is a no-op for synthetic turns (turnId not in the ledger).
3377
3377
  // No-op when the flag is off.
3378
+ //
3379
+ // #2624 — sr-* model short-reply cascade fix. When the model routes through
3380
+ // LiteLLM (sr-* path), the claude CLI calls reply("OK", {disable_notification:
3381
+ // true}) for short answers — below the 200-char backstop and notification-
3382
+ // suppressed, so isFinalAnswerReply returns false and finalAnswerDelivered stays
3383
+ // false. This triggers a cascade: obligation re-presents with growing 25k-token
3384
+ // context, blocking the agent for minutes. The ack-then-ghost case that
3385
+ // obligations are designed to catch ends via silence_fallback, NOT turn_end.
3386
+ // At turn_end with replyCalled=true the model explicitly signalled completion
3387
+ // AND replied, so the obligation is satisfied regardless of finalAnswerDelivered.
3378
3388
  if (OBLIGATION_LEDGER_ENABLED) {
3379
- if (turn.finalAnswerDelivered) {
3389
+ if (turn.finalAnswerDelivered || turn.replyCalled) {
3380
3390
  obligationLedger.close(turn.turnId)
3381
3391
  } else {
3382
- // Turn ended WITHOUT a final answer. If this turn was handling an open
3383
- // obligation, stamp its grace clock so the idle sweep waits before
3384
- // re-presenting/escalating a slow/worker answer may still be in flight
3385
- // (the over-escalation fix). No-op when turn.turnId isn't an open
3386
- // obligation (synthetic / already-closed turn).
3392
+ // Turn ended WITHOUT any reply (no ack, no answer). If this turn was
3393
+ // handling an open obligation, stamp its grace clock so the idle sweep
3394
+ // waits before re-presenting/escalating. No-op when turn.turnId isn't
3395
+ // in the ledger (synthetic / already-closed turn).
3387
3396
  obligationLedger.noteTurnEnded(turn.turnId, Date.now())
3388
3397
  }
3389
3398
  }