@1presence/bridge 0.96.0 → 0.97.0
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/claude.js +17 -15
- package/dist/index.js +5 -4
- package/package.json +1 -1
package/dist/claude.js
CHANGED
|
@@ -245,7 +245,9 @@ export function makeGatedPromptStream(messages) {
|
|
|
245
245
|
};
|
|
246
246
|
}
|
|
247
247
|
export function spawnClaude(params) {
|
|
248
|
-
const { conversationId, presenceSessionId, text, uid, history, vaultFileOpen, clientCapabilities, syncedFolders, model: perTurnModel, onEvent, onDone, onError, onNotice } = params;
|
|
248
|
+
const { conversationId, presenceSessionId, chatSessionId, text, uid, history, vaultFileOpen, clientCapabilities, syncedFolders, model: perTurnModel, onEvent, onDone, onError, onNotice } = params;
|
|
249
|
+
const sessionTag = ` · session ${chatSessionId ?? conversationId}`;
|
|
250
|
+
const errLine = (text) => paint(SECTION_COLORS.error, `${text}${sessionTag}`);
|
|
249
251
|
const systemPromptPath = join(tmpdir(), `agent-${uid}.md`);
|
|
250
252
|
const mcpConfigPath = join(tmpdir(), `mcp-${uid}.json`);
|
|
251
253
|
if (verbose) {
|
|
@@ -270,7 +272,7 @@ export function spawnClaude(params) {
|
|
|
270
272
|
debugBlock('user · this turn', SECTION_COLORS.user, text);
|
|
271
273
|
}
|
|
272
274
|
else {
|
|
273
|
-
process.stderr.write(`[bridge] session ${
|
|
275
|
+
process.stderr.write(`[bridge] session ${chatSessionId ?? '(none)'} turn ${conversationId}\n`);
|
|
274
276
|
}
|
|
275
277
|
void vaultFileOpen;
|
|
276
278
|
void clientCapabilities;
|
|
@@ -392,7 +394,7 @@ export function spawnClaude(params) {
|
|
|
392
394
|
if (blockText && TOOL_CALL_XML_RE.test(blockText)) {
|
|
393
395
|
const cleaned = stripToolCallXml(blockText);
|
|
394
396
|
if (cleaned !== blockText) {
|
|
395
|
-
process.stderr.write(
|
|
397
|
+
process.stderr.write(errLine(`[bridge] suppressed confabulated tool-call XML in assistant text`) + '\n');
|
|
396
398
|
block['text'] = cleaned;
|
|
397
399
|
blockText = cleaned;
|
|
398
400
|
}
|
|
@@ -406,7 +408,7 @@ export function spawnClaude(params) {
|
|
|
406
408
|
apiErrorText = blockText.trim();
|
|
407
409
|
if (isAuthFailure)
|
|
408
410
|
sawAuthFailure = true;
|
|
409
|
-
process.stderr.write(
|
|
411
|
+
process.stderr.write(errLine(`[bridge] ${blockText.replace(/\n+/g, ' ')}`) + '\n');
|
|
410
412
|
return false;
|
|
411
413
|
}
|
|
412
414
|
producedRealOutput = true;
|
|
@@ -437,7 +439,7 @@ export function spawnClaude(params) {
|
|
|
437
439
|
if (block['is_error']) {
|
|
438
440
|
const detail = toolResultText(out).replace(/\s+/g, ' ').trim();
|
|
439
441
|
const shown = detail.length > 400 ? `${detail.slice(0, 400)}…` : detail;
|
|
440
|
-
process.stderr.write(
|
|
442
|
+
process.stderr.write(errLine(`[bridge] ✗ tool error ← ${name}: ${shown || 'no detail'}`) + '\n');
|
|
441
443
|
}
|
|
442
444
|
if (!verbose && !debug)
|
|
443
445
|
continue;
|
|
@@ -464,7 +466,7 @@ export function spawnClaude(params) {
|
|
|
464
466
|
const detail = joinErrorDetail(event['result'], event['errors']);
|
|
465
467
|
apiErrorText = joinErrorDetail(apiErrorText, detail) || apiErrorText;
|
|
466
468
|
const subtype = event['subtype'] ? ` subtype=${event['subtype']}` : '';
|
|
467
|
-
process.stderr.write(
|
|
469
|
+
process.stderr.write(errLine(`[bridge] result error${status != null ? ` (${status})` : ''}${subtype}: ${apiErrorText || 'unknown'}`) + '\n');
|
|
468
470
|
if (!detail) {
|
|
469
471
|
let raw;
|
|
470
472
|
try {
|
|
@@ -473,7 +475,7 @@ export function spawnClaude(params) {
|
|
|
473
475
|
catch {
|
|
474
476
|
raw = String(event);
|
|
475
477
|
}
|
|
476
|
-
process.stderr.write(
|
|
478
|
+
process.stderr.write(errLine(`[bridge] result raw: ${raw.slice(0, 2000)}`) + '\n');
|
|
477
479
|
}
|
|
478
480
|
}
|
|
479
481
|
}
|
|
@@ -553,11 +555,11 @@ export function spawnClaude(params) {
|
|
|
553
555
|
return;
|
|
554
556
|
mcpReconnecting = true;
|
|
555
557
|
lastMcpReconnectAt = now;
|
|
556
|
-
process.stderr.write(
|
|
558
|
+
process.stderr.write(errLine('[bridge] remote MCP connection lost — reconnecting and retrying') + '\n');
|
|
557
559
|
onNotice?.('Reconnecting to 1Presence tools…');
|
|
558
560
|
void q.reconnectMcpServer(REMOTE_MCP_SERVER_NAME)
|
|
559
561
|
.then(() => process.stderr.write(paint(SECTION_COLORS.result, '[bridge] remote MCP reconnected') + '\n'))
|
|
560
|
-
.catch((err) => process.stderr.write(
|
|
562
|
+
.catch((err) => process.stderr.write(errLine(`[bridge] remote MCP reconnect failed: ${err.message}`) + '\n'))
|
|
561
563
|
.finally(() => { mcpReconnecting = false; });
|
|
562
564
|
};
|
|
563
565
|
try {
|
|
@@ -590,9 +592,9 @@ export function spawnClaude(params) {
|
|
|
590
592
|
detail = ` — ${remote.error.replace(/\s+/g, ' ').trim().slice(0, 300)}`;
|
|
591
593
|
}
|
|
592
594
|
catch { }
|
|
593
|
-
process.stderr.write(
|
|
595
|
+
process.stderr.write(errLine(`[bridge] FATAL no 1Presence tools this turn (${surface.status}) — ending the turn rather than answering blind${detail}`) + '\n');
|
|
594
596
|
if (surface.status === 'needs-auth' && !detail) {
|
|
595
|
-
process.stderr.write(
|
|
597
|
+
process.stderr.write(errLine('[bridge] ↳ the server asked for OAuth, which Local Mode does not use — this is NOT a stale local token, and restarting will not clear it. The gateway is rejecting this account\'s token on /mcp.') + '\n');
|
|
596
598
|
}
|
|
597
599
|
active.delete(conversationId);
|
|
598
600
|
clearTimeout(inputReleaseTimer);
|
|
@@ -604,7 +606,7 @@ export function spawnClaude(params) {
|
|
|
604
606
|
}
|
|
605
607
|
else if (subtype === 'api_retry') {
|
|
606
608
|
const r = m;
|
|
607
|
-
process.stderr.write(
|
|
609
|
+
process.stderr.write(errLine(`[bridge] api retry ${r.attempt ?? '?'}/${r.max_retries ?? '?'}${r.error_status != null ? ` (${r.error_status})` : ''}: ${r.error ?? 'unknown'}${r.retry_delay_ms != null ? `, next in ${r.retry_delay_ms}ms` : ''}`) + '\n');
|
|
608
610
|
const attempt = r.attempt ?? 0;
|
|
609
611
|
if (attempt >= 2 || (r.retry_delay_ms ?? 0) >= 2000) {
|
|
610
612
|
onNotice?.(formatRetryNotice(attempt, r.max_retries ?? 0, r.retry_delay_ms));
|
|
@@ -629,7 +631,7 @@ export function spawnClaude(params) {
|
|
|
629
631
|
const full = joinErrorDetail(`API Error: ${am.error}`, msgText, rid);
|
|
630
632
|
if (!apiErrorText || /^API Error: \w+$/.test(apiErrorText))
|
|
631
633
|
apiErrorText = full;
|
|
632
|
-
process.stderr.write(
|
|
634
|
+
process.stderr.write(errLine(`[bridge] assistant error: ${joinErrorDetail(am.error, msgText, rid)}`) + '\n');
|
|
633
635
|
break;
|
|
634
636
|
}
|
|
635
637
|
const event = { type: 'assistant', message: am.message, error: am.error };
|
|
@@ -652,7 +654,7 @@ export function spawnClaude(params) {
|
|
|
652
654
|
const resultText = toolResultText(b['content']);
|
|
653
655
|
if (b['is_error'] === true && isPermissionTransportFailure(resultText)) {
|
|
654
656
|
const detail = resultText.replace(/\s+/g, ' ').trim().slice(0, 300);
|
|
655
|
-
process.stderr.write(
|
|
657
|
+
process.stderr.write(errLine(`[bridge] FATAL permission transport lost — ending the turn rather than answering blind: ${detail}`) + '\n');
|
|
656
658
|
active.delete(conversationId);
|
|
657
659
|
clearTimeout(inputReleaseTimer);
|
|
658
660
|
input.release();
|
|
@@ -742,7 +744,7 @@ export function spawnClaude(params) {
|
|
|
742
744
|
return;
|
|
743
745
|
const message = err?.message ?? String(err);
|
|
744
746
|
const stack = err?.stack;
|
|
745
|
-
process.stderr.write(
|
|
747
|
+
process.stderr.write(errLine(`[bridge] query() threw: ${stack || message}`) + '\n');
|
|
746
748
|
if (/40[13]\b|unauthor|invalid (api key|authentication)|please run \/login/i.test(message)) {
|
|
747
749
|
sawAuthFailure = true;
|
|
748
750
|
}
|
package/dist/index.js
CHANGED
|
@@ -280,7 +280,7 @@ async function handleMessage(conversationId, text, sessionId, history, auth, vau
|
|
|
280
280
|
if (!isTokenValid(auth.token)) {
|
|
281
281
|
const message = 'Authentication expired and refresh failed — please restart the bridge to sign in again.';
|
|
282
282
|
stopTurnTimer();
|
|
283
|
-
console.error(paint(SECTION_COLORS.error, `[bridge] ${message} (${err.message})`));
|
|
283
|
+
console.error(paint(SECTION_COLORS.error, `[bridge] ${message} (${err.message}) · session ${sessionId ?? conversationId}`));
|
|
284
284
|
if (currentWs?.readyState === WebSocket.OPEN) {
|
|
285
285
|
currentWs.send(JSON.stringify({ type: 'error', conversationId, message }));
|
|
286
286
|
}
|
|
@@ -294,7 +294,7 @@ async function handleMessage(conversationId, text, sessionId, history, auth, vau
|
|
|
294
294
|
catch (err) {
|
|
295
295
|
const message = `System prompt refresh failed: ${err.message}`;
|
|
296
296
|
stopTurnTimer();
|
|
297
|
-
console.error(paint(SECTION_COLORS.error, `[${new Date().toLocaleTimeString()}] ✗ ${message}`));
|
|
297
|
+
console.error(paint(SECTION_COLORS.error, `[${new Date().toLocaleTimeString()}] ✗ ${message} · session ${sessionId ?? conversationId}`));
|
|
298
298
|
if (currentWs?.readyState === WebSocket.OPEN) {
|
|
299
299
|
currentWs.send(JSON.stringify({ type: 'error', conversationId, message }));
|
|
300
300
|
}
|
|
@@ -352,6 +352,7 @@ async function handleMessage(conversationId, text, sessionId, history, auth, vau
|
|
|
352
352
|
spawnClaude({
|
|
353
353
|
conversationId,
|
|
354
354
|
presenceSessionId: claudePinnedSessionId,
|
|
355
|
+
chatSessionId: turnSessionId,
|
|
355
356
|
text,
|
|
356
357
|
uid: activeAuth.uid,
|
|
357
358
|
history,
|
|
@@ -414,7 +415,7 @@ async function handleMessage(conversationId, text, sessionId, history, auth, vau
|
|
|
414
415
|
},
|
|
415
416
|
onError: (message, usage, model) => {
|
|
416
417
|
const elapsed = stopTurnTimer();
|
|
417
|
-
console.error(paint(SECTION_COLORS.error, `[${new Date().toLocaleTimeString()}] ✗ ${message} (${formatElapsed(elapsed)})`));
|
|
418
|
+
console.error(paint(SECTION_COLORS.error, `[${new Date().toLocaleTimeString()}] ✗ ${message} (${formatElapsed(elapsed)}) · session ${turnSessionId}`));
|
|
418
419
|
const mapped = toBridgeUsage(usage);
|
|
419
420
|
if (currentWs?.readyState === WebSocket.OPEN) {
|
|
420
421
|
currentWs.send(JSON.stringify({
|
|
@@ -555,7 +556,7 @@ function connect(auth, retryDelay = 1000) {
|
|
|
555
556
|
startTurnTimer();
|
|
556
557
|
handleMessage(conversationId, text, sessionId ?? null, hist, auth, vaultFileOpen, clientCapabilities, syncedFolders, agentSlug, model).catch((err) => {
|
|
557
558
|
stopTurnTimer();
|
|
558
|
-
console.error(paint(SECTION_COLORS.error, `[bridge] handleMessage error: ${err.message}`));
|
|
559
|
+
console.error(paint(SECTION_COLORS.error, `[bridge] handleMessage error: ${err.message} · session ${sessionId ?? conversationId}`));
|
|
559
560
|
});
|
|
560
561
|
});
|
|
561
562
|
ws.on('close', (code) => {
|