@sema-agent/client-core 0.90.0 → 0.92.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.
Files changed (172) hide show
  1. package/CHANGELOG.md +365 -0
  2. package/README.md +48 -32
  3. package/dist/adapt/arms.js +13 -12
  4. package/dist/adapt/panelTasks.d.ts +0 -2
  5. package/dist/adapt/panelTasks.js +6 -26
  6. package/dist/adapt.js +2 -2
  7. package/dist/adapter/activeRunSelfHeal.d.ts +0 -2
  8. package/dist/adapter/activeRunSelfHeal.js +5 -27
  9. package/dist/adapter/downstream/eventToSdkMessage.js +4 -2
  10. package/dist/adapter/downstream/terminalToSdkResult.js +16 -7
  11. package/dist/adapter/downstream/wiringManifestView.d.ts +6 -0
  12. package/dist/adapter/downstream/wiringManifestView.js +16 -0
  13. package/dist/adapter/runStream.js +39 -20
  14. package/dist/askSurvivesStandingAnswer.d.ts +13 -0
  15. package/dist/askSurvivesStandingAnswer.js +53 -0
  16. package/dist/attachmentSeatCapability.d.ts +11 -0
  17. package/dist/attachmentSeatCapability.js +27 -0
  18. package/dist/attachmentsWireCaps.d.ts +9 -0
  19. package/dist/attachmentsWireCaps.js +74 -21
  20. package/dist/autoModeUnavailable.js +3 -2
  21. package/dist/cloudConfigWireCaps.js +5 -4
  22. package/dist/compensations.js +13 -17
  23. package/dist/controlRouter.d.ts +32 -25
  24. package/dist/controlRouter.js +166 -63
  25. package/dist/coreValuePorts.d.ts +4 -2
  26. package/dist/coreValuePorts.js +5 -0
  27. package/dist/decideFailureNote.js +7 -3
  28. package/dist/decideReceipt.d.ts +9 -0
  29. package/dist/decideReceipt.js +62 -1
  30. package/dist/disableSkillsWire.d.ts +1 -0
  31. package/dist/disableSkillsWire.js +8 -1
  32. package/dist/displayUntrusted.js +155 -5
  33. package/dist/effectiveFacts.d.ts +14 -4
  34. package/dist/effectiveFacts.js +45 -5
  35. package/dist/engineAgentAbsence.js +2 -1
  36. package/dist/engineCapReader.js +16 -10
  37. package/dist/engineCapsCache.d.ts +5 -1
  38. package/dist/engineCapsCache.js +69 -8
  39. package/dist/engineClosedSets.d.ts +2 -0
  40. package/dist/engineClosedSets.js +3 -0
  41. package/dist/engineErrorCodes.d.ts +17 -0
  42. package/dist/engineErrorCodes.js +47 -0
  43. package/dist/engineNoticeCodes.d.ts +14 -0
  44. package/dist/engineNoticeCodes.js +71 -0
  45. package/dist/executionLaneCapability.js +2 -0
  46. package/dist/gateOutcome.js +2 -17
  47. package/dist/gateVocabulary.d.ts +2 -4
  48. package/dist/gateVocabulary.js +3 -11
  49. package/dist/generated/engineFactTables.d.ts +27 -0
  50. package/dist/generated/engineFactTables.js +128 -0
  51. package/dist/generated/engineNoticeTables.js +3 -0
  52. package/dist/generated/settingsSchemaTables.d.ts +8 -0
  53. package/dist/generated/settingsSchemaTables.js +40 -0
  54. package/dist/hitl/allowRuleShadow.d.ts +21 -0
  55. package/dist/hitl/allowRuleShadow.js +167 -0
  56. package/dist/hitl/askClassPair.d.ts +14 -0
  57. package/dist/hitl/askClassPair.js +42 -0
  58. package/dist/hitl/askGateWire.d.ts +1 -1
  59. package/dist/hitl/askGateWire.js +2 -1
  60. package/dist/hitl/askSurvivesPosture.d.ts +5 -0
  61. package/dist/hitl/askSurvivesPosture.js +17 -0
  62. package/dist/hitl/automaticAnswerVerdict.d.ts +21 -0
  63. package/dist/hitl/automaticAnswerVerdict.js +143 -0
  64. package/dist/hitl/crashConverged.d.ts +8 -0
  65. package/dist/hitl/crashConverged.js +58 -1
  66. package/dist/hitl/crashConvergedNotice.d.ts +4 -0
  67. package/dist/hitl/crashConvergedNotice.js +57 -0
  68. package/dist/hitl/frameRouter.d.ts +2 -0
  69. package/dist/hitl/frameRouter.js +66 -14
  70. package/dist/hitl/gateLedger.d.ts +6 -0
  71. package/dist/hitl/gateLedger.js +34 -5
  72. package/dist/hitl/hitlBridge.d.ts +7 -4
  73. package/dist/hitl/hitlHostSurface.d.ts +2 -0
  74. package/dist/hitl/hitlHostSurface.js +7 -0
  75. package/dist/hitl/livePendingAsk.js +24 -5
  76. package/dist/hitl/parkResolver.d.ts +7 -2
  77. package/dist/hitl/parkResolver.js +21 -7
  78. package/dist/hitl/persistedRulesWire.d.ts +4 -1
  79. package/dist/hitl/persistedRulesWire.js +9 -2
  80. package/dist/hitl/planReviewWire.d.ts +1 -1
  81. package/dist/hitl/planReviewWire.js +19 -5
  82. package/dist/hitl/replayedApproval.d.ts +21 -0
  83. package/dist/hitl/replayedApproval.js +89 -0
  84. package/dist/hitl/sessionPolicyDeliverable.js +20 -2
  85. package/dist/hitl/sessionPolicyWire.d.ts +13 -0
  86. package/dist/hitl/sessionPolicyWire.js +75 -2
  87. package/dist/hitl/suspendedReopen.js +2 -2
  88. package/dist/hitl/toolApprovalWire.d.ts +9 -1
  89. package/dist/hitl/toolApprovalWire.js +40 -40
  90. package/dist/hookMatcherVerdict.d.ts +29 -0
  91. package/dist/hookMatcherVerdict.js +266 -0
  92. package/dist/humanTurn.d.ts +91 -0
  93. package/dist/humanTurn.js +252 -0
  94. package/dist/humanTurnRead.d.ts +105 -0
  95. package/dist/humanTurnRead.js +331 -0
  96. package/dist/index.d.ts +38 -11
  97. package/dist/index.js +27 -8
  98. package/dist/inheritEnvWire.js +4 -5
  99. package/dist/liveModelCatalog.d.ts +2 -0
  100. package/dist/liveModelCatalog.js +51 -3
  101. package/dist/mcpLiveness.js +2 -1
  102. package/dist/memoryVerbsWire.d.ts +1 -1
  103. package/dist/memoryVerbsWire.js +3 -0
  104. package/dist/model/catalog.js +2 -1
  105. package/dist/model/providerPresets.d.ts +3 -1
  106. package/dist/model/tierVocabulary.d.ts +2 -1
  107. package/dist/model/tierVocabulary.js +3 -8
  108. package/dist/peerFrames.js +2 -2
  109. package/dist/permissionRuleIssue.d.ts +1 -1
  110. package/dist/permissionRuleIssue.js +31 -9
  111. package/dist/permissionsAllowGrantCapability.d.ts +2 -1
  112. package/dist/permissionsAllowGrantCapability.js +11 -2
  113. package/dist/permissionsDeclaration.d.ts +29 -0
  114. package/dist/permissionsDeclaration.js +155 -66
  115. package/dist/pluginHooksWire.js +2 -11
  116. package/dist/promptDelivery.d.ts +11 -3
  117. package/dist/promptDelivery.js +164 -29
  118. package/dist/promptProfileWireCaps.d.ts +2 -1
  119. package/dist/protocolSegment.d.ts +9 -0
  120. package/dist/protocolSegment.js +28 -0
  121. package/dist/providerRejection.d.ts +1 -0
  122. package/dist/providerRejection.js +20 -0
  123. package/dist/readDenyTiers.d.ts +10 -0
  124. package/dist/readDenyTiers.js +29 -0
  125. package/dist/request/taskRequest.js +3 -17
  126. package/dist/resumeRefusalCopy.d.ts +11 -0
  127. package/dist/resumeRefusalCopy.js +61 -4
  128. package/dist/rewindArchiveCapability.js +4 -4
  129. package/dist/rewindWireCaps.d.ts +2 -1
  130. package/dist/rewindWireCaps.js +19 -2
  131. package/dist/ruleCompileVerdict.d.ts +2 -0
  132. package/dist/ruleCompileVerdict.js +13 -0
  133. package/dist/ruleRemovalConsequence.d.ts +2 -1
  134. package/dist/runCancelContext.d.ts +12 -0
  135. package/dist/runCancelContext.js +83 -1
  136. package/dist/seam.d.ts +2 -0
  137. package/dist/seam.js +1 -1
  138. package/dist/seatContract.d.ts +2 -1
  139. package/dist/sessionMemoryStatus.d.ts +2 -4
  140. package/dist/sessionSyncFileHistoryCapability.d.ts +18 -0
  141. package/dist/sessionSyncFileHistoryCapability.js +50 -0
  142. package/dist/skillToolListsCapability.d.ts +18 -0
  143. package/dist/skillToolListsCapability.js +50 -0
  144. package/dist/sqlEngineCapability.js +1 -8
  145. package/dist/steerPriorityCapability.d.ts +18 -0
  146. package/dist/steerPriorityCapability.js +80 -0
  147. package/dist/steerReceipt.d.ts +9 -0
  148. package/dist/steerReceipt.js +25 -0
  149. package/dist/subagent/engineSubagentSteer.js +2 -9
  150. package/dist/supportFloor.js +2 -2
  151. package/dist/taskRequestWords.d.ts +7 -1
  152. package/dist/taskRequestWords.js +18 -8
  153. package/dist/toolHistoryBadTurn.d.ts +1 -0
  154. package/dist/toolHistoryBadTurn.js +89 -0
  155. package/dist/toolHistoryMismatch.d.ts +2 -1
  156. package/dist/toolHistoryMismatch.js +19 -6
  157. package/dist/toolResult.d.ts +8 -0
  158. package/dist/toolResult.js +47 -3
  159. package/dist/types/engineState.d.ts +2 -12
  160. package/dist/userAttachmentEnvelope.d.ts +61 -0
  161. package/dist/userAttachmentEnvelope.js +204 -0
  162. package/dist/userInvokedSkillsCapability.d.ts +18 -0
  163. package/dist/userInvokedSkillsCapability.js +50 -0
  164. package/dist/wireFailureShape.d.ts +3 -0
  165. package/dist/wireFailureShape.js +8 -0
  166. package/dist/wireRefusalCopy.d.ts +6 -0
  167. package/dist/wireRefusalCopy.js +26 -3
  168. package/dist/workflowsJournalCapability.d.ts +18 -0
  169. package/dist/workflowsJournalCapability.js +50 -0
  170. package/dist/writeProtectionCapability.d.ts +2 -4
  171. package/docs/INTEGRATION-CLIENTS.md +1489 -16
  172. package/package.json +3 -3
