osborn 0.9.78 → 0.9.80
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/index.js +39 -0
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -1361,6 +1361,36 @@ async function main() {
|
|
|
1361
1361
|
console.error('🧟 [ZOMBIE-WATCHDOG] poll error:', err instanceof Error ? err.message : err);
|
|
1362
1362
|
}
|
|
1363
1363
|
}, WATCHDOG_POLL_MS);
|
|
1364
|
+
// ── 0.9.80: Event-loss adopter (poll-based) ──
|
|
1365
|
+
// After a leave/rejoin cycle the same Room instance can stop delivering
|
|
1366
|
+
// ParticipantConnected entirely — observed 2026-07-28: the leave-room guard
|
|
1367
|
+
// saw "1 participant(s) still in room" while the agent sat at "Waiting for
|
|
1368
|
+
// user to connect" (state knew, events never fired; user stuck on
|
|
1369
|
+
// "Connecting..." forever). Same blind-spot family as the zombie watchdog:
|
|
1370
|
+
// never trust the event stream alone. Every 5s: participant present but no
|
|
1371
|
+
// voice session → re-emit ParticipantConnected (60s per-identity cooldown
|
|
1372
|
+
// so a slow in-flight session creation isn't double-fired).
|
|
1373
|
+
const adoptAttempts = new Map();
|
|
1374
|
+
setInterval(() => {
|
|
1375
|
+
try {
|
|
1376
|
+
if (livekitState.status !== 'connected')
|
|
1377
|
+
return;
|
|
1378
|
+
if (currentSession)
|
|
1379
|
+
return;
|
|
1380
|
+
const p = room.remoteParticipants.values().next().value;
|
|
1381
|
+
if (!p)
|
|
1382
|
+
return;
|
|
1383
|
+
const last = adoptAttempts.get(p.identity) ?? 0;
|
|
1384
|
+
if (Date.now() - last < 60_000)
|
|
1385
|
+
return;
|
|
1386
|
+
adoptAttempts.set(p.identity, Date.now());
|
|
1387
|
+
console.log(`📥 [ADOPT-POLL] ${p.identity} present with no session — re-emitting ParticipantConnected`);
|
|
1388
|
+
room.emit(RoomEvent.ParticipantConnected, p);
|
|
1389
|
+
}
|
|
1390
|
+
catch (err) {
|
|
1391
|
+
console.error('📥 [ADOPT-POLL] error:', err instanceof Error ? err.message : err);
|
|
1392
|
+
}
|
|
1393
|
+
}, 5_000);
|
|
1364
1394
|
/**
|
|
1365
1395
|
* Hard-kill the in-flight Claude SDK query AND the persistent subprocess.
|
|
1366
1396
|
*
|
|
@@ -4795,6 +4825,15 @@ async function main() {
|
|
|
4795
4825
|
}
|
|
4796
4826
|
if (livekitState.status !== 'connected')
|
|
4797
4827
|
return; // already out — no-op
|
|
4828
|
+
// Never abandon a user who is CURRENTLY in the room. Stale/racing
|
|
4829
|
+
// leave-room calls (a previous client's teardown landing after a new
|
|
4830
|
+
// client joined) were kicking the agent out mid-adopt, stranding the new
|
|
4831
|
+
// user on "Connecting..." (observed 2026-07-28). The alone-timer handles
|
|
4832
|
+
// the real departure when they actually leave.
|
|
4833
|
+
if (room.remoteParticipants.size > 0) {
|
|
4834
|
+
console.log(`🛑 /leave-room ignored (${reason}) — ${room.remoteParticipants.size} participant(s) still in room`);
|
|
4835
|
+
return;
|
|
4836
|
+
}
|
|
4798
4837
|
intentionalLeave = true;
|
|
4799
4838
|
console.log(`🚪 Leaving LiveKit room (${reason}) — stops connection-minute burn`);
|
|
4800
4839
|
armIdleExitTimer(`explicit leave (${reason})`);
|