instar 1.3.1611 → 1.3.1613

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.
Files changed (159) hide show
  1. package/dashboard/console/console.css +3 -1
  2. package/dashboard/console/console.js +18 -5
  3. package/dashboard/console/home-model.js +4 -1
  4. package/dashboard/console/messages-model.js +2 -1
  5. package/dashboard/console/messages.js +1 -1
  6. package/dashboard/console/pace-model.js +5 -0
  7. package/dashboard/console/pace.js +3 -1
  8. package/dashboard/console/plans-model.js +17 -1
  9. package/dashboard/console/promises.js +2 -1
  10. package/dashboard/console/secrets-model.js +11 -1
  11. package/dist/commands/server.d.ts.map +1 -1
  12. package/dist/commands/server.js +32 -8
  13. package/dist/commands/server.js.map +1 -1
  14. package/dist/core/AppConversationStore.d.ts +2 -0
  15. package/dist/core/AppConversationStore.d.ts.map +1 -1
  16. package/dist/core/AppConversationStore.js +8 -1
  17. package/dist/core/AppConversationStore.js.map +1 -1
  18. package/dist/core/AppRecordSignatures.d.ts +23 -2
  19. package/dist/core/AppRecordSignatures.d.ts.map +1 -1
  20. package/dist/core/AppRecordSignatures.js +32 -5
  21. package/dist/core/AppRecordSignatures.js.map +1 -1
  22. package/dist/core/LocalAttentionItems.d.ts +49 -0
  23. package/dist/core/LocalAttentionItems.d.ts.map +1 -0
  24. package/dist/core/LocalAttentionItems.js +107 -0
  25. package/dist/core/LocalAttentionItems.js.map +1 -0
  26. package/dist/core/MacDesktopHost.d.ts +3 -0
  27. package/dist/core/MacDesktopHost.d.ts.map +1 -1
  28. package/dist/core/MacDesktopHost.js +10 -0
  29. package/dist/core/MacDesktopHost.js.map +1 -1
  30. package/dist/core/MachineLockStateReader.d.ts.map +1 -1
  31. package/dist/core/MachineLockStateReader.js +6 -1
  32. package/dist/core/MachineLockStateReader.js.map +1 -1
  33. package/dist/core/PostUpdateMigrator.d.ts +6 -0
  34. package/dist/core/PostUpdateMigrator.d.ts.map +1 -1
  35. package/dist/core/PostUpdateMigrator.js +59 -2
  36. package/dist/core/PostUpdateMigrator.js.map +1 -1
  37. package/dist/core/types.d.ts +12 -0
  38. package/dist/core/types.d.ts.map +1 -1
  39. package/dist/core/types.js.map +1 -1
  40. package/dist/data/standards-guard-index.json +1 -1
  41. package/dist/data/standards-guard-index.meta.json +2 -2
  42. package/dist/data/standards-registry.meta.json +1 -1
  43. package/dist/lifeline/TelegramLifeline.d.ts +2 -0
  44. package/dist/lifeline/TelegramLifeline.d.ts.map +1 -1
  45. package/dist/lifeline/TelegramLifeline.js +28 -0
  46. package/dist/lifeline/TelegramLifeline.js.map +1 -1
  47. package/dist/localVerify/localVerifyWiring.d.ts +11 -0
  48. package/dist/localVerify/localVerifyWiring.d.ts.map +1 -1
  49. package/dist/localVerify/localVerifyWiring.js +9 -0
  50. package/dist/localVerify/localVerifyWiring.js.map +1 -1
  51. package/dist/messaging/TelegramAdapter.d.ts +8 -0
  52. package/dist/messaging/TelegramAdapter.d.ts.map +1 -1
  53. package/dist/messaging/TelegramAdapter.js +46 -31
  54. package/dist/messaging/TelegramAdapter.js.map +1 -1
  55. package/dist/messaging/shared/MessageLogger.d.ts +2 -0
  56. package/dist/messaging/shared/MessageLogger.d.ts.map +1 -1
  57. package/dist/messaging/shared/MessageLogger.js.map +1 -1
  58. package/dist/messaging/slack/SlackAdapter.d.ts +19 -0
  59. package/dist/messaging/slack/SlackAdapter.d.ts.map +1 -1
  60. package/dist/messaging/slack/SlackAdapter.js +21 -0
  61. package/dist/messaging/slack/SlackAdapter.js.map +1 -1
  62. package/dist/messaging/telegram-origin/OriginForwardToHolder.d.ts +13 -0
  63. package/dist/messaging/telegram-origin/OriginForwardToHolder.d.ts.map +1 -1
  64. package/dist/messaging/telegram-origin/OriginForwardToHolder.js +16 -0
  65. package/dist/messaging/telegram-origin/OriginForwardToHolder.js.map +1 -1
  66. package/dist/messaging/telegram-origin/OriginLegacy.d.ts +8 -0
  67. package/dist/messaging/telegram-origin/OriginLegacy.d.ts.map +1 -1
  68. package/dist/messaging/telegram-origin/OriginLegacy.js +34 -6
  69. package/dist/messaging/telegram-origin/OriginLegacy.js.map +1 -1
  70. package/dist/messaging/telegram-origin/TelegramOriginBoot.d.ts +3 -0
  71. package/dist/messaging/telegram-origin/TelegramOriginBoot.d.ts.map +1 -1
  72. package/dist/messaging/telegram-origin/TelegramOriginBoot.js +54 -10
  73. package/dist/messaging/telegram-origin/TelegramOriginBoot.js.map +1 -1
  74. package/dist/messaging/telegram-origin/types.d.ts +11 -0
  75. package/dist/messaging/telegram-origin/types.d.ts.map +1 -1
  76. package/dist/messaging/telegram-origin/types.js +15 -0
  77. package/dist/messaging/telegram-origin/types.js.map +1 -1
  78. package/dist/monitoring/GreenPrAutoMerger.d.ts.map +1 -1
  79. package/dist/monitoring/GreenPrAutoMerger.js +13 -0
  80. package/dist/monitoring/GreenPrAutoMerger.js.map +1 -1
  81. package/dist/monitoring/greenPrAutomergeWiring.d.ts.map +1 -1
  82. package/dist/monitoring/greenPrAutomergeWiring.js +3 -0
  83. package/dist/monitoring/greenPrAutomergeWiring.js.map +1 -1
  84. package/dist/monitoring/promptRelaySettle.d.ts +35 -0
  85. package/dist/monitoring/promptRelaySettle.d.ts.map +1 -0
  86. package/dist/monitoring/promptRelaySettle.js +58 -0
  87. package/dist/monitoring/promptRelaySettle.js.map +1 -0
  88. package/dist/native/instar-desktop-host +0 -0
  89. package/dist/scaffold/templates.d.ts.map +1 -1
  90. package/dist/scaffold/templates.js +3 -1
  91. package/dist/scaffold/templates.js.map +1 -1
  92. package/dist/server/AgentServer.d.ts +15 -0
  93. package/dist/server/AgentServer.d.ts.map +1 -1
  94. package/dist/server/AgentServer.js +78 -20
  95. package/dist/server/AgentServer.js.map +1 -1
  96. package/dist/server/CapabilityIndex.js +2 -2
  97. package/dist/server/CapabilityIndex.js.map +1 -1
  98. package/dist/server/mobileConversationRoutes.d.ts +16 -3
  99. package/dist/server/mobileConversationRoutes.d.ts.map +1 -1
  100. package/dist/server/mobileConversationRoutes.js +36 -8
  101. package/dist/server/mobileConversationRoutes.js.map +1 -1
  102. package/dist/server/mobilePairingRoutes.d.ts +1 -1
  103. package/dist/server/mobilePairingRoutes.d.ts.map +1 -1
  104. package/dist/server/mobilePairingRoutes.js +5 -2
  105. package/dist/server/mobilePairingRoutes.js.map +1 -1
  106. package/dist/server/mobileSlackRoutes.d.ts +162 -0
  107. package/dist/server/mobileSlackRoutes.d.ts.map +1 -0
  108. package/dist/server/mobileSlackRoutes.js +552 -0
  109. package/dist/server/mobileSlackRoutes.js.map +1 -0
  110. package/dist/server/routes.d.ts +2 -0
  111. package/dist/server/routes.d.ts.map +1 -1
  112. package/dist/server/routes.js +85 -6
  113. package/dist/server/routes.js.map +1 -1
  114. package/package.json +1 -1
  115. package/scripts/build-locked-proof.mjs +125 -0
  116. package/scripts/lib/locked-proof-build.mjs +71 -0
  117. package/scripts/locked-proof/configure-proof-agent.mjs +68 -0
  118. package/scripts/locked-proof/create-proof-user.sh +89 -0
  119. package/scripts/locked-proof/driver.mjs +457 -0
  120. package/scripts/locked-proof/lib.mjs +267 -0
  121. package/scripts/locked-proof/pty-feed.py +59 -0
  122. package/scripts/locked-proof/remove-proof-user.sh +18 -0
  123. package/scripts/locked-proof/reset-attempts.py +52 -0
  124. package/scripts/locked-proof/stage-proof-agents.sh +68 -0
  125. package/src/data/builtin-manifest.json +65 -65
  126. package/src/data/standards-guard-index.json +1 -1
  127. package/src/data/standards-guard-index.meta.json +2 -2
  128. package/src/data/standards-registry.meta.json +1 -1
  129. package/src/scaffold/templates.ts +3 -1
  130. package/upgrades/1.3.1612.md +72 -0
  131. package/upgrades/1.3.1613.md +108 -0
  132. package/upgrades/side-effects/blocker-text-is-the-message.eli16.md +5 -0
  133. package/upgrades/side-effects/blocker-text-is-the-message.md +38 -0
  134. package/upgrades/side-effects/console-needs-row-tidy.eli16.md +13 -0
  135. package/upgrades/side-effects/console-needs-row-tidy.md +24 -0
  136. package/upgrades/side-effects/console-partial-survives-reload.eli16.md +5 -0
  137. package/upgrades/side-effects/console-partial-survives-reload.md +34 -0
  138. package/upgrades/side-effects/console-secret-drop-names.eli16.md +5 -0
  139. package/upgrades/side-effects/console-secret-drop-names.md +34 -0
  140. package/upgrades/side-effects/desktop-tests-stop-touching-tcc.eli16.md +13 -0
  141. package/upgrades/side-effects/desktop-tests-stop-touching-tcc.md +65 -0
  142. package/upgrades/side-effects/green-pr-eligible-needs-passing-record.eli16.md +7 -0
  143. package/upgrades/side-effects/green-pr-eligible-needs-passing-record.md +39 -0
  144. package/upgrades/side-effects/green-pr-poke-unknown-mergeable.eli16.md +5 -0
  145. package/upgrades/side-effects/green-pr-poke-unknown-mergeable.md +41 -0
  146. package/upgrades/side-effects/held-expiry-one-row-per-topic.eli16.md +5 -0
  147. package/upgrades/side-effects/held-expiry-one-row-per-topic.md +37 -0
  148. package/upgrades/side-effects/locked-proof-driver.md +72 -0
  149. package/upgrades/side-effects/locked-proof-test-build.md +64 -0
  150. package/upgrades/side-effects/locked-security-item-no-telegram.md +78 -0
  151. package/upgrades/side-effects/mobile-native-conversations-inc4.md +115 -0
  152. package/upgrades/side-effects/origin-config-unknown-not-missing.eli16.md +16 -0
  153. package/upgrades/side-effects/origin-config-unknown-not-missing.md +38 -0
  154. package/upgrades/side-effects/pool-rows-use-local-machine-name.eli16.md +5 -0
  155. package/upgrades/side-effects/pool-rows-use-local-machine-name.md +34 -0
  156. package/upgrades/side-effects/prompt-gate-settle-before-relay.eli16.md +11 -0
  157. package/upgrades/side-effects/prompt-gate-settle-before-relay.md +57 -0
  158. package/upgrades/side-effects/topic-names-through-lifeline.eli16.md +9 -0
  159. package/upgrades/side-effects/topic-names-through-lifeline.md +39 -0