@@ -1,3 +1,4 @@
1
+ import { SETTINGS_SECRET_LITERAL_RE } from './generated/settingsSchemaTables.js';
1
2
  export const REDACTION_MARKER_PREFIX = '\u00abredacted';
2
3
  const MARKER_RE = /^\u00abredacted(?::[a-z-]{1,16}){0,2}\u00bb$/;
3
4
  const REDACTED_USERINFO = '\u00abredacted:userinfo\u00bb';
@@ -26,7 +27,7 @@ function pushEdit(edits, src, start, end, text) {
26
27
  const UNIT_NONE = 0;
27
28
  const UNIT_SEQUENCE = 1;
28
29
  const UNIT_SINGLE = 2;
29
- const SECRET_LITERAL_RE = /^(sk-|gh[opus]_|github_pat_|xox[baprse]-|xapp-|bearer\s|basic\s|eyJ[A-Za-z0-9_-]{10,}\.|AKIA[0-9A-Z]{12,}|AIza[0-9A-Za-z_-]{20,}|-----BEGIN[A-Z0-9 ]*PRIVATE KEY)/i;
30
+ const SECRET_LITERAL_RE = SETTINGS_SECRET_LITERAL_RE;
30
31
  const SCHEME_TOKEN_RE = /(?:^|[^A-Za-z0-9_-])(?:bearer|basic)[ \t]+\S{8,4096}/i;
31
32
  const JWT_RE = /(?:^|[^A-Za-z0-9_-])eyJ[A-Za-z0-9_-]{8,2048}\.[A-Za-z0-9_-]{8,2048}\.[A-Za-z0-9_-]{4,2048}/i;
32
33
  function scanForSecretLiteral(s) {
@@ -1473,7 +1474,7 @@ function quotedAddressEnd(S, from, to) {
1473
1474
  }
1474
1475
  return to;
1475
1476
  }
1476
- function labelCandidates(S, pass, regions, out) {
1477
+ function labelCandidates(S, pass, regions, out, blocks) {
1477
1478
  const text = S.text;
1478
1479
  const unitAt = (k) => S.unitAt(k);
1479
1480
  const re = pass === 'label' ? SECRET_LABELLED_WORD : SECRET_SCHEME_WORD;
@@ -1642,6 +1643,11 @@ function labelCandidates(S, pass, regions, out) {
1642
1643
  if (schemePass && labelStartsAt(text, hit.index))
1643
1644
  continue;
1644
1645
  const from = hit.index + hit[0].length;
1646
+ if (blocks !== undefined && (text.charCodeAt(from) === 0x7c || text.charCodeAt(from) === 0x3e) && isColonSeparator(hit[0].slice((hit[1] ?? '').length))) {
1647
+ const blk = blockScalarExtent(blocks, S.rawStart(from), S.rawStart(hit.index));
1648
+ if (blk !== null)
1649
+ blocks.out.push({ start: blk.start, end: blk.end, kind: 'secret', cls: 'word', tokenEnd: blk.end, pretrimmed: true });
1650
+ }
1645
1651
  if (credentialWordStartsAt(text, from, idx.tokenInner)) {
1646
1652
  pushInnerRemainder(from);
1647
1653
  re.lastIndex = from;
@@ -1886,6 +1892,149 @@ function lineBreakLengthBefore(text, at) {
1886
1892
  return 2;
1887
1893
  return 0;
1888
1894
  }
1895
+ const isRawBlank = (c) => (isRegexSpace(c) && c !== 0xfeff) || isNameBlank(c);
1896
+ function isColonSeparator(sep) {
1897
+ let colon = false;
1898
+ for (let k = 0; k < sep.length; k++) {
1899
+ const c = sep.charCodeAt(k);
1900
+ if (c === 0x3d || c === 0xff1d)
1901
+ return false;
1902
+ if (c === 0x3a || c === 0xff1a)
1903
+ colon = true;
1904
+ }
1905
+ return colon;
1906
+ }
1907
+ function blockBreakAt(raw, at, escaped) {
1908
+ const n = lineBreakLengthAt(raw, at);
1909
+ return n > 0 && (raw.charCodeAt(at) === 0x5c) === escaped ? n : 0;
1910
+ }
1911
+ function blockMarks(scan) {
1912
+ if (scan.marks !== null)
1913
+ return scan.marks;
1914
+ const V = scan.view;
1915
+ const seq = new Uint8Array(scan.raw.length);
1916
+ const payload = new Uint8Array(scan.raw.length);
1917
+ for (let k = 0; k < V.view.length; k++) {
1918
+ if (V.dropped[k] !== 1 || V.units[k] !== UNIT_SEQUENCE)
1919
+ continue;
1920
+ for (let x = V.starts[k] ?? 0; x < (V.ends[k] ?? 0); x++)
1921
+ seq[x] = 1;
1922
+ }
1923
+ for (const [a, b] of V.contents)
1924
+ for (let x = a; x < b; x++)
1925
+ payload[x] = 1;
1926
+ scan.marks = { seq, payload };
1927
+ return scan.marks;
1928
+ }
1929
+ function blockLines(scan, escaped) {
1930
+ const slot = escaped ? 1 : 0;
1931
+ const have = scan.lines[slot];
1932
+ if (have !== null)
1933
+ return have;
1934
+ const raw = scan.raw;
1935
+ const unit = scan.view.rawUnit;
1936
+ const { seq, payload } = blockMarks(scan);
1937
+ const starts = [];
1938
+ const ends = [];
1939
+ const indent = [];
1940
+ let pos = 0;
1941
+ for (;;) {
1942
+ let k = pos;
1943
+ let n = 0;
1944
+ let width = 0;
1945
+ let lead = true;
1946
+ let visible = false;
1947
+ while (k < raw.length && (n = blockBreakAt(raw, k, escaped)) === 0) {
1948
+ if (lead) {
1949
+ const c = raw.charCodeAt(k);
1950
+ if (payload[k] === 1)
1951
+ visible = true;
1952
+ if (seq[k] === 1) {
1953
+ }
1954
+ else if (isRawBlank(c))
1955
+ width++;
1956
+ else if (unit[k] !== 1) {
1957
+ visible = true;
1958
+ lead = false;
1959
+ }
1960
+ }
1961
+ k++;
1962
+ }
1963
+ starts.push(pos);
1964
+ ends.push(k);
1965
+ indent.push(visible ? width : -1);
1966
+ if (k >= raw.length)
1967
+ break;
1968
+ pos = k + n;
1969
+ }
1970
+ const nextContent = new Int32Array(starts.length + 1);
1971
+ nextContent[starts.length] = starts.length;
1972
+ for (let i = starts.length - 1; i >= 0; i--)
1973
+ nextContent[i] = (indent[i] ?? -1) !== -1 ? i : (nextContent[i + 1] ?? starts.length);
1974
+ const built = { starts, ends, indent, nextContent, memo: new Map() };
1975
+ scan.lines[slot] = built;
1976
+ return built;
1977
+ }
1978
+ function blockLineOf(lines, p) {
1979
+ let lo = 0;
1980
+ let hi = lines.starts.length - 1;
1981
+ while (lo < hi) {
1982
+ const mid = (lo + hi + 1) >> 1;
1983
+ if ((lines.starts[mid] ?? 0) <= p)
1984
+ lo = mid;
1985
+ else
1986
+ hi = mid - 1;
1987
+ }
1988
+ return lo;
1989
+ }
1990
+ function blockScalarExtent(scan, at, labelAt) {
1991
+ const raw = scan.raw;
1992
+ const mark = raw.charCodeAt(at);
1993
+ if (mark !== 0x7c && mark !== 0x3e)
1994
+ return null;
1995
+ const unit = scan.view.rawUnit;
1996
+ let k = at + 1;
1997
+ while (k < raw.length && lineBreakLengthAt(raw, k) === 0) {
1998
+ const c = raw.charCodeAt(k);
1999
+ if (c === 0x2d || c === 0x2b || (c >= 0x30 && c <= 0x39) || (unit[k] === 1 && !isRawBlank(c)))
2000
+ k++;
2001
+ else
2002
+ break;
2003
+ }
2004
+ while (k < raw.length && lineBreakLengthAt(raw, k) === 0 && (isRawBlank(raw.charCodeAt(k)) || unit[k] === 1))
2005
+ k++;
2006
+ if (k >= raw.length)
2007
+ return null;
2008
+ let escaped;
2009
+ if (lineBreakLengthAt(raw, k) > 0)
2010
+ escaped = raw.charCodeAt(k) === 0x5c;
2011
+ else if (raw.charCodeAt(k) === 0x23) {
2012
+ const real = blockLines(scan, false);
2013
+ if ((real.ends[blockLineOf(real, k)] ?? raw.length) < raw.length)
2014
+ escaped = false;
2015
+ else {
2016
+ const lit = blockLines(scan, true);
2017
+ if ((lit.ends[blockLineOf(lit, k)] ?? raw.length) >= raw.length)
2018
+ return null;
2019
+ escaped = true;
2020
+ }
2021
+ }
2022
+ else
2023
+ return null;
2024
+ const lines = blockLines(scan, escaped);
2025
+ const head = blockLineOf(lines, at);
2026
+ const limit = Math.max(0, lines.indent[blockLineOf(lines, labelAt)] ?? 0);
2027
+ const key = head * (raw.length + 1) + limit;
2028
+ let end = lines.memo.get(key);
2029
+ if (end === undefined) {
2030
+ end = lines.ends[head] ?? raw.length;
2031
+ for (let i = lines.nextContent[head + 1] ?? lines.starts.length; i < lines.starts.length && (lines.indent[i] ?? -1) > limit; i = lines.nextContent[i + 1] ?? lines.starts.length) {
2032
+ end = lines.ends[i] ?? end;
2033
+ }
2034
+ lines.memo.set(key, end);
2035
+ }
2036
+ return { start: at, end };
2037
+ }
1889
2038
  function pemBodyEndWithoutTrailer(text, from) {
1890
2039
  let pos = from;
1891
2040
  let inBody = false;
@@ -2779,6 +2928,7 @@ function collectCandidates(text, o, nested) {
2779
2928
  const screen = screenSurfaces(text, o);
2780
2929
  surfaces.push(...screen.surfaces);
2781
2930
  const raw = [];
2931
+ const blocks = { raw: text, view: V, out: raw, lines: [null, null], marks: null };
2782
2932
  const regionSurface = screen.surfaces[0] ?? separated;
2783
2933
  const pemBlocksSeen = [];
2784
2934
  for (const S of surfaces) {
@@ -2792,9 +2942,9 @@ function collectCandidates(text, o, nested) {
2792
2942
  if (o.words) {
2793
2943
  editsToCandidates(pemEdits(S, (blk) => { if (S === regionSurface)
2794
2944
  pemBlocksSeen.push(pemBlockToRaw(S, blk)); }), 'pem', cands);
2795
- labelCandidates(S, 'scheme', regions, cands);
2796
- labelCandidates(S, 'token', regions, cands);
2797
- labelCandidates(S, 'label', regions, cands);
2945
+ labelCandidates(S, 'scheme', regions, cands, blocks);
2946
+ labelCandidates(S, 'token', regions, cands, blocks);
2947
+ labelCandidates(S, 'label', regions, cands, blocks);
2798
2948
  editsToCandidates(authParamEdits(S.text), 'param', cands);
2799
2949
  editsToCandidates(proseLiteralEdits(S.text), 'prose', cands);
2800
2950
  }
@@ -7,15 +7,25 @@ export interface EffectiveReasoningView {
7
7
  endpoint: string;
8
8
  dropped?: true;
9
9
  }
10
+ export type EffectiveMemoryProjectKey = {
11
+ readonly scope: string;
12
+ readonly absent?: never;
13
+ } | {
14
+ readonly absent: string;
15
+ readonly scope?: never;
16
+ };
17
+ export interface EffectiveMemoryScopeRow {
18
+ scope: string;
19
+ origin: 'deployment' | 'request';
20
+ shadowed?: number;
21
+ }
10
22
  export interface EffectiveMemoryScopesView {
11
23
  state: 'mounted' | 'memoryless' | 'none';
12
24
  reason?: string;
13
25
  contract?: 'v2' | 'legacy';
14
- scopes: readonly {
15
- scope: string;
16
- origin: 'deployment' | 'request';
17
- }[];
26
+ scopes: readonly EffectiveMemoryScopeRow[];
18
27
  writeScope: string | null;
28
+ projectKey?: EffectiveMemoryProjectKey;
19
29
  materializedResidue?: readonly string[];
20
30
  }
21
31
  export declare function readEffectiveReasoning(v: unknown): EffectiveReasoningView | undefined;
@@ -1,4 +1,37 @@
1
1
  const nonEmpty = (v) => typeof v === 'string' && v.length > 0;
2
+ const nonBlank = (v) => typeof v === 'string' && v.trim().length > 0;
3
+ const UNREADABLE = Symbol('unreadable');
4
+ const protectedRead = (o, key) => {
5
+ try {
6
+ return o[key];
7
+ }
8
+ catch {
9
+ return UNREADABLE;
10
+ }
11
+ };
12
+ function readProjectKey(v) {
13
+ try {
14
+ if (typeof v !== 'object' || v === null || Array.isArray(v))
15
+ return undefined;
16
+ const o = v;
17
+ const scope = protectedRead(o, 'scope');
18
+ const absent = protectedRead(o, 'absent');
19
+ if (scope === UNREADABLE || absent === UNREADABLE)
20
+ return undefined;
21
+ if ((scope === undefined) === (absent === undefined))
22
+ return undefined;
23
+ if (scope !== undefined)
24
+ return nonBlank(scope) ? { scope } : undefined;
25
+ return nonBlank(absent) ? { absent } : undefined;
26
+ }
27
+ catch {
28
+ return undefined;
29
+ }
30
+ }
31
+ function readShadowed(r, isWriteHome) {
32
+ const n = protectedRead(r, 'shadowed');
33
+ return !isWriteHome && typeof n === 'number' && Number.isSafeInteger(n) && n > 0 ? n : undefined;
34
+ }
2
35
  export function readEffectiveReasoning(v) {
3
36
  if (typeof v !== 'object' || v === null)
4
37
  return undefined;
@@ -27,7 +60,8 @@ export function readEffectiveMemoryScopes(v) {
27
60
  return undefined;
28
61
  if (!Array.isArray(o.scopes))
29
62
  return undefined;
30
- if (o.writeScope !== null && typeof o.writeScope !== 'string')
63
+ const writeScope = o.writeScope;
64
+ if (writeScope !== null && typeof writeScope !== 'string')
31
65
  return undefined;
32
66
  const contract = o.contract === 'v2' || o.contract === 'legacy' ? o.contract : undefined;
33
67
  const reason = nonEmpty(o.reason) ? o.reason : undefined;
@@ -39,13 +73,19 @@ export function readEffectiveMemoryScopes(v) {
39
73
  if (typeof row !== 'object' || row === null)
40
74
  continue;
41
75
  const r = row;
42
- if (!nonEmpty(r.scope) || typeof r.origin !== 'string' || !ORIGINS.has(r.origin))
76
+ const scope = r.scope;
77
+ if (!nonEmpty(scope))
78
+ continue;
79
+ const origin = r.origin;
80
+ if (typeof origin !== 'string' || !ORIGINS.has(origin))
43
81
  continue;
44
- scopes.push({ scope: r.scope, origin: r.origin });
82
+ const shadowed = readShadowed(r, scope === writeScope);
83
+ scopes.push({ scope, origin: origin, ...(shadowed !== undefined ? { shadowed } : {}) });
45
84
  }
46
- return { state: 'mounted', contract, scopes, writeScope: o.writeScope };
85
+ const projectKey = readProjectKey(protectedRead(o, 'projectKey'));
86
+ return { state: 'mounted', contract, scopes, writeScope, ...(projectKey !== undefined ? { projectKey } : {}) };
47
87
  }
48
- if (o.scopes.length !== 0 || o.writeScope !== null)
88
+ if (o.scopes.length !== 0 || writeScope !== null)
49
89
  return undefined;
50
90
  if (o.state === 'memoryless') {
51
91
  if (reason !== 'mount-failed' && reason !== 'no-backend')
@@ -2,6 +2,7 @@ import { registryClockNowMs, registryListingProvenanceOf } from './agentSession/
2
2
  import { displayUntrusted } from './displayUntrusted.js';
3
3
  import { ABSENT_SETTLE_MS } from './fleetAgentPanelProjection.js';
4
4
  import { isEnginePanelTaskResident, isStaleEngineAgentPanelEnd, } from './engineAgentPanelStore.js';
5
+ import { CORE_DURABLE_AGENT_HANDLE_RE } from './generated/engineFactTables.js';
5
6
  export const ENGINE_AGENT_ABSENT_ROW_TEXT = 'engine no longer reports this agent · it may still be running';
6
7
  export const ENGINE_AGENT_ABSENCE_TTL_MS = 30 * 60_000;
7
8
  function effectiveTtl(ttlMs) {
@@ -132,7 +133,7 @@ export function engineAgentTerminalAfterDropLine(label, status, hasReport) {
132
133
  return `${displayUntrusted(label)} reported ${displayUntrusted(status)} after it was dropped from the task panel${tail}`;
133
134
  }
134
135
  const REGISTRY_LIST_LIMIT = 500;
135
- const REGISTRY_AGENT_HANDLE_RE = /^a[0-9a-f]{6,32}$/;
136
+ const REGISTRY_AGENT_HANDLE_RE = CORE_DURABLE_AGENT_HANDLE_RE;
136
137
  const REGISTRY_AGENT_TYPE = 'background_agent';
137
138
  function registryStatusReading(status) {
138
139
  const s = status;
@@ -1,4 +1,5 @@
1
1
  import { snapshotCapsGeneration, capsGenerationStillCurrent } from './engineCapsGenerationGuard.js';
2
+ import { capsGenerationMarkOf, retainCapsGenerationMark } from './engineCapsCache.js';
2
3
  function freezeReading(reading, seen = new Set()) {
3
4
  if (reading === null || typeof reading !== 'object' || seen.has(reading))
4
5
  return reading;
@@ -11,7 +12,7 @@ function freezeReading(reading, seen = new Set()) {
11
12
  return reading;
12
13
  }
13
14
  export function createEngineCapReader(spec) {
14
- const readingByBase = new Map();
15
+ const cellByBase = new Map();
15
16
  return {
16
17
  note(baseUrl, caps, opts) {
17
18
  if (typeof baseUrl !== 'string' || baseUrl === '')
@@ -21,6 +22,7 @@ export function createEngineCapReader(spec) {
21
22
  return;
22
23
  if (!capsGenerationStillCurrent(baseUrl, gen))
23
24
  return;
25
+ const mark = retainCapsGenerationMark(baseUrl);
24
26
  let reading;
25
27
  try {
26
28
  reading = spec.project(caps);
@@ -28,29 +30,33 @@ export function createEngineCapReader(spec) {
28
30
  catch {
29
31
  reading = undefined;
30
32
  }
31
- if (!capsGenerationStillCurrent(baseUrl, gen))
33
+ if (capsGenerationMarkOf(baseUrl) !== mark)
32
34
  return;
33
35
  if (reading === undefined) {
34
- readingByBase.delete(baseUrl);
36
+ cellByBase.delete(baseUrl);
35
37
  return;
36
38
  }
37
- readingByBase.set(baseUrl, freezeReading(reading));
39
+ cellByBase.set(baseUrl, { reading: freezeReading(reading), mark });
38
40
  },
39
41
  observed(baseUrl) {
40
42
  if (typeof baseUrl !== 'string' || baseUrl === '')
41
43
  return spec.makeUnobserved();
42
- const hit = readingByBase.get(baseUrl);
43
- if (hit !== undefined)
44
- return hit;
45
- return spec.makeUnobserved();
44
+ const cell = cellByBase.get(baseUrl);
45
+ if (cell === undefined)
46
+ return spec.makeUnobserved();
47
+ if (cell.mark !== capsGenerationMarkOf(baseUrl)) {
48
+ cellByBase.delete(baseUrl);
49
+ return spec.makeUnobserved();
50
+ }
51
+ return cell.reading;
46
52
  },
47
53
  forget(baseUrl) {
48
54
  if (typeof baseUrl !== 'string' || baseUrl === '')
49
55
  return;
50
- readingByBase.delete(baseUrl);
56
+ cellByBase.delete(baseUrl);
51
57
  },
52
58
  __resetForTests() {
53
- readingByBase.clear();
59
+ cellByBase.clear();
54
60
  },
55
61
  };
56
62
  }
@@ -1,6 +1,10 @@
1
1
  export declare function engineCapsGeneration(baseUrl: string): number;
2
+ export declare function capsGenerationMarkOf(baseUrl: string): object | undefined;
3
+ export declare function retainCapsGenerationMark(baseUrl: string): object;
2
4
  export declare function kickEngineCapsProbe(baseUrl: string, probe: () => Promise<unknown>): void;
3
- export declare function engineCapsSettled(baseUrl: string | undefined): Promise<void>;
5
+ export declare function engineCapsSettled(baseUrl: string | undefined, opts?: {
6
+ withinMs?: number;
7
+ }): Promise<'settled' | 'timed_out'>;
4
8
  export type EngineCapState = 'true' | 'false' | 'unprobed' | 'absent' | 'non_boolean';
5
9
  export declare function engineCapState(baseUrl: string | undefined, key: string): EngineCapState;
6
10
  export declare function engineCapTrue(baseUrl: string | undefined, key: string): boolean;
@@ -3,11 +3,22 @@ const inFlight = new Set();
3
3
  const settleByBase = new Map();
4
4
  const genByBase = new Map();
5
5
  function capsGeneration(baseUrl) {
6
- return genByBase.get(baseUrl) ?? 0;
6
+ return genByBase.get(baseUrl)?.n ?? 0;
7
7
  }
8
8
  export function engineCapsGeneration(baseUrl) {
9
9
  return capsGeneration(baseUrl);
10
10
  }
11
+ export function capsGenerationMarkOf(baseUrl) {
12
+ return genByBase.get(baseUrl);
13
+ }
14
+ export function retainCapsGenerationMark(baseUrl) {
15
+ let mark = genByBase.get(baseUrl);
16
+ if (mark === undefined) {
17
+ mark = Object.freeze({ n: 0 });
18
+ genByBase.set(baseUrl, mark);
19
+ }
20
+ return mark;
21
+ }
11
22
  export function kickEngineCapsProbe(baseUrl, probe) {
12
23
  if (!baseUrl || capsByBase.has(baseUrl) || inFlight.has(baseUrl))
13
24
  return;
@@ -43,21 +54,71 @@ export function kickEngineCapsProbe(baseUrl, probe) {
43
54
  }
44
55
  })();
45
56
  }
46
- export async function engineCapsSettled(baseUrl) {
47
- if (!baseUrl)
48
- return;
57
+ const MAX_WITHIN_MS = 2_147_483_647;
58
+ function waitBudgetOf(opts) {
59
+ try {
60
+ if (opts === undefined || opts === null)
61
+ return undefined;
62
+ if (typeof opts !== 'object')
63
+ return 0;
64
+ const v = opts.withinMs;
65
+ if (v === undefined)
66
+ return undefined;
67
+ if (typeof v !== 'number' || !Number.isFinite(v) || !(v > 0))
68
+ return 0;
69
+ return v > MAX_WITHIN_MS ? MAX_WITHIN_MS : v;
70
+ }
71
+ catch {
72
+ return 0;
73
+ }
74
+ }
75
+ async function relaySettled(baseUrl, deadline) {
49
76
  for (;;) {
50
77
  const entry = settleByBase.get(baseUrl);
51
78
  if (entry === undefined)
52
- return;
79
+ return 'settled';
53
80
  const awaitedGen = entry.gen;
54
- await Promise.race([
81
+ const landed = Promise.race([
55
82
  entry.promise.then(() => undefined, () => undefined),
56
83
  entry.superseded,
57
84
  ]);
85
+ if (deadline === undefined) {
86
+ await landed;
87
+ }
88
+ else {
89
+ const first = await Promise.race([landed.then(() => 'landed'), deadline]);
90
+ if (first === 'timed_out')
91
+ return 'timed_out';
92
+ }
58
93
  const next = settleByBase.get(baseUrl);
59
94
  if (next === undefined || next.gen <= awaitedGen)
60
- return;
95
+ return 'settled';
96
+ }
97
+ }
98
+ export async function engineCapsSettled(baseUrl, opts) {
99
+ const budget = waitBudgetOf(opts);
100
+ if (!baseUrl)
101
+ return 'settled';
102
+ if (budget === undefined)
103
+ return relaySettled(baseUrl, undefined);
104
+ if (settleByBase.get(baseUrl) === undefined)
105
+ return 'settled';
106
+ if (budget === 0)
107
+ return 'timed_out';
108
+ let timer;
109
+ try {
110
+ const deadline = new Promise((resolve) => {
111
+ timer = setTimeout(() => resolve('timed_out'), budget);
112
+ });
113
+ deadline.catch(() => undefined);
114
+ return await relaySettled(baseUrl, deadline);
115
+ }
116
+ catch {
117
+ return 'timed_out';
118
+ }
119
+ finally {
120
+ if (timer !== undefined)
121
+ clearTimeout(timer);
61
122
  }
62
123
  }
63
124
  export function engineCapState(baseUrl, key) {
@@ -115,7 +176,7 @@ export function invalidateEngineCaps(baseUrl, probe) {
115
176
  settleByBase.has(baseUrl) ||
116
177
  genByBase.has(baseUrl);
117
178
  if (hadState) {
118
- genByBase.set(baseUrl, capsGeneration(baseUrl) + 1);
179
+ genByBase.set(baseUrl, Object.freeze({ n: capsGeneration(baseUrl) + 1 }));
119
180
  capsByBase.delete(baseUrl);
120
181
  inFlight.delete(baseUrl);
121
182
  settleByBase.get(baseUrl)?.wake();
@@ -0,0 +1,2 @@
1
+ export declare const ASK_EVIDENCE_ABSENCE_VALUES: readonly ["not_wired", "not_adjudicated", "unavailable", "no_match", "not_reported"];
2
+ export declare const SYSTEM_INJECTION_PRIORITIES: readonly ["now", "next", "later"];
@@ -0,0 +1,3 @@
1
+ import { CORE_ASK_EVIDENCE_ABSENCE_VALUES, CORE_SYSTEM_INJECTION_PRIORITIES } from './generated/engineFactTables.js';
2
+ export const ASK_EVIDENCE_ABSENCE_VALUES = CORE_ASK_EVIDENCE_ABSENCE_VALUES;
3
+ export const SYSTEM_INJECTION_PRIORITIES = CORE_SYSTEM_INJECTION_PRIORITIES;
@@ -14,6 +14,8 @@ export declare const CONFIG_DELEGATION_ENTRY_CAPS = "config.delegation_entry_cap
14
14
  export declare const CONFIG_MEMORY_PROJECT_KEY_SPELLING = "config.memory_project_key_spelling";
15
15
  export declare const CONFIG_MEMORY_WRITE_SCOPE_MISMATCH = "config.memory_write_scope_mismatch";
16
16
  export declare const CONFIG_LEGACY_TOOL_NAME = "config.legacy_tool_name";
17
+ export declare const CONFIG_IMAGE_INVALID = "config.image_invalid";
18
+ export declare function imageInvalidFailureNoteOf(code: string | undefined): string | undefined;
17
19
  export declare const CONFIG_REFUSAL_CODES: ReadonlySet<string>;
18
20
  export declare const RULES_LEGACY_TOOL_NAME = "rules.legacy_tool_name";
19
21
  export declare function isRulesRefusalCode(code: string | undefined): boolean;
@@ -49,6 +51,9 @@ export declare function isRewindFamilyCode(code: string | undefined): boolean;
49
51
  export declare const RESUME_USAGE_WINDOW_EXHAUSTED = "resume.usage_window_exhausted";
50
52
  export declare const RESUME_PREFLIGHT_REJECTED = "resume.preflight_rejected";
51
53
  export declare const RESUME_SESSION_NOT_FOUND = "resume.session_not_found";
54
+ export declare const REQUEST_FIELD_CONFLICT = "request.field_conflict";
55
+ export declare const CHECKPOINT_UNSUPPORTED_VERSION = "checkpoint.unsupported_version";
56
+ export declare function refusalSaysStillPending(err: object): boolean;
52
57
  export type StatusDerivedCoarseCode = (typeof STATUS_DERIVED_COARSE_CODES)[number];
53
58
  export declare const RESUME_PLACEMENT_MISMATCH = "resume.placement_mismatch";
54
59
  export declare const RESUME_CONTEXT_UNAVAILABLE = "conflict.resume_context_unavailable";
@@ -66,6 +71,18 @@ export declare const DECIDE_GATE_MOVED = "decide.gate_moved";
66
71
  export declare const DECIDE_CLAIM_LOST = "decide.claim_lost";
67
72
  export declare const DECIDE_PARK_MOVED_CODES: readonly string[];
68
73
  export declare function isDecideParkMovedCode(code: string | null | undefined): boolean;
74
+ export declare const ASK_GONE = "gone.ask";
75
+ export declare const ASK_GONE_DENIED_WORD = "routing_failure_fail_closed";
76
+ export declare const RUN_STALLED = "run.stalled";
77
+ export declare const RUN_ORPHANED = "run.orphaned";
78
+ export declare const APPROVAL_EXPIRED = "approval.expired";
79
+ export declare const RUN_DEATH_VERDICT_CODES: readonly ["run.stalled", "run.orphaned", "approval.expired"];
80
+ export type RunDeathVerdictCode = (typeof RUN_DEATH_VERDICT_CODES)[number];
81
+ export declare function runDeathVerdictNoteOf(code: string | undefined): string | undefined;
82
+ export declare const CAPABILITY_OPERATOR_PRINCIPALS_REQUIRED = "capability.operator_principals_required";
83
+ export declare function isUnavailableFaceCode(code: string | undefined): boolean;
84
+ export type OperatorGateRefusal = 'operator_only' | 'operators_unconfigured';
85
+ export declare function operatorGateRefusalContent(cause: OperatorGateRefusal): string | undefined;
69
86
  export declare const WORKFLOW_PARK_REFUSAL_CODES: readonly string[];
70
87
  export declare function isWorkflowParkRefusalCode(code: unknown): boolean;
71
88
  export declare const DRAINING_ERROR_CODE = "draining";
@@ -19,6 +19,12 @@ export const CONFIG_DELEGATION_ENTRY_CAPS = 'config.delegation_entry_caps';
19
19
  export const CONFIG_MEMORY_PROJECT_KEY_SPELLING = 'config.memory_project_key_spelling';
20
20
  export const CONFIG_MEMORY_WRITE_SCOPE_MISMATCH = 'config.memory_write_scope_mismatch';
21
21
  export const CONFIG_LEGACY_TOOL_NAME = 'config.legacy_tool_name';
22
+ export const CONFIG_IMAGE_INVALID = 'config.image_invalid';
23
+ const IMAGE_INVALID_FAILURE_NOTE = 'This run did not start: an image sent with the message was refused before the model was called — the engine’s own error text says which image and what is wrong with it. ' +
24
+ 'Nothing was sent to the model; remove or replace that image, then send the message again.';
25
+ export function imageInvalidFailureNoteOf(code) {
26
+ return code === CONFIG_IMAGE_INVALID ? IMAGE_INVALID_FAILURE_NOTE : undefined;
27
+ }
22
28
  export const CONFIG_REFUSAL_CODES = frozenSet([
23
29
  CONFIG_LIMIT_INVALID,
24
30
  CONFIG_STRATEGY_FIND_LIMIT_INVALID,
@@ -28,6 +34,7 @@ export const CONFIG_REFUSAL_CODES = frozenSet([
28
34
  CONFIG_MEMORY_PROJECT_KEY_SPELLING,
29
35
  CONFIG_MEMORY_WRITE_SCOPE_MISMATCH,
30
36
  CONFIG_LEGACY_TOOL_NAME,
37
+ CONFIG_IMAGE_INVALID,
31
38
  ...CORE_TOOL_DECLARATION_CODES,
32
39
  ]);
33
40
  export const RULES_LEGACY_TOOL_NAME = 'rules.legacy_tool_name';
@@ -107,6 +114,16 @@ export function isRewindFamilyCode(code) {
107
114
  export const RESUME_USAGE_WINDOW_EXHAUSTED = 'resume.usage_window_exhausted';
108
115
  export const RESUME_PREFLIGHT_REJECTED = 'resume.preflight_rejected';
109
116
  export const RESUME_SESSION_NOT_FOUND = 'resume.session_not_found';
117
+ export const REQUEST_FIELD_CONFLICT = 'request.field_conflict';
118
+ export const CHECKPOINT_UNSUPPORTED_VERSION = 'checkpoint.unsupported_version';
119
+ export function refusalSaysStillPending(err) {
120
+ try {
121
+ return Object.hasOwn(err, 'retriable') && err.retriable === true;
122
+ }
123
+ catch {
124
+ return false;
125
+ }
126
+ }
110
127
  export const RESUME_PLACEMENT_MISMATCH = 'resume.placement_mismatch';
111
128
  export const RESUME_CONTEXT_UNAVAILABLE = 'conflict.resume_context_unavailable';
112
129
  export const RESUME_RETRY_LATER_CODES = Object.freeze([
@@ -139,6 +156,36 @@ export const DECIDE_PARK_MOVED_CODES = Object.freeze([
139
156
  export function isDecideParkMovedCode(code) {
140
157
  return typeof code === 'string' && DECIDE_PARK_MOVED_CODES.includes(code);
141
158
  }
159
+ export const ASK_GONE = 'gone.ask';
160
+ export const ASK_GONE_DENIED_WORD = 'routing_failure_fail_closed';
161
+ export const RUN_STALLED = 'run.stalled';
162
+ export const RUN_ORPHANED = 'run.orphaned';
163
+ export const APPROVAL_EXPIRED = 'approval.expired';
164
+ export const RUN_DEATH_VERDICT_CODES = Object.freeze([RUN_STALLED, RUN_ORPHANED, APPROVAL_EXPIRED]);
165
+ const RUN_HOLDER_LOST_NOTE = 'This run ended because the engine process that was running it went away (it was restarted, or stopped answering) before the run finished. ' +
166
+ 'The request itself was not at fault, but this run cannot be picked up again; submit the work again as a new task.';
167
+ const RUN_APPROVAL_EXPIRED_NOTE = 'This run ended because it was waiting on an approval for too long and the engine retired it. ' +
168
+ 'The request itself was not at fault, but this run cannot be picked up again; submit the work again as a new task, and it will ask for the approval again.';
169
+ export function runDeathVerdictNoteOf(code) {
170
+ if (code === RUN_STALLED || code === RUN_ORPHANED)
171
+ return RUN_HOLDER_LOST_NOTE;
172
+ if (code === APPROVAL_EXPIRED)
173
+ return RUN_APPROVAL_EXPIRED_NOTE;
174
+ return undefined;
175
+ }
176
+ export const CAPABILITY_OPERATOR_PRINCIPALS_REQUIRED = 'capability.operator_principals_required';
177
+ export function isUnavailableFaceCode(code) {
178
+ return typeof code === 'string' && (code.startsWith('capability.') || code.startsWith('feature.'));
179
+ }
180
+ export function operatorGateRefusalContent(cause) {
181
+ if (cause === 'operator_only') {
182
+ return 'Nothing was done: this is an operator-only action and the caller is not one of this deployment’s operators.';
183
+ }
184
+ if (cause === 'operators_unconfigured') {
185
+ return 'Nothing was done: this is an operator-only action and this deployment has no operators configured, so no caller can perform it here — whoever runs the deployment has to name its operators first.';
186
+ }
187
+ return undefined;
188
+ }
142
189
  const WORKFLOW_PARK_TRUTH_UNREADABLE = 'workflow.park_truth_unreadable';
143
190
  const WORKFLOW_PARK_NOT_PENDING = 'workflow.park_not_pending';
144
191
  const WORKFLOW_PARK_BINDING_BROKEN = 'workflow.park_binding_broken';
@@ -169,6 +169,19 @@ export interface UserInputUndrainedFactsView {
169
169
  }
170
170
  export declare function readUserInputUndrained(notice: unknown): UserInputUndrainedFactsView | undefined;
171
171
  export declare function userInputUndrainedNotice(facts: Pick<UserInputUndrainedFactsView, 'kind' | 'count' | 'cause' | 'childSessionId'>): string | undefined;
172
+ export interface TurnInterruptedFactsView {
173
+ lane: 'input_now' | 'user_halt' | 'unrecognized';
174
+ inputId?: string;
175
+ cause?: string;
176
+ sessionId?: string;
177
+ runId?: string;
178
+ taskId?: string;
179
+ actorId?: string;
180
+ }
181
+ export declare function readTurnInterrupted(notice: unknown): TurnInterruptedFactsView | undefined;
182
+ export declare function turnInterruptedNotice(facts: Pick<TurnInterruptedFactsView, 'lane'>): string | undefined;
183
+ export type SteerCutVerdict = 'this_input' | 'other_input' | 'user_halt' | 'unattributed' | 'not_a_cut';
184
+ export declare function steerCutVerdict(notice: unknown, messageId: string | undefined): SteerCutVerdict;
172
185
  export declare const ENGINE_NOTICE_FACT_READERS: Readonly<{
173
186
  readonly 'mcp.injection_dropped': typeof readMcpInjectionDrop;
174
187
  readonly 'delegation.ask_unresolvable': typeof readAskUnresolvable;
@@ -189,6 +202,7 @@ export declare const ENGINE_NOTICE_FACT_READERS: Readonly<{
189
202
  readonly 'task.tool_turn_incomplete': typeof readToolTurnIncomplete;
190
203
  readonly 'task.user_steer_undrained': typeof readUserInputUndrained;
191
204
  readonly 'task.user_followup_undrained': typeof readUserInputUndrained;
205
+ readonly 'task.turn_interrupted': typeof readTurnInterrupted;
192
206
  }>;
193
207
  type FactReaderTable = typeof ENGINE_NOTICE_FACT_READERS;
194
208
  export type EngineNoticeFactsCode = keyof FactReaderTable;