@@ -1161,8 +1161,10 @@ a.machine-line-link:hover { border-color: var(--accent); color: var(--text); }
1161
1161
  /* Queue pace card (docs/specs/queue-pace.md) */
1162
1162
  .pace-card { grid-column: 1 / -1; margin-top: var(--s-4, 16px); }
1163
1163
  .pace-lines { list-style: none; margin: var(--s-2, 8px) 0 0; padding: 0; display: grid; gap: 8px; }
1164
- .pace-line { display: flex; align-items: baseline; gap: 8px; flex-wrap: wrap; font-size: 14px; color: var(--text); }
1164
+ .pace-line { display: grid; grid-template-columns: auto 1fr; align-items: baseline; column-gap: 8px; font-size: 14px; color: var(--text); }
1165
1165
  .pace-line .dot { position: relative; top: -1px; }
1166
+ .pace-line .pace-text { min-width: 0; }
1167
+ .pace-line .pace-prs { grid-column: 2; }
1166
1168
  .pace-line[data-tone="muted"] .pace-text { color: var(--text-muted); }
1167
1169
  .pace-prs { display: inline-flex; gap: 6px; flex-wrap: wrap; font-size: 13px; }
1168
1170
  .mb-pace { margin-top: 4px; }
@@ -393,6 +393,8 @@ function paintCard(def, model, repaint = false) {
393
393
  foot.append(b);
394
394
  } else foot.append(el('span', { class: 'card-age', text: extra > 0 ? `and ${extra} more` : '' }));
395
395
  if (def.href) foot.append(el('a', { href: def.href, text: 'Open', 'aria-label': `Open ${def.title} in the dashboard` }));
396
+ // An empty footer would leave a blank band (and its divider) under the rows.
397
+ foot.hidden = !foot.textContent.trim() && !foot.querySelector('a, button');
396
398
  return model;
397
399
  }
398
400
 
@@ -438,13 +440,25 @@ function paintHeadline(models) {
438
440
  // should not turn Home into "part could not be checked". While it is retried,
439
441
  // its rows from the last complete answer stand in, for up to two minutes; the
440
442
  // machines that did answer always show their fresh rows.
443
+ // Kept in session storage too, so reopening the app or reloading the page while a
444
+ // machine is slow still has it (page memory alone is lost on reload). Storage can be
445
+ // absent or full; then it is page memory only, as before.
441
446
  const lastComplete = {};
442
447
  const ROW_LISTS = { attention: 'items', sessions: 'sessions' };
448
+ const LAST_COMPLETE_STORE = 'console.lastComplete.';
443
449
  function rememberComplete(key, result) {
444
- if (ROW_LISTS[key]) lastComplete[key] = { result, at: Date.now() };
450
+ if (!ROW_LISTS[key]) return;
451
+ lastComplete[key] = { result, at: Date.now() };
452
+ try { sessionStorage.setItem(LAST_COMPLETE_STORE + key, JSON.stringify(lastComplete[key])); } catch { /* @silent-fallback-ok: storage unavailable or full; page memory only, as before */ }
453
+ }
454
+ function storedComplete(key) {
455
+ try {
456
+ const v = JSON.parse(sessionStorage.getItem(LAST_COMPLETE_STORE + key) || 'null');
457
+ return v && typeof v.at === 'number' && v.result ? v : null;
458
+ } catch { return null; } // @silent-fallback-ok: unreadable storage means no stored answer
445
459
  }
446
460
  function fillFromLastComplete(key, fresh) {
447
- const prev = lastComplete[key];
461
+ const prev = lastComplete[key] || (lastComplete[key] = storedComplete(key) || undefined);
448
462
  return ROW_LISTS[key] && prev ? fillPartial(fresh, prev.result, ROW_LISTS[key], Date.now(), prev.at) : null;
449
463
  }
450
464
 
@@ -565,7 +579,6 @@ function renderGroup(main, g) {
565
579
  el('section', { class: 'group-head' },
566
580
  el('div', { class: 'eyebrow', text: g.label }),
567
581
  el('h1', { text: g.question }),
568
- el('p', { text: 'Each of these opens in the dashboard, where everything works exactly as before.' }),
569
582
  ),
570
583
  el('div', { class: 'tiles' }, g.tabs.map((t) => tile(t))),
571
584
  ...groupExtras(g, { get }), // the Development tile (Work, maintainer mode only) and the developer-tools switch (Settings)
@@ -585,8 +598,8 @@ function renderGroup(main, g) {
585
598
 
586
599
  function footNote() {
587
600
  return el('p', { class: 'foot-note' },
588
- document.createTextNode('This is the new Instar console. Everything is still in the '),
589
- el('a', { href: '/dashboard', text: 'legacy dashboard' }),
601
+ document.createTextNode('The older dashboard is still available: '),
602
+ el('a', { href: '/dashboard', text: 'open the legacy dashboard' }),
590
603
  document.createTextNode('.'),
591
604
  );
592
605
  }
@@ -166,7 +166,10 @@ export function buildNeeds(res, now = Date.now(), names = {}) {
166
166
  return {
167
167
  key: groupKey(top), stale, last: g.last, prio: PRIORITY[top.priority] ?? 9,
168
168
  main: top.title || top.summary || 'Untitled item',
169
- sub: [g.items.length > 1 ? `${g.items.length} copies` : null, [...g.machines].join(', ') || null, String(top.priority || '').toLowerCase()].filter(Boolean).join(' · '),
169
+ // The machine only when the title does not already start with it; the
170
+ // priority word is the queue's bookkeeping, not something to act on.
171
+ sub: [g.items.length > 1 ? `${g.items.length} copies` : null,
172
+ [...g.machines].filter((m) => !String(top.title || top.summary || '').startsWith(`${m}:`)).join(', ') || null].filter(Boolean).join(' · '),
170
173
  end: (ago(g.last, now) || '').replace(' ago', '') ? `${ago(g.last, now)}` : '',
171
174
  tone: stale ? 'unknown' : (top.priority === 'URGENT' ? 'bad' : 'attn'),
172
175
  detail: top.description || top.body || '',
@@ -82,7 +82,8 @@ export function buildMessagesPage(statusRes, healthRes, now = Date.now(), topicN
82
82
  const automatic = held.filter(h => h.producerKind === 'server-automation').length;
83
83
  headline = heldHeadline(held.length, replies, automatic, held.length - replies - automatic);
84
84
  } else if (expired) headline = `${expired} ${expired === 1 ? 'message' : 'messages'} expired before delivery.`;
85
- else headline = 'No messages are held.';
85
+ // Held replies are a fault, never a feature to report on: with none, the page is just Messages.
86
+ else headline = 'Messages to you';
86
87
  const sub = [
87
88
  held.length ? 'I need to restore delivery. This is not a task for you.' : null,
88
89
  individual.length && individual[individual.length - 1].sinceTs ? `The oldest has waited ${ago(individual[individual.length - 1].sinceTs, now).replace(' ago', '')}.` : null,
@@ -43,7 +43,7 @@ export async function renderMessages(main, ctx) {
43
43
  el('span', { class: 'need-sub', text: 'Who wrote each message is private to you. One unlock lasts about 15 minutes in this page.' }),
44
44
  el('button', { class: 'btn-primary btn-inline', type: 'button', text: 'Unlock', onclick: async () => { const a = await askPin({ title: 'Message records', explain: 'Unlock message records. Your PIN is not kept; the unlock lives in this page until it expires.', adapter: 'session' }); if (a) refresh(); } })) : null;
45
45
  setKids(main, el('div', { class: 'msg-page' },
46
- pageHead({ eyebrow: 'People · Messages to you', headline: hf ? heldHeadline(hf.count, hf.sessionReplies, hf.automaticMessages, hf.otherMessages) : 'Messages to you', sub: hf ? 'I’m handling delivery. Unlock to see the individual records.' : '', tone: hf && hf.count ? 'attn' : 'muted' }),
46
+ pageHead({ eyebrow: 'People · Messages to you', headline: hf && hf.count ? heldHeadline(hf.count, hf.sessionReplies, hf.automaticMessages, hf.otherMessages) : 'Messages to you', sub: hf && hf.count ? 'I’m handling delivery. Unlock to see the individual records.' : '', tone: hf && hf.count ? 'attn' : 'muted' }),
47
47
  unlock || cantTell(page.reason), legacyLink()));
48
48
  return;
49
49
  }
@@ -60,6 +60,11 @@ export function paceLine(q, showMachine = false) {
60
60
  if (person && q.verdict === 'falling-behind') verdict = 'waiting on you';
61
61
  if (q.verdict === 'catching-up' && typeof q.daysToClear === 'number' && !person) verdict += `, about ${fmtRate(q.daysToClear)} days to clear`;
62
62
  const inR = fmtRate(q.inflowPerDay), outR = fmtRate(q.outflowPerDay);
63
+ // Nothing in, nothing done, but items still open: that is a stalled pile, not "steady".
64
+ const open = Number(q.open);
65
+ if (!Number(q.inflowPerDay) && !Number(q.outflowPerDay) && open > 0) {
66
+ return `${label}${where}: nothing came in or got done this week; ${open} still open`;
67
+ }
63
68
  const rates = inR !== null && outR !== null ? `${inR} a day in, ${outR} done — ` : '';
64
69
  let line = `${label}${where}: ${rates}${verdict}`;
65
70
  if (q.verdict === 'falling-behind') {
@@ -17,7 +17,9 @@ export function paceCard(get) {
17
17
  const machines = new Set(queues.map((q) => q.machine));
18
18
  const anyBehind = queues.some((q) => toneOf(q) === 'attn');
19
19
  host.dataset.state = anyBehind ? 'attn' : 'ok';
20
- const lines = queues.map((q) => {
20
+ // A queue with nothing coming in, nothing done and nothing open says nothing.
21
+ const idle = (q) => !Number(q.inflowPerDay) && !Number(q.outflowPerDay) && !Number(q.open);
22
+ const lines = queues.filter((q) => !idle(q)).map((q) => {
21
23
  const tone = toneOf(q);
22
24
  const li = el('li', { class: 'pace-line', 'data-tone': tone },
23
25
  el('span', { class: `dot ${DOT[tone] || ''}`.trim() }),
@@ -162,9 +162,25 @@ function recheckText(e, now) {
162
162
  return { text: `rechecking ${new Date(t).toLocaleDateString([], { weekday: 'short', month: 'short', day: 'numeric' })}`, overdue: false };
163
163
  }
164
164
 
165
+ // The deferral detector recorded whole reply commands (`cat <<'EOF' | <reply script> N`
166
+ // + the message + `EOF`), signed links included (2026-11-02). Show the message's first line,
167
+ // with credential-looking query values masked; a command with no message text is named, not
168
+ // printed.
169
+ const SECRET_QUERY = /([?&](?:sig|signature|token|key|auth|access_token)[^=&\s]*=)[^&\s]+/gi;
170
+ const SHELL_START = /^\s*(?:cd|cat|curl|echo|node|bash|sh|gh|git|python3?|npx)\b/;
171
+ export function blockerText(raw) {
172
+ const s = String(raw || '');
173
+ const doc = /<<-?\s*['"]?(\w+)['"]?[^\n]*\n([\s\S]*?)(?:\n[ \t]*\1[ \t]*(?:\n|$)|$)/.exec(s);
174
+ let body = doc ? doc[2] : s;
175
+ if (!doc && SHELL_START.test(body)) return 'Flagged in a command I ran (no message text)';
176
+ body = body.replace(SECRET_QUERY, '$1…');
177
+ const line = body.split('\n').map((l) => l.trim()).find(Boolean) || '';
178
+ return line.length > 220 ? `${line.slice(0, 219)}…` : line;
179
+ }
180
+
165
181
  /** A blocker as a row: { key, main, sub, end, tone, kind, record }. */
166
182
  export function blockerRow(e, now = Date.now()) {
167
- const main = e.detectedText || e.origin || 'A blocker';
183
+ const main = blockerText(e.detectedText) || e.origin || 'A blocker';
168
184
  let sub; let tone = null; let kind;
169
185
  if (e.state === 'true-blocker') { const r = recheckText(e, now); sub = `Truly stuck for now · ${r.text}`; tone = 'bad'; kind = 'stuck'; }
170
186
  else if (e.state === 'access-requested') { sub = 'Waiting on you for access'; tone = 'attn'; kind = 'needs-you'; }
@@ -56,7 +56,8 @@ export async function renderPromises(main, ctx) {
56
56
  }),
57
57
  page.coverage ? note(page.coverage) : null,
58
58
  el('div', { class: 'page-sections' },
59
- section({ id: 'waiting', title: 'Waiting on you', rows: s.waiting.map((r) => ({ ...r, tone: 'attn' })), empty: 'Nothing is waiting on you.', onRow: open }),
59
+ // When nothing waits on the operator the headline already says so; an empty card would repeat it.
60
+ s.waiting.length ? section({ id: 'waiting', title: 'Waiting on you', rows: s.waiting.map((r) => ({ ...r, tone: 'attn' })), empty: 'Nothing is waiting on you.', onRow: open }) : null,
60
61
  section({ id: 'carrying', title: 'I’m handling', rows: s.carrying, collapsed: true, onRow: open }),
61
62
  section({ id: 'handled', title: 'Older, still open', rows: s.handled.map((r) => ({ ...r, tone: 'unknown' })), collapsed: true, onRow: open }),
62
63
  section({ id: 'closed', title: 'Closed this week', rows: s.closed, collapsed: true, onRow: open }),
@@ -124,8 +124,18 @@ export function buildRequests(res, opts = {}) {
124
124
  * (names only); falls back to the secret-sync key list when that is switched off. Lengths
125
125
  * and values are never read into the model.
126
126
  */
127
+ // A saved Secret Drop is stored under `secretDrops.<64-hex token>` (often with
128
+ // "(+N nested)"): a token, not a name. Show them as one counted line instead.
129
+ const DROP_KEY = /^secretDrops\.[0-9a-f]{16,}\b/;
130
+ function groupDrops(names) {
131
+ const drops = names.filter((n) => DROP_KEY.test(n)).length;
132
+ if (!drops) return names;
133
+ const rest = names.filter((n) => !DROP_KEY.test(n));
134
+ return [...rest, drops === 1 ? 'Saved Secret Drop submission (1)' : `Saved Secret Drop submissions (${drops})`].sort((a, b) => a.localeCompare(b));
135
+ }
136
+
127
137
  export function buildKeys(ctxRes, syncRes) {
128
- const clean = (arr) => [...new Set(arr.filter((n) => typeof n === 'string' && n.trim()).map((n) => n.trim()))].sort((a, b) => a.localeCompare(b));
138
+ const clean = (arr) => groupDrops([...new Set(arr.filter((n) => typeof n === 'string' && n.trim()).map((n) => n.trim()))]).sort((a, b) => a.localeCompare(b));
129
139
  if (ctxRes && ctxRes.ok && ctxRes.data && Array.isArray(ctxRes.data.names)) {
130
140
  const vaultState = ctxRes.data.vaultState;
131
141
  if (vaultState === 'decrypt-failed') return { ok: false, decryptFailed: true, names: [], reason: 'Can’t open the saved keys on this machine.' };
@@ -1 +1 @@
1
- {"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../../src/commands/server.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../../src/commands/server.ts"],"names":[],"mappings":"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"}
@@ -962,6 +962,8 @@ let _slackAdapter = null;
962
962
  // block; null when Slack is not configured (the owner-side Slack branch then
963
963
  // no-ops — a forwarded Slack key on a Slack-less owner is a misconfiguration the
964
964
  // router's placement should never produce, and falling through is harmless).
965
+ // Returns what happened to the message (mobile-native-conversations §4.9: the app's Slack send
966
+ // records it); the live and forwarded Slack paths ignore the result.
965
967
  let _slackInboundDispatch = null;
966
968
  // SessionRefresh — agent-initiated respawn. Module-scope so onRestartSession
967
969
  // (defined outside startServer) can delegate to it once startServer wires it.
@@ -7357,6 +7359,20 @@ export async function startServer(options) {
7357
7359
  }
7358
7360
  // Relay to messaging platform if adapter is available and session has a binding
7359
7361
  if (classification.action === 'relay' || classification.action === 'auto-approve') {
7362
+ // Settle first: many prompts are answered without a person (account
7363
+ // swap, permission floor, respawn). Relay only one still on screen.
7364
+ const { settleBeforeRelay, DEFAULT_RELAY_SETTLE_MS } = await import('../monitoring/promptRelaySettle.js');
7365
+ const settle = await settleBeforeRelay(prompt, {
7366
+ settleMs: promptGateConfig.relaySettleMs ?? DEFAULT_RELAY_SETTLE_MS,
7367
+ sleep: (ms) => new Promise((r) => setTimeout(r, ms)),
7368
+ isAlive: (name) => sessionManager.isSessionAlive(name),
7369
+ capture: (name) => sessionManager.captureOutput(name, 60),
7370
+ });
7371
+ if (!settle.relay) {
7372
+ console.log(`[PromptGate] Not relaying ${prompt.type} prompt for ${prompt.sessionName}: ${settle.reason}`);
7373
+ detector.onInputSent(prompt.sessionName);
7374
+ return;
7375
+ }
7360
7376
  let relayed = false;
7361
7377
  // Try Telegram first
7362
7378
  if (telegram) {
@@ -9166,6 +9182,12 @@ export async function startServer(options) {
9166
9182
  else if (safeSenderName) {
9167
9183
  prefix = `[slack:${channelId} from ${safeSenderName}]`;
9168
9184
  }
9185
+ // Sent from the Instar app (mobile-native-conversations §4.9): the server appends the mark
9186
+ // after the sanitized name; "📱 signed" only when the phone's signature checked out.
9187
+ const appOrigin = message.metadata?.appOrigin;
9188
+ if (typeof appOrigin === 'string') {
9189
+ prefix = `${prefix.slice(0, -1)} (📱 ${appOrigin === 'verified' ? 'signed' : 'from the app'})]`;
9190
+ }
9169
9191
  // Build context for the session — inject inline like Telegram does
9170
9192
  // Use async fallback to fetch from Slack API if ring buffer is empty
9171
9193
  const tmpDir = '/tmp/instar-slack';
@@ -9297,8 +9319,9 @@ export async function startServer(options) {
9297
9319
  }
9298
9320
  catch (injectErr) {
9299
9321
  console.error(`[slack→session] Injection failed: ${injectErr instanceof Error ? injectErr.message : injectErr}`);
9322
+ return 'refused';
9300
9323
  }
9301
- return;
9324
+ return 'delivered';
9302
9325
  }
9303
9326
  }
9304
9327
  console.log(`[slack→session] Session "${existingSession}" died, respawning...`);
@@ -9328,7 +9351,7 @@ export async function startServer(options) {
9328
9351
  ? 'conversation identity unavailable'
9329
9352
  : (!relayReadiness.ready ? relayReadiness.reason : 'unknown readiness failure');
9330
9353
  console.error(`[slack→session] spawn refused: slack-relay-not-ready (${reason})`);
9331
- return;
9354
+ return 'refused';
9332
9355
  }
9333
9356
  // Slack DMs are isolated 1:1 bound sessions too. A shared lifeline
9334
9357
  // intentionally has no single INSTAR_CONVERSATION_ID, so routing DMs
@@ -9376,7 +9399,7 @@ export async function startServer(options) {
9376
9399
  custodyLive: custody,
9377
9400
  }).catch(() => { });
9378
9401
  }
9379
- return;
9402
+ return custody ? 'queued' : 'refused';
9380
9403
  }
9381
9404
  }
9382
9405
  }
@@ -9403,10 +9426,13 @@ export async function startServer(options) {
9403
9426
  if (contextWallForcesFresh && conversationId !== null) {
9404
9427
  _clearContextExhaustionFreshRequired?.(conversationId);
9405
9428
  }
9429
+ return 'delivered';
9406
9430
  }
9431
+ return 'refused';
9407
9432
  }
9408
9433
  catch (err) {
9409
9434
  console.error(`[slack] Session spawn failed: ${err instanceof Error ? err.message : err}`);
9435
+ return 'refused';
9410
9436
  }
9411
9437
  };
9412
9438
  // Expose to the owner-side mesh bridge (a forwarded Slack message replays
@@ -22302,7 +22328,7 @@ export async function startServer(options) {
22302
22328
  greenPrAutoMerger?.attachLocalVerify({
22303
22329
  effectiveFloor: () => (rec ? rec.effectiveFloor() : null),
22304
22330
  mainHealth: () => svc.mainHealth().state,
22305
- hasRecord: (pr, head, base) => !!svc.getRecord(pr, head, base),
22331
+ hasRecord: (pr, head, base) => wiring.hasPassingRecord(svc, pr, head, base),
22306
22332
  requestVerify: (pr) => svc.request(pr, { explicit: false }),
22307
22333
  // Dry-run posting also suppresses the watcher's actions→local disarm write.
22308
22334
  postStatuses: () => liveConfig.get('monitoring.localVerify.postStatuses', false) === true,
@@ -28116,9 +28142,7 @@ export async function startServer(options) {
28116
28142
  heldAudit({ phase: 'expired', topicId: row.destination.topicId, operationId: row.operationId, lastAttempt: row.holdDetail?.lastAttempt ?? null });
28117
28143
  if (Number.isSafeInteger(topicId))
28118
28144
  heldCollapser.clear(topicId);
28119
- await telegram.createAttentionItem({ id: originForwardMod.heldExpiryItemId(row), category: 'telegram-origin', priority: 'HIGH',
28120
- title: `Held reply to topic ${row.destination.topicId ?? '?'} expired`, summary: originForwardMod.expiredForwardWording(row),
28121
- sourceContext: 'telegram-origin-forward-to-holder' }, { hubOnly: true });
28145
+ await telegram.createAttentionItem(originForwardMod.heldExpiryItem(row), { hubOnly: true });
28122
28146
  };
28123
28147
  }
28124
28148
  telegram.outboundRelay = async (topicId, text, opts) => {
@@ -29456,7 +29480,7 @@ export async function startServer(options) {
29456
29480
  const server = new AgentServer({ config, ecosystemLedger: _ecosystemLedger ?? undefined, singleInstanceLock, agentIdentity: _agentIdentityDeps, terminateSessionAuthority: terminateWithAuthority, subscriptionEmailBinding: credentialLocationLedger, subscriptionEmailBarrier, subscriptionIdentityOracle, sessionManager, llmQueue: sharedLlmQueue, state, scheduler, telegram, telegramOrigin: telegramOriginBoot?.runtime, relationships, feedback, feedbackAnomalyDetector, dispatches, updateChecker, autoUpdater, autoDispatcher, quotaTracker, quotaManager, publisher, viewer, jobAnomalySendAutomationReply: sendAutomationReply, tunnel, evolution, watchdog, topicMemory, triageNurse, projectMapper, cartographerRoots: cartographerRoots ?? undefined, coherenceGate: scopeVerifier, contextHierarchy, canonicalState, operationGate, sentinel, adaptiveTrust, memoryMonitor, orphanReaper, coherenceMonitor, commitmentTracker, subscriptionPool, accountFollowMePeerViews: async () => { const nickById = new Map((_listPoolMachines?.() ?? []).map((m) => [m.machineId, verifiedEntityName(m.machineId, m.nickname) ?? ''])); let peers = (_resolvePeerUrls?.() ?? []).map((p) => ({ machineId: p.machineId, nickname: nickById.get(p.machineId) ?? '', url: p.url })); if (peers.length === 0) {
29457
29481
  peers = (_listPoolMachines?.() ?? []).filter((m) => m.machineId !== _meshSelfId && !!m.lastKnownUrl).map((m) => ({ machineId: m.machineId, nickname: verifiedEntityName(m.machineId, m.nickname) ?? '', url: m.lastKnownUrl }));
29458
29482
  } if (peers.length === 0)
29459
- return []; const { fetchPeerSubscriptionViews } = await import('../core/fetchPeerSubscriptionViews.js'); return fetchPeerSubscriptionViews({ peers: () => peers, fetchImpl: fetch, authToken: config.authToken ?? '' }); }, quotaPoller, quotaAwareScheduler: _quotaAwareScheduler ?? undefined, proactiveSwapMonitor: _proactiveSwapMonitor ?? undefined, inUseAccountResolver, enrollmentWizard, accountFollowMeRevocation, credentialRepointing, semanticMemory, activitySentinel, rateLimitSentinel, releaseReadinessSentinel: releaseReadinessSentinel ?? undefined, greenPrAutoMerger: greenPrAutoMerger ?? undefined, localVerify: localVerifyService ?? undefined, localVerifyStatus: localVerifyStatus ?? undefined, guardLatchStore: guardLatchStore ?? undefined, messageRouter, summarySentinel, spawnManager, systemReviewer, capabilityMapper, selfKnowledgeTree, coverageAuditor, topicResumeMap: _topicResumeMap ?? undefined, topicProfile: _topicProfileCtx ?? undefined, sessionRefresh: _sessionRefresh ?? undefined, autonomyManager, trustElevationTracker, autonomousEvolution, coordinator: coordinator.enabled ? coordinator : undefined, meshBindActive: coordinator.managers.identityManager.hasIdentity() && config.multiMachine?.meshTransport?.enabled !== false, localSigningKeyPem, leaseTransport, peerEndpointRecorder, getSelfMeshEndpoints, onLeasePullRequest: () => leaseCoordinatorRef?.currentLease() ?? null, liveTailReceiver, handoffWireTransport, onHandoffBegin, onHandoffInitiate: handoffInitiate, handoffInProgress: handoffSentinelInProgress, messageLedger, currentInboundByTopic, replyMarkerTransport, onReplyMarker: messageLedger ? (marker) => { const m = marker; messageLedger.applyRemoteReplyMarker(m.dedupeKey, { platform: m.platform, replyIdempotencyKey: m.replyIdempotencyKey, epoch: m.epoch, topic: m.topic ?? null }); } : undefined, whatsapp: whatsappAdapter, slack: slackAdapter, imessage: imessageAdapter, conversationRegistry, conversationBindAuth, appConversations: _appConversationService ?? undefined, conversationFollowThrough, whatsappBusinessBackend, messageBridge, hookEventReceiver, worktreeMonitor, subagentTracker, instructionsVerifier, handshakeManager: threadlineHandshake, threadlineRouter, conversationStore, threadLog, threadMessageRecorder, warrantsReplyGate, collaborationSurfacer, peerHomebaseRelay, threadResumeMap, topicLinkageHandler: topicLinkageHandler ?? undefined, threadlineRelayClient, pairingInvites: threadlinePairingInvites, getLastRelayEvent: threadlineGetLastRelayEvent, a2aRelayForward: _a2aRelayForwardCtx ?? undefined, threadlineReplyWaiters, threadlineMcpHttp, listenerManager: listenerManager ?? undefined, a2aDeliveryTracker: a2aDeliveryTracker ?? undefined, relayVerdictCounters: threadlineRelayClient ? (() => ({ ...threadlineRelayClient.relayVerdictCounters, expiredMismatchIgnored: a2aDeliveryTracker?.expiredMismatchIgnored ?? 0 })) : undefined, inboundIdLedger: _inboundIdLedger ?? undefined, inboundIdLedgerDaemonDeferred: () => _inboundIdLedgerDaemonDeferred, responseReviewGate, reviewCanaryBattery, messagingToneGate, outboundDedupGate, telemetryHeartbeat, pasteManager, featureRegistry, discoveryEvaluator, completionEvaluator, unifiedTrust, liveConfig, sharedStateLedger, ledgerSessionRegistry, worktreeManager, oidcEnrolledRepos: parallelDevConfig?.oidcEnrolledRepos, initiativeTracker, projectRoundRunner, projectDriftChecker, machineHeartbeat, machinePoolRegistry, ropeHealthMonitor, writeAdmission: writeAdmission ?? undefined, getInboundQueue: () => _inboundQueue, getMachineCoherence: () => _machineCoherenceSentinel, getSingleMachineFailoverGap: () => _singleMachineFailoverGap, getMissingLoginSession: () => _missingLoginSession, getSessionPoolFailoverRunner: () => _sessionPoolFailoverRunnerDriver?.status() ?? null, sessionPoolPromotionActivation: _sessionPoolPromotionActivation, meshRpcDispatcher, deliverA2aToMachine: _deliverA2aToMachine ?? undefined, workingSetPullCoordinator, workingSetArtifactManager, orchestratorPoller, commitmentReplicaStore, preferenceReplicaStore, replicatedRecordEmitter, replicatedStoreReconciler, conflictStore, rollbackUnmerge, droppedOriginRegistry, preferencesUnionReader, jevMemoryPicker, forwardCommitmentMutate, sessionOwnershipRegistry, sendDrain: _sendDrain ?? undefined, topicPinStore: _topicPinStore ?? undefined, topicPinSkewQuarantine: _topicPinSkewQuarantine ?? undefined, topicPinFoldView: _topicPinFoldView ?? undefined, ownershipReconciler: _ownershipReconciler ?? undefined, staleOwnerEngine: _staleOwnerEngine ?? undefined, duplicateReconciler: _duplicateReconciler ?? undefined, ownerDarkLadder: _ownerDarkLadder ?? undefined, spawnAdmission: _spawnAdmission ?? undefined, judgmentProvenance: _judgmentProvenance ?? undefined, leaseHandback: _leaseHandbackCtx ?? undefined, streamTicketStore: _streamTicketStore ?? undefined, poolStreamAllowRemoteInput: config.dashboard?.poolStream?.allowRemoteInput ?? false, poolStreamConnector: _poolStreamConnector ?? undefined, secretSync: _secretSyncHandle ?? undefined, meshSelfId: _meshSelfId ?? undefined, resolveRouterUrl: _resolveRouterUrl ?? undefined, resolvePeerUrls: _resolvePeerUrls ?? undefined, recordRopeResult: _recordRopeResult ?? undefined, guardRegistry, listPoolMachines: _listPoolMachines ?? undefined, deliverMandateToMachine: _deliverMandateToMachine ?? undefined, passkeyRevokeOutbox: _passkeyRevokeOutbox ? () => _passkeyRevokeOutbox : undefined, passkeyPeerOnline: _passkeyPeerOnline, passkeyPoolReader: _passkeyPoolReader ? () => _passkeyPoolReader : undefined, passkeyProofBrowser: async (profileDir) => { const { ChromeCdpReloginBrowser } = await import('../core/ChromeCdpReloginBrowser.js'); return new ChromeCdpReloginBrowser({ userDataDir: profileDir, passkeyMode: true, headless: true, launchTimeoutMs: 30_000, operationTimeoutMs: 20_000 }); }, poolLink: _poolLink ?? undefined, poolPollCache: _poolPollCache ?? undefined, sessionPoolE2EResultStore, proxyCoordinator, topicIntentStore, topicIntentArcCheck, usherSignalStore, intelligence: sharedIntelligence ?? undefined, telegramBridgeConfig, telegramBridge: telegramBridge ?? undefined, threadlineObservability, briefDeps, workingMemory, taskFlowRegistry, threadlineFlowBridge, sessionReaper, agentWorktreeReaper, externalHogSentinel, orphanedWorkSentinel, mcpProcessReaper, codexArmSessionSweeper, geminiLoopRunner, sleepController, agentActivityState, reapLog, resumeQueue, resumeDrainer, autonomousLivenessReconciler, enforcedTerminationStatus: () => enforcedTerminationWatchdog?.guardStatus() ?? null, prHandLease: prHandLease ?? undefined, standDownRegistry: _standDownRegistry ?? undefined, standDownAudit: _standDownAudit ?? undefined, operatorStopRecorder: recordOperatorStop, sleepWakeDetector, unjustifiedStopGate, stopGateDb, stopNotifier, liveTestGate, liveTestGateMode, liveTestRunnerCtx }); // Resolve the late-bound topic-operator getter (increment 2e): routing was
29483
+ return []; const { fetchPeerSubscriptionViews } = await import('../core/fetchPeerSubscriptionViews.js'); return fetchPeerSubscriptionViews({ peers: () => peers, fetchImpl: fetch, authToken: config.authToken ?? '' }); }, quotaPoller, quotaAwareScheduler: _quotaAwareScheduler ?? undefined, proactiveSwapMonitor: _proactiveSwapMonitor ?? undefined, inUseAccountResolver, enrollmentWizard, accountFollowMeRevocation, credentialRepointing, semanticMemory, activitySentinel, rateLimitSentinel, releaseReadinessSentinel: releaseReadinessSentinel ?? undefined, greenPrAutoMerger: greenPrAutoMerger ?? undefined, localVerify: localVerifyService ?? undefined, localVerifyStatus: localVerifyStatus ?? undefined, guardLatchStore: guardLatchStore ?? undefined, messageRouter, summarySentinel, spawnManager, systemReviewer, capabilityMapper, selfKnowledgeTree, coverageAuditor, topicResumeMap: _topicResumeMap ?? undefined, topicProfile: _topicProfileCtx ?? undefined, sessionRefresh: _sessionRefresh ?? undefined, autonomyManager, trustElevationTracker, autonomousEvolution, coordinator: coordinator.enabled ? coordinator : undefined, meshBindActive: coordinator.managers.identityManager.hasIdentity() && config.multiMachine?.meshTransport?.enabled !== false, localSigningKeyPem, leaseTransport, peerEndpointRecorder, getSelfMeshEndpoints, onLeasePullRequest: () => leaseCoordinatorRef?.currentLease() ?? null, liveTailReceiver, handoffWireTransport, onHandoffBegin, onHandoffInitiate: handoffInitiate, handoffInProgress: handoffSentinelInProgress, messageLedger, currentInboundByTopic, replyMarkerTransport, onReplyMarker: messageLedger ? (marker) => { const m = marker; messageLedger.applyRemoteReplyMarker(m.dedupeKey, { platform: m.platform, replyIdempotencyKey: m.replyIdempotencyKey, epoch: m.epoch, topic: m.topic ?? null }); } : undefined, whatsapp: whatsappAdapter, slack: slackAdapter, imessage: imessageAdapter, conversationRegistry, conversationBindAuth, appConversations: _appConversationService ?? undefined, slackInboundDispatch: () => _slackInboundDispatch, conversationFollowThrough, whatsappBusinessBackend, messageBridge, hookEventReceiver, worktreeMonitor, subagentTracker, instructionsVerifier, handshakeManager: threadlineHandshake, threadlineRouter, conversationStore, threadLog, threadMessageRecorder, warrantsReplyGate, collaborationSurfacer, peerHomebaseRelay, threadResumeMap, topicLinkageHandler: topicLinkageHandler ?? undefined, threadlineRelayClient, pairingInvites: threadlinePairingInvites, getLastRelayEvent: threadlineGetLastRelayEvent, a2aRelayForward: _a2aRelayForwardCtx ?? undefined, threadlineReplyWaiters, threadlineMcpHttp, listenerManager: listenerManager ?? undefined, a2aDeliveryTracker: a2aDeliveryTracker ?? undefined, relayVerdictCounters: threadlineRelayClient ? (() => ({ ...threadlineRelayClient.relayVerdictCounters, expiredMismatchIgnored: a2aDeliveryTracker?.expiredMismatchIgnored ?? 0 })) : undefined, inboundIdLedger: _inboundIdLedger ?? undefined, inboundIdLedgerDaemonDeferred: () => _inboundIdLedgerDaemonDeferred, responseReviewGate, reviewCanaryBattery, messagingToneGate, outboundDedupGate, telemetryHeartbeat, pasteManager, featureRegistry, discoveryEvaluator, completionEvaluator, unifiedTrust, liveConfig, sharedStateLedger, ledgerSessionRegistry, worktreeManager, oidcEnrolledRepos: parallelDevConfig?.oidcEnrolledRepos, initiativeTracker, projectRoundRunner, projectDriftChecker, machineHeartbeat, machinePoolRegistry, ropeHealthMonitor, writeAdmission: writeAdmission ?? undefined, getInboundQueue: () => _inboundQueue, getMachineCoherence: () => _machineCoherenceSentinel, getSingleMachineFailoverGap: () => _singleMachineFailoverGap, getMissingLoginSession: () => _missingLoginSession, getSessionPoolFailoverRunner: () => _sessionPoolFailoverRunnerDriver?.status() ?? null, sessionPoolPromotionActivation: _sessionPoolPromotionActivation, meshRpcDispatcher, deliverA2aToMachine: _deliverA2aToMachine ?? undefined, workingSetPullCoordinator, workingSetArtifactManager, orchestratorPoller, commitmentReplicaStore, preferenceReplicaStore, replicatedRecordEmitter, replicatedStoreReconciler, conflictStore, rollbackUnmerge, droppedOriginRegistry, preferencesUnionReader, jevMemoryPicker, forwardCommitmentMutate, sessionOwnershipRegistry, sendDrain: _sendDrain ?? undefined, topicPinStore: _topicPinStore ?? undefined, topicPinSkewQuarantine: _topicPinSkewQuarantine ?? undefined, topicPinFoldView: _topicPinFoldView ?? undefined, ownershipReconciler: _ownershipReconciler ?? undefined, staleOwnerEngine: _staleOwnerEngine ?? undefined, duplicateReconciler: _duplicateReconciler ?? undefined, ownerDarkLadder: _ownerDarkLadder ?? undefined, spawnAdmission: _spawnAdmission ?? undefined, judgmentProvenance: _judgmentProvenance ?? undefined, leaseHandback: _leaseHandbackCtx ?? undefined, streamTicketStore: _streamTicketStore ?? undefined, poolStreamAllowRemoteInput: config.dashboard?.poolStream?.allowRemoteInput ?? false, poolStreamConnector: _poolStreamConnector ?? undefined, secretSync: _secretSyncHandle ?? undefined, meshSelfId: _meshSelfId ?? undefined, resolveRouterUrl: _resolveRouterUrl ?? undefined, resolvePeerUrls: _resolvePeerUrls ?? undefined, recordRopeResult: _recordRopeResult ?? undefined, guardRegistry, listPoolMachines: _listPoolMachines ?? undefined, deliverMandateToMachine: _deliverMandateToMachine ?? undefined, passkeyRevokeOutbox: _passkeyRevokeOutbox ? () => _passkeyRevokeOutbox : undefined, passkeyPeerOnline: _passkeyPeerOnline, passkeyPoolReader: _passkeyPoolReader ? () => _passkeyPoolReader : undefined, passkeyProofBrowser: async (profileDir) => { const { ChromeCdpReloginBrowser } = await import('../core/ChromeCdpReloginBrowser.js'); return new ChromeCdpReloginBrowser({ userDataDir: profileDir, passkeyMode: true, headless: true, launchTimeoutMs: 30_000, operationTimeoutMs: 20_000 }); }, poolLink: _poolLink ?? undefined, poolPollCache: _poolPollCache ?? undefined, sessionPoolE2EResultStore, proxyCoordinator, topicIntentStore, topicIntentArcCheck, usherSignalStore, intelligence: sharedIntelligence ?? undefined, telegramBridgeConfig, telegramBridge: telegramBridge ?? undefined, threadlineObservability, briefDeps, workingMemory, taskFlowRegistry, threadlineFlowBridge, sessionReaper, agentWorktreeReaper, externalHogSentinel, orphanedWorkSentinel, mcpProcessReaper, codexArmSessionSweeper, geminiLoopRunner, sleepController, agentActivityState, reapLog, resumeQueue, resumeDrainer, autonomousLivenessReconciler, enforcedTerminationStatus: () => enforcedTerminationWatchdog?.guardStatus() ?? null, prHandLease: prHandLease ?? undefined, standDownRegistry: _standDownRegistry ?? undefined, standDownAudit: _standDownAudit ?? undefined, operatorStopRecorder: recordOperatorStop, sleepWakeDetector, unjustifiedStopGate, stopGateDb, stopNotifier, liveTestGate, liveTestGateMode, liveTestRunnerCtx }); // Resolve the late-bound topic-operator getter (increment 2e): routing was
29460
29484
  const readIdentityProjectionPeerRows = async () => {
29461
29485
  const peers = _resolvePeerUrls?.() ?? [];
29462
29486
  const extra = config.multiMachine?.peerUrlAllowlist;