agentfootprint 9.94.3 → 9.96.1

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 (156) hide show
  1. package/CHANGELOG.md +48 -0
  2. package/CLAUDE.md +4 -1
  3. package/dist/answer-validation/evidence.js +121 -0
  4. package/dist/answer-validation/evidence.js.map +1 -0
  5. package/dist/answer-validation/index.js +10 -0
  6. package/dist/answer-validation/index.js.map +1 -0
  7. package/dist/answer-validation/types.js +24 -0
  8. package/dist/answer-validation/types.js.map +1 -0
  9. package/dist/answer-validation/validate.js +326 -0
  10. package/dist/answer-validation/validate.js.map +1 -0
  11. package/dist/core/Agent.js +93 -3
  12. package/dist/core/Agent.js.map +1 -1
  13. package/dist/core/agent/AgentBuilder.js +27 -1
  14. package/dist/core/agent/AgentBuilder.js.map +1 -1
  15. package/dist/core/agent/buildAgentChart.js +17 -2
  16. package/dist/core/agent/buildAgentChart.js.map +1 -1
  17. package/dist/core/agent/buildDynamicAgentChart.js +27 -2
  18. package/dist/core/agent/buildDynamicAgentChart.js.map +1 -1
  19. package/dist/core/agent/evidence/gate.js +13 -1
  20. package/dist/core/agent/evidence/gate.js.map +1 -1
  21. package/dist/core/agent/evidence/recovery.js +75 -0
  22. package/dist/core/agent/evidence/recovery.js.map +1 -0
  23. package/dist/core/agent/outputEnforcement.js.map +1 -1
  24. package/dist/core/agent/stages/answerValidation.js +57 -0
  25. package/dist/core/agent/stages/answerValidation.js.map +1 -0
  26. package/dist/core/agent/stages/breakFinal.js +11 -1
  27. package/dist/core/agent/stages/breakFinal.js.map +1 -1
  28. package/dist/core/agent/stages/callLLM.js +31 -8
  29. package/dist/core/agent/stages/callLLM.js.map +1 -1
  30. package/dist/core/agent/stages/evidenceRecheck.js +12 -22
  31. package/dist/core/agent/stages/evidenceRecheck.js.map +1 -1
  32. package/dist/core/agent/stages/prepareFinal.js +35 -2
  33. package/dist/core/agent/stages/prepareFinal.js.map +1 -1
  34. package/dist/core/agent/stages/route.js +9 -5
  35. package/dist/core/agent/stages/route.js.map +1 -1
  36. package/dist/core/agent/stages/seed.js +6 -1
  37. package/dist/core/agent/stages/seed.js.map +1 -1
  38. package/dist/core/runCheckpoint.js +22 -1
  39. package/dist/core/runCheckpoint.js.map +1 -1
  40. package/dist/esm/answer-validation/evidence.d.ts +12 -0
  41. package/dist/esm/answer-validation/evidence.js +117 -0
  42. package/dist/esm/answer-validation/evidence.js.map +1 -0
  43. package/dist/esm/answer-validation/index.d.ts +3 -0
  44. package/dist/esm/answer-validation/index.js +4 -0
  45. package/dist/esm/answer-validation/index.js.map +1 -0
  46. package/dist/esm/answer-validation/types.d.ts +94 -0
  47. package/dist/esm/answer-validation/types.js +20 -0
  48. package/dist/esm/answer-validation/types.js.map +1 -0
  49. package/dist/esm/answer-validation/validate.d.ts +15 -0
  50. package/dist/esm/answer-validation/validate.js +321 -0
  51. package/dist/esm/answer-validation/validate.js.map +1 -0
  52. package/dist/esm/core/Agent.d.ts +10 -1
  53. package/dist/esm/core/Agent.js +93 -3
  54. package/dist/esm/core/Agent.js.map +1 -1
  55. package/dist/esm/core/agent/AgentBuilder.d.ts +11 -0
  56. package/dist/esm/core/agent/AgentBuilder.js +27 -1
  57. package/dist/esm/core/agent/AgentBuilder.js.map +1 -1
  58. package/dist/esm/core/agent/buildAgentChart.d.ts +2 -0
  59. package/dist/esm/core/agent/buildAgentChart.js +19 -4
  60. package/dist/esm/core/agent/buildAgentChart.js.map +1 -1
  61. package/dist/esm/core/agent/buildDynamicAgentChart.js +29 -4
  62. package/dist/esm/core/agent/buildDynamicAgentChart.js.map +1 -1
  63. package/dist/esm/core/agent/evidence/gate.js +13 -1
  64. package/dist/esm/core/agent/evidence/gate.js.map +1 -1
  65. package/dist/esm/core/agent/evidence/index.d.ts +1 -1
  66. package/dist/esm/core/agent/evidence/recovery.d.ts +21 -0
  67. package/dist/esm/core/agent/evidence/recovery.js +69 -0
  68. package/dist/esm/core/agent/evidence/recovery.js.map +1 -0
  69. package/dist/esm/core/agent/evidence/types.d.ts +30 -0
  70. package/dist/esm/core/agent/outputEnforcement.d.ts +2 -0
  71. package/dist/esm/core/agent/outputEnforcement.js.map +1 -1
  72. package/dist/esm/core/agent/stages/answerValidation.d.ts +10 -0
  73. package/dist/esm/core/agent/stages/answerValidation.js +53 -0
  74. package/dist/esm/core/agent/stages/answerValidation.js.map +1 -0
  75. package/dist/esm/core/agent/stages/breakFinal.d.ts +6 -0
  76. package/dist/esm/core/agent/stages/breakFinal.js +9 -0
  77. package/dist/esm/core/agent/stages/breakFinal.js.map +1 -1
  78. package/dist/esm/core/agent/stages/callLLM.d.ts +4 -0
  79. package/dist/esm/core/agent/stages/callLLM.js +31 -8
  80. package/dist/esm/core/agent/stages/callLLM.js.map +1 -1
  81. package/dist/esm/core/agent/stages/evidenceRecheck.d.ts +3 -6
  82. package/dist/esm/core/agent/stages/evidenceRecheck.js +13 -23
  83. package/dist/esm/core/agent/stages/evidenceRecheck.js.map +1 -1
  84. package/dist/esm/core/agent/stages/prepareFinal.d.ts +7 -0
  85. package/dist/esm/core/agent/stages/prepareFinal.js +33 -1
  86. package/dist/esm/core/agent/stages/prepareFinal.js.map +1 -1
  87. package/dist/esm/core/agent/stages/route.js +9 -5
  88. package/dist/esm/core/agent/stages/route.js.map +1 -1
  89. package/dist/esm/core/agent/stages/seed.d.ts +3 -0
  90. package/dist/esm/core/agent/stages/seed.js +6 -1
  91. package/dist/esm/core/agent/stages/seed.js.map +1 -1
  92. package/dist/esm/core/agent/types.d.ts +12 -1
  93. package/dist/esm/core/runCheckpoint.d.ts +17 -1
  94. package/dist/esm/core/runCheckpoint.js +22 -1
  95. package/dist/esm/core/runCheckpoint.js.map +1 -1
  96. package/dist/esm/events/types.d.ts +1 -1
  97. package/dist/esm/index.d.ts +2 -1
  98. package/dist/esm/index.js +2 -0
  99. package/dist/esm/index.js.map +1 -1
  100. package/dist/esm/lib/time-travel/servedView.js +5 -2
  101. package/dist/esm/lib/time-travel/servedView.js.map +1 -1
  102. package/dist/esm/recorders/core/contextEngineering.js +1 -0
  103. package/dist/esm/recorders/core/contextEngineering.js.map +1 -1
  104. package/dist/index.js +4 -1
  105. package/dist/index.js.map +1 -1
  106. package/dist/lib/time-travel/servedView.js +5 -2
  107. package/dist/lib/time-travel/servedView.js.map +1 -1
  108. package/dist/recorders/core/contextEngineering.js +1 -0
  109. package/dist/recorders/core/contextEngineering.js.map +1 -1
  110. package/dist/types/answer-validation/evidence.d.ts +13 -0
  111. package/dist/types/answer-validation/evidence.d.ts.map +1 -0
  112. package/dist/types/answer-validation/index.d.ts +4 -0
  113. package/dist/types/answer-validation/index.d.ts.map +1 -0
  114. package/dist/types/answer-validation/types.d.ts +95 -0
  115. package/dist/types/answer-validation/types.d.ts.map +1 -0
  116. package/dist/types/answer-validation/validate.d.ts +16 -0
  117. package/dist/types/answer-validation/validate.d.ts.map +1 -0
  118. package/dist/types/core/Agent.d.ts +10 -1
  119. package/dist/types/core/Agent.d.ts.map +1 -1
  120. package/dist/types/core/agent/AgentBuilder.d.ts +11 -0
  121. package/dist/types/core/agent/AgentBuilder.d.ts.map +1 -1
  122. package/dist/types/core/agent/buildAgentChart.d.ts +2 -0
  123. package/dist/types/core/agent/buildAgentChart.d.ts.map +1 -1
  124. package/dist/types/core/agent/buildDynamicAgentChart.d.ts.map +1 -1
  125. package/dist/types/core/agent/evidence/gate.d.ts.map +1 -1
  126. package/dist/types/core/agent/evidence/index.d.ts +1 -1
  127. package/dist/types/core/agent/evidence/index.d.ts.map +1 -1
  128. package/dist/types/core/agent/evidence/recovery.d.ts +22 -0
  129. package/dist/types/core/agent/evidence/recovery.d.ts.map +1 -0
  130. package/dist/types/core/agent/evidence/types.d.ts +30 -0
  131. package/dist/types/core/agent/evidence/types.d.ts.map +1 -1
  132. package/dist/types/core/agent/outputEnforcement.d.ts +2 -0
  133. package/dist/types/core/agent/outputEnforcement.d.ts.map +1 -1
  134. package/dist/types/core/agent/stages/answerValidation.d.ts +11 -0
  135. package/dist/types/core/agent/stages/answerValidation.d.ts.map +1 -0
  136. package/dist/types/core/agent/stages/breakFinal.d.ts +6 -0
  137. package/dist/types/core/agent/stages/breakFinal.d.ts.map +1 -1
  138. package/dist/types/core/agent/stages/callLLM.d.ts +4 -0
  139. package/dist/types/core/agent/stages/callLLM.d.ts.map +1 -1
  140. package/dist/types/core/agent/stages/evidenceRecheck.d.ts +3 -6
  141. package/dist/types/core/agent/stages/evidenceRecheck.d.ts.map +1 -1
  142. package/dist/types/core/agent/stages/prepareFinal.d.ts +7 -0
  143. package/dist/types/core/agent/stages/prepareFinal.d.ts.map +1 -1
  144. package/dist/types/core/agent/stages/seed.d.ts +3 -0
  145. package/dist/types/core/agent/stages/seed.d.ts.map +1 -1
  146. package/dist/types/core/agent/types.d.ts +12 -1
  147. package/dist/types/core/agent/types.d.ts.map +1 -1
  148. package/dist/types/core/runCheckpoint.d.ts +17 -1
  149. package/dist/types/core/runCheckpoint.d.ts.map +1 -1
  150. package/dist/types/events/types.d.ts +1 -1
  151. package/dist/types/events/types.d.ts.map +1 -1
  152. package/dist/types/index.d.ts +2 -1
  153. package/dist/types/index.d.ts.map +1 -1
  154. package/dist/types/lib/time-travel/servedView.d.ts.map +1 -1
  155. package/dist/types/recorders/core/contextEngineering.d.ts.map +1 -1
  156. package/package.json +1 -1
@@ -0,0 +1,321 @@
1
+ /** One explicit JSON-answer validation; the runner owns when to invoke it. */
2
+ import { applyOutputSchema } from '../core/outputSchema.js';
3
+ import { computeArtifactDigest } from '../artifacts/payload.js';
4
+ import { createAnswerEvidenceResolver } from './evidence.js';
5
+ const DEFAULT_LIMITS = Object.freeze({
6
+ maxReads: 16,
7
+ maxBytes: 4 * 1024 * 1024,
8
+ maxChecks: 100,
9
+ maxCandidateBytes: 1024 * 1024,
10
+ timeoutMs: 5000,
11
+ });
12
+ const encoder = new TextEncoder();
13
+ const dispositions = new Set(['checked-pass', 'checked-fail', 'not-applicable', 'unreachable']);
14
+ function ownData(value, allowed) {
15
+ if (value === null ||
16
+ typeof value !== 'object' ||
17
+ Array.isArray(value) ||
18
+ ![Object.prototype, null].includes(Object.getPrototypeOf(value)))
19
+ throw new Error('Expected a plain data object.');
20
+ const result = Object.create(null);
21
+ for (const key of Reflect.ownKeys(value)) {
22
+ if (typeof key !== 'string' || (allowed && !allowed.includes(key)))
23
+ throw new Error('Unknown property.');
24
+ const descriptor = Object.getOwnPropertyDescriptor(value, key);
25
+ if (!descriptor?.enumerable || !('value' in descriptor))
26
+ throw new Error('Expected an enumerable data property.');
27
+ Object.defineProperty(result, key, { value: descriptor.value, enumerable: true });
28
+ }
29
+ return result;
30
+ }
31
+ function text(value, max) {
32
+ if (typeof value !== 'string' || value.trim() === '' || value.length > max)
33
+ throw new Error('Expected bounded non-empty text.');
34
+ return value;
35
+ }
36
+ /** Validate and snapshot an authored contract once, before running an agent. */
37
+ export function resolveAnswerValidation(options) {
38
+ const source = ownData(options, ['id', 'version', 'mode', 'limits', 'validate']);
39
+ const id = text(source.id, 128);
40
+ const version = text(source.version, 128);
41
+ const mode = source.mode === undefined ? 'enforce' : source.mode;
42
+ if (mode !== 'enforce' && mode !== 'observe')
43
+ throw new Error('answerValidation.mode must be enforce or observe.');
44
+ if (typeof source.validate !== 'function')
45
+ throw new Error('answerValidation.validate must be a function.');
46
+ const validate = source.validate;
47
+ const supplied = source.limits === undefined ? {} : ownData(source.limits, Object.keys(DEFAULT_LIMITS));
48
+ const limits = { ...DEFAULT_LIMITS };
49
+ for (const key of Object.keys(DEFAULT_LIMITS)) {
50
+ if (Object.hasOwn(supplied, key)) {
51
+ const value = supplied[key];
52
+ if (typeof value !== 'number' ||
53
+ !Number.isSafeInteger(value) ||
54
+ value <= 0 ||
55
+ (key === 'timeoutMs' && value > 2147483647))
56
+ throw new Error(`answerValidation.limits.${key} must be a positive bounded integer.`);
57
+ limits[key] = value;
58
+ }
59
+ }
60
+ return Object.freeze({
61
+ id,
62
+ version,
63
+ mode,
64
+ limits: Object.freeze(limits),
65
+ validate: (candidate, context) => validate(candidate, context),
66
+ });
67
+ }
68
+ /** JSON copy without invoking toJSON/getters or silently dropping data. */
69
+ function jsonCopy(value, maxBytes, freeze) {
70
+ let budget = maxBytes;
71
+ const ancestors = new Set();
72
+ const spend = (bytes) => {
73
+ budget -= bytes;
74
+ if (budget < 0)
75
+ throw new Error('JSON byte limit.');
76
+ };
77
+ const string = (item) => {
78
+ if (item.length > budget)
79
+ throw new Error('JSON byte limit.');
80
+ spend(encoder.encode(JSON.stringify(item)).byteLength);
81
+ };
82
+ const copy = (item, depth) => {
83
+ if (depth > 100)
84
+ throw new Error('JSON nesting limit.');
85
+ if (item === null) {
86
+ spend(4);
87
+ return null;
88
+ }
89
+ if (typeof item === 'string') {
90
+ string(item);
91
+ return item;
92
+ }
93
+ if (typeof item === 'boolean') {
94
+ spend(item ? 4 : 5);
95
+ return item;
96
+ }
97
+ if (typeof item === 'number') {
98
+ if (!Number.isFinite(item) || Object.is(item, -0))
99
+ throw new Error('Non-lossless JSON number.');
100
+ spend(JSON.stringify(item).length);
101
+ return item;
102
+ }
103
+ if (typeof item !== 'object')
104
+ throw new Error('Non-JSON value.');
105
+ if (ancestors.has(item))
106
+ throw new Error('Cyclic JSON value.');
107
+ ancestors.add(item);
108
+ spend(2);
109
+ let output;
110
+ if (Array.isArray(item)) {
111
+ if (Object.getPrototypeOf(item) !== Array.prototype)
112
+ throw new Error('Non-JSON array prototype.');
113
+ if (item.length > budget + 1)
114
+ throw new Error('JSON byte limit.');
115
+ const keys = Reflect.ownKeys(item);
116
+ if (keys.length !== item.length + 1)
117
+ throw new Error('Sparse or decorated array.');
118
+ const result = [];
119
+ for (let index = 0; index < item.length; index++) {
120
+ const descriptor = Object.getOwnPropertyDescriptor(item, String(index));
121
+ if (!descriptor?.enumerable || !('value' in descriptor))
122
+ throw new Error('Sparse or accessor array.');
123
+ if (index)
124
+ spend(1);
125
+ result.push(copy(descriptor.value, depth + 1));
126
+ }
127
+ output = result;
128
+ }
129
+ else {
130
+ const fields = ownData(item);
131
+ const result = {};
132
+ let index = 0;
133
+ for (const key of Object.keys(fields)) {
134
+ if (index++)
135
+ spend(1);
136
+ string(key);
137
+ spend(1);
138
+ Object.defineProperty(result, key, {
139
+ value: copy(fields[key], depth + 1),
140
+ enumerable: true,
141
+ writable: true,
142
+ configurable: true,
143
+ });
144
+ }
145
+ output = result;
146
+ }
147
+ ancestors.delete(item);
148
+ return freeze ? Object.freeze(output) : output;
149
+ };
150
+ return copy(value, 0);
151
+ }
152
+ function readChecks(value, config, resolved) {
153
+ // Bound before copying. The copy rejects getters, class instances, cycles,
154
+ // decorated arrays and values JSON would otherwise silently discard.
155
+ const source = ownData(value, ['checks']);
156
+ if (!Array.isArray(source.checks) || source.checks.length > config.limits.maxChecks)
157
+ throw new Error('Invalid checks.');
158
+ const detached = jsonCopy(source.checks, config.limits.maxChecks * 4096, false);
159
+ const ids = new Set();
160
+ const refs = new Set(resolved);
161
+ return detached.map((raw) => {
162
+ const check = ownData(raw, ['id', 'disposition', 'reason', 'path', 'evidenceRefs']);
163
+ const id = text(check.id, 128);
164
+ if (ids.has(id) ||
165
+ typeof check.disposition !== 'string' ||
166
+ !dispositions.has(check.disposition))
167
+ throw new Error('Invalid check identity or disposition.');
168
+ ids.add(id);
169
+ const reason = check.reason === undefined ? undefined : text(check.reason, 1024);
170
+ const path = check.path;
171
+ if (path !== undefined && (typeof path !== 'string' || path.length > 256))
172
+ throw new Error('Invalid check path.');
173
+ let evidenceRefs;
174
+ if (check.evidenceRefs !== undefined) {
175
+ if (!Array.isArray(check.evidenceRefs) || check.evidenceRefs.length > config.limits.maxReads)
176
+ throw new Error('Invalid evidence references.');
177
+ evidenceRefs = check.evidenceRefs.map((ref) => {
178
+ if (typeof ref !== 'string' || !refs.has(ref))
179
+ throw new Error('Unresolved evidence reference.');
180
+ return ref;
181
+ });
182
+ if (new Set(evidenceRefs).size !== evidenceRefs.length)
183
+ throw new Error('Duplicate evidence reference.');
184
+ }
185
+ return Object.freeze({
186
+ id,
187
+ disposition: check.disposition,
188
+ ...(reason !== undefined && { reason }),
189
+ ...(path !== undefined && { path }),
190
+ ...(evidenceRefs !== undefined && { evidenceRefs: Object.freeze(evidenceRefs) }),
191
+ });
192
+ });
193
+ }
194
+ /**
195
+ * Validate once. Content is present only when delivery is permitted by this
196
+ * contract. It is the exact JSON string whose detached value was checked;
197
+ * callers must not reparse through a transforming schema or rewrite afterward.
198
+ */
199
+ export async function executeAnswerValidation(raw, parser, config, store, scope, signal) {
200
+ const controller = new AbortController();
201
+ const evidence = createAnswerEvidenceResolver(store, scope, config.limits, controller.signal);
202
+ let reason;
203
+ let schemaAccepted = false;
204
+ let canonical;
205
+ let candidateDigest;
206
+ let checks = [];
207
+ let active = true;
208
+ let stop;
209
+ const abort = () => {
210
+ reason = 'aborted';
211
+ controller.abort();
212
+ stop?.();
213
+ };
214
+ const timedOut = () => {
215
+ reason = 'timeout';
216
+ controller.abort();
217
+ stop?.();
218
+ };
219
+ const deadline = Date.now() + config.limits.timeoutMs;
220
+ const timer = setTimeout(timedOut, config.limits.timeoutMs);
221
+ signal?.addEventListener('abort', abort, { once: true });
222
+ if (signal?.aborted)
223
+ abort();
224
+ try {
225
+ const interrupted = new Promise((resolve) => {
226
+ stop = resolve;
227
+ if (controller.signal.aborted)
228
+ resolve();
229
+ });
230
+ const work = async () => {
231
+ if (controller.signal.aborted)
232
+ return;
233
+ let candidate;
234
+ try {
235
+ if (raw.length > config.limits.maxCandidateBytes ||
236
+ encoder.encode(raw).byteLength > config.limits.maxCandidateBytes) {
237
+ reason = 'candidate-limit';
238
+ return;
239
+ }
240
+ candidate = applyOutputSchema(raw, parser);
241
+ }
242
+ catch {
243
+ reason = 'schema-rejected';
244
+ return;
245
+ }
246
+ try {
247
+ candidate = jsonCopy(candidate, config.limits.maxCandidateBytes, true);
248
+ canonical = JSON.stringify(candidate);
249
+ schemaAccepted = true;
250
+ }
251
+ catch {
252
+ reason = 'non-json-candidate';
253
+ return;
254
+ }
255
+ if (Date.now() >= deadline) {
256
+ timedOut();
257
+ return;
258
+ }
259
+ try {
260
+ const digest = await computeArtifactDigest(canonical);
261
+ if (!active || controller.signal.aborted)
262
+ return;
263
+ candidateDigest = digest;
264
+ const returned = await config.validate(candidate, Object.freeze({ signal: controller.signal, artifacts: evidence.resolver }));
265
+ if (!active || controller.signal.aborted)
266
+ return;
267
+ if (Date.now() >= deadline) {
268
+ timedOut();
269
+ return;
270
+ }
271
+ try {
272
+ checks = readChecks(returned, config, evidence.resolvedRefs());
273
+ }
274
+ catch {
275
+ reason = 'invalid-validator-result';
276
+ }
277
+ }
278
+ catch {
279
+ if (active && !controller.signal.aborted)
280
+ reason = 'validator-error';
281
+ }
282
+ };
283
+ await Promise.race([work(), interrupted]);
284
+ }
285
+ finally {
286
+ active = false;
287
+ clearTimeout(timer);
288
+ signal?.removeEventListener('abort', abort);
289
+ evidence.close();
290
+ controller.abort();
291
+ }
292
+ const failed = checks.filter((check) => check.disposition === 'checked-fail').length;
293
+ const checked = failed + checks.filter((check) => check.disposition === 'checked-pass').length;
294
+ const unreachable = checks.filter((check) => check.disposition === 'unreachable').length;
295
+ const notApplicable = checks.filter((check) => check.disposition === 'not-applicable').length;
296
+ if (!reason && evidence.failureReason())
297
+ reason = `evidence-${evidence.failureReason()}`;
298
+ if (!reason && checked === 0)
299
+ reason = 'no-comparable-checks';
300
+ if (!reason && unreachable > 0)
301
+ reason = 'unreachable-checks';
302
+ const status = reason ? 'unverified' : failed > 0 ? 'failed' : 'passed';
303
+ const report = Object.freeze({
304
+ validatorId: config.id,
305
+ validatorVersion: config.version,
306
+ mode: config.mode,
307
+ status,
308
+ checked,
309
+ failed,
310
+ unreachable,
311
+ notApplicable,
312
+ checks: Object.freeze(checks),
313
+ schemaAccepted,
314
+ ...(reason !== undefined && { reason }),
315
+ ...(candidateDigest !== undefined && { candidateDigest }),
316
+ resolvedRefs: Object.freeze(evidence.resolvedRefs()),
317
+ });
318
+ const content = status === 'passed' || config.mode === 'observe' ? canonical ?? raw : undefined;
319
+ return { report, ...(content !== undefined && { content }) };
320
+ }
321
+ //# sourceMappingURL=validate.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validate.js","sourceRoot":"","sources":["../../../src/answer-validation/validate.ts"],"names":[],"mappings":"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"}
@@ -36,6 +36,7 @@ import { RunnerBase } from './RunnerBase.js';
36
36
  import type { ToolRegistryEntry } from './tools.js';
37
37
  import type { ToolProvider } from '../tool-providers/types.js';
38
38
  import type { AgentArtifactsOptions, AgentInput, AgentOptions, AgentOutput, AgentRecordingsOptions, AgentState, ObserverDeliveryOptions, RunConfig, RunConfigContext, RunConfigFn, WriteProvenanceMode } from './agent/types.js';
39
+ import { type AnswerValidationReport, type ResolvedAnswerValidation } from '../answer-validation/index.js';
39
40
  import type { MessageMiddleware, ToolMiddleware } from './agent/middleware/types.js';
40
41
  import { AgentBuilder } from './agent/AgentBuilder.js';
41
42
  export type { SkillGraphOptions } from './agent/AgentBuilder.js';
@@ -361,6 +362,8 @@ export declare class Agent extends RunnerBase<AgentInput, AgentOutput> {
361
362
  * function restores `scope.history` from this instead of starting
362
363
  * fresh. Cleared on first read so subsequent runs start clean. */
363
364
  private pendingResumeHistory?;
365
+ /** Retried request's repair state; never inherited by a new human turn. */
366
+ private pendingEvidenceRecovery?;
364
367
  /** Its sibling for the folded spans. A restored conversation that dropped
365
368
  * them would carry summaries nobody could unpack — the evidence would be
366
369
  * destroyed by the act of continuing, which is the one thing retention
@@ -463,6 +466,7 @@ export declare class Agent extends RunnerBase<AgentInput, AgentOutput> {
463
466
  /** `AgentOptions.recordReceipt` (9.88.0) — ON by default. `false` declines
464
467
  * the mint at `callLLM`; nothing else about the run changes. */
465
468
  private readonly recordReceiptValue;
469
+ private readonly answerValidationConfig?;
466
470
  constructor(opts: AgentOptions, systemPromptValue: string, registry: readonly ToolRegistryEntry[], voice: {
467
471
  readonly appName: string;
468
472
  readonly commentaryTemplates: Readonly<Record<string, string>>;
@@ -472,7 +476,7 @@ export declare class Agent extends RunnerBase<AgentInput, AgentOutput> {
472
476
  readonly strictness: 'assist' | 'guard' | 'rails';
473
477
  readonly continuity: 'turn' | 'conversation';
474
478
  readonly nodeIds: ReadonlySet<string>;
475
- }, skillBrains?: import('./agent/skillBrains.js').FoldedSkillBrains, evidenceGate?: ResolvedEvidenceGate, limitsTravelWithTheAnswer?: boolean, recipes?: readonly AppliedRecipe[], skillGraphDeclared?: SkillGraphDeclaredMap, mapsPlan?: import('../maps/engagement/types.js').EngagementPlan, claimContract?: readonly import('../integrity/unsupported-claim/check.js').DeclaredClaim[]);
479
+ }, skillBrains?: import('./agent/skillBrains.js').FoldedSkillBrains, evidenceGate?: ResolvedEvidenceGate, limitsTravelWithTheAnswer?: boolean, recipes?: readonly AppliedRecipe[], skillGraphDeclared?: SkillGraphDeclaredMap, mapsPlan?: import('../maps/engagement/types.js').EngagementPlan, claimContract?: readonly import('../integrity/unsupported-claim/check.js').DeclaredClaim[], answerValidationConfig?: ResolvedAnswerValidation);
476
480
  static create(opts: AgentOptions): AgentBuilder;
477
481
  /**
478
482
  * Cache policy for the base system prompt. Read by the CacheDecision
@@ -873,6 +877,8 @@ export declare class Agent extends RunnerBase<AgentInput, AgentOutput> {
873
877
  * ```
874
878
  */
875
879
  checkpoint(): AgentRunCheckpoint | undefined;
880
+ /** Both checkpoint doors keep the repair budget separately from conversation text. */
881
+ private evidenceRecoveryOf;
876
882
  /**
877
883
  * The graph cursor a conversation carrier stores — the run's final
878
884
  * committed `currentSkillId`, read from the SNAPSHOT (the state the run
@@ -1302,6 +1308,9 @@ export declare class Agent extends RunnerBase<AgentInput, AgentOutput> {
1302
1308
  * ```
1303
1309
  */
1304
1310
  unsupportedValues(): AgentState['unsupportedValues'];
1311
+ /** The last run's answer checks, detached from its execution record.
1312
+ * Undefined means no terminal validation ran, never an implicit pass. */
1313
+ answerValidation(): AnswerValidationReport | undefined;
1305
1314
  private finalizeResult;
1306
1315
  private buildChart;
1307
1316
  }
@@ -121,6 +121,8 @@ import { buildOutputRetryStage } from './agent/stages/outputRetry.js';
121
121
  import { RunnerBase, makeRunId } from './RunnerBase.js';
122
122
  import { clampIterations, validateMemoryIdUniqueness, validateToolNameUniqueness, } from './agent/validators.js';
123
123
  import { buildRouteDeciderStage } from './agent/stages/route.js';
124
+ import { withAnswerValidation } from './agent/stages/answerValidation.js';
125
+ import { AnswerValidationError, } from '../answer-validation/index.js';
124
126
  import { buildSeedStage } from './agent/stages/seed.js';
125
127
  import { MessageDeniedError } from './agent/middleware/errors.js';
126
128
  import { buildCallLLMStage } from './agent/stages/callLLM.js';
@@ -414,6 +416,8 @@ export class Agent extends RunnerBase {
414
416
  * function restores `scope.history` from this instead of starting
415
417
  * fresh. Cleared on first read so subsequent runs start clean. */
416
418
  pendingResumeHistory;
419
+ /** Retried request's repair state; never inherited by a new human turn. */
420
+ pendingEvidenceRecovery;
417
421
  /** Its sibling for the folded spans. A restored conversation that dropped
418
422
  * them would carry summaries nobody could unpack — the evidence would be
419
423
  * destroyed by the act of continuing, which is the one thing retention
@@ -516,8 +520,10 @@ export class Agent extends RunnerBase {
516
520
  /** `AgentOptions.recordReceipt` (9.88.0) — ON by default. `false` declines
517
521
  * the mint at `callLLM`; nothing else about the run changes. */
518
522
  recordReceiptValue = true;
519
- constructor(opts, systemPromptValue, registry, voice, injections = [], memories = [], outputSchemaParser, toolProvider, systemPromptCachePolicy = 'always', cachingDisabled = false, cacheStrategy, outputFallbackCfg, reliabilityConfig, thinkingHandlerValue, thinkingBudgetValue, skillGraphNextSkill, skillGraphReachable, skillGraphScoreEntries, checkInOptions, runConfigFn, windowStrategy, toolMiddleware, messageMiddleware, outputEnforcement, skillGraphEdgeTargets, skillGraphExplainNextSkill, skillGraphIsTree, skillGraphSupersededEntries, skillGraphCascade, skillBrains, evidenceGate, limitsTravelWithTheAnswer, recipes, skillGraphDeclared, mapsPlan, claimContract) {
523
+ answerValidationConfig;
524
+ constructor(opts, systemPromptValue, registry, voice, injections = [], memories = [], outputSchemaParser, toolProvider, systemPromptCachePolicy = 'always', cachingDisabled = false, cacheStrategy, outputFallbackCfg, reliabilityConfig, thinkingHandlerValue, thinkingBudgetValue, skillGraphNextSkill, skillGraphReachable, skillGraphScoreEntries, checkInOptions, runConfigFn, windowStrategy, toolMiddleware, messageMiddleware, outputEnforcement, skillGraphEdgeTargets, skillGraphExplainNextSkill, skillGraphIsTree, skillGraphSupersededEntries, skillGraphCascade, skillBrains, evidenceGate, limitsTravelWithTheAnswer, recipes, skillGraphDeclared, mapsPlan, claimContract, answerValidationConfig) {
520
525
  super();
526
+ this.answerValidationConfig = answerValidationConfig;
521
527
  this.provider = opts.provider;
522
528
  this.name = opts.name ?? 'Agent';
523
529
  this.id = opts.id ?? 'agent';
@@ -1144,6 +1150,17 @@ export class Agent extends RunnerBase {
1144
1150
  throw new Error('Agent.runTyped: run paused — typed mode does not support pauses. ' +
1145
1151
  'Use agent.run() + agent.parseOutput(...) after resume.');
1146
1152
  }
1153
+ if (this.answerValidationConfig !== undefined) {
1154
+ // The validator judged the schema's JSON output. Do not run a transforming
1155
+ // or stateful parser again and hand back a value the validator never saw.
1156
+ if (this.answerValidation()?.schemaAccepted !== true) {
1157
+ throw new OutputSchemaError('Answer validation could not establish a JSON schema result.', {
1158
+ rawOutput: out,
1159
+ stage: 'schema-validate',
1160
+ });
1161
+ }
1162
+ return JSON.parse(out);
1163
+ }
1147
1164
  return this.parseOutputAsync(out);
1148
1165
  }
1149
1166
  /**
@@ -1306,6 +1323,7 @@ export class Agent extends RunnerBase {
1306
1323
  // named values one `.cause` deep, where the person deciding what to
1307
1324
  // do about them will not look.
1308
1325
  cause instanceof UnsupportedValuesError ||
1326
+ cause instanceof AnswerValidationError ||
1309
1327
  // 9.60.0 — a dead checker is a WIRING verdict on this build, not a
1310
1328
  // recoverable run state: resuming would run the same dead wiring.
1311
1329
  cause.name === 'CheckerDeadError');
@@ -1334,7 +1352,7 @@ export class Agent extends RunnerBase {
1334
1352
  this.conversationOwner(),
1335
1353
  // …and the same graph cursor (SG-C), from the same snapshot reader —
1336
1354
  // one reader, two carriers, so neither can lose what the other keeps.
1337
- this.continuityCursorOf(this.getLastSnapshot()?.sharedState));
1355
+ this.continuityCursorOf(this.getLastSnapshot()?.sharedState), this.evidenceRecoveryOf(this.getLastSnapshot()?.sharedState));
1338
1356
  throw new RunCheckpointError(cause, checkpoint);
1339
1357
  }
1340
1358
  throw cause;
@@ -1356,6 +1374,7 @@ export class Agent extends RunnerBase {
1356
1374
  this.pendingResumeHistory = undefined;
1357
1375
  this.pendingResumeFolded = undefined;
1358
1376
  this.pendingResumeSkillCursor = undefined;
1377
+ this.pendingEvidenceRecovery = undefined;
1359
1378
  }
1360
1379
  }
1361
1380
  /**
@@ -1724,6 +1743,7 @@ export class Agent extends RunnerBase {
1724
1743
  const folded = this.foldedSpansOf(state);
1725
1744
  const owner = this.conversationOwner();
1726
1745
  const skillCursor = this.continuityCursorOf(state);
1746
+ const evidenceRecovery = this.evidenceRecoveryOf(state);
1727
1747
  return {
1728
1748
  version: 1,
1729
1749
  runId: this.currentRunContext.runId,
@@ -1742,6 +1762,20 @@ export class Agent extends RunnerBase {
1742
1762
  // `continuity: 'conversation'`, so every other checkpoint keeps its
1743
1763
  // exact byte shape.
1744
1764
  ...(skillCursor !== undefined && { skillCursor }),
1765
+ ...(evidenceRecovery !== undefined && { evidenceRecovery }),
1766
+ };
1767
+ }
1768
+ /** Both checkpoint doors keep the repair budget separately from conversation text. */
1769
+ evidenceRecoveryOf(state) {
1770
+ if (state?.evidenceRevisionSpent !== true)
1771
+ return undefined;
1772
+ const pending = state.evidenceRecovery;
1773
+ return {
1774
+ revisionSpent: true,
1775
+ ...(pending !== undefined &&
1776
+ state.evidenceRecoveryUsed !== true && {
1777
+ pending: { instruction: pending.instruction },
1778
+ }),
1745
1779
  };
1746
1780
  }
1747
1781
  /**
@@ -1834,6 +1868,12 @@ export class Agent extends RunnerBase {
1834
1868
  // continuity graph and continued on a `'turn'` one is consumed and
1835
1869
  // ignored, exactly like a `folded` field on an agent that never folds.
1836
1870
  this.pendingResumeSkillCursor = cp.skillCursor;
1871
+ // Same failed request retains its single repair budget. A new user turn
1872
+ // receives neither the rejected draft nor a spent retry allowance.
1873
+ this.pendingEvidenceRecovery =
1874
+ appendMessage === undefined && cp.evidenceRecovery !== undefined
1875
+ ? structuredClone(cp.evidenceRecovery)
1876
+ : undefined;
1837
1877
  }
1838
1878
  /** One turn at a time — see `RunInFlightError`. @internal */
1839
1879
  assertNotRunning(door) {
@@ -2717,6 +2757,13 @@ export class Agent extends RunnerBase {
2717
2757
  const state = this.getLastSnapshot()?.sharedState;
2718
2758
  return state?.unsupportedValues;
2719
2759
  }
2760
+ /** The last run's answer checks, detached from its execution record.
2761
+ * Undefined means no terminal validation ran, never an implicit pass. */
2762
+ answerValidation() {
2763
+ const report = this.getLastSnapshot()?.sharedState
2764
+ ?.answerValidation;
2765
+ return report === undefined ? undefined : structuredClone(report);
2766
+ }
2720
2767
  finalizeResult(executor, result) {
2721
2768
  const paused = this.detectPause(executor, result);
2722
2769
  if (paused)
@@ -2844,6 +2891,32 @@ export class Agent extends RunnerBase {
2844
2891
  }
2845
2892
  if (result instanceof Error)
2846
2893
  throw result;
2894
+ if (this.answerValidationConfig !== undefined) {
2895
+ const state = executor.getSnapshot().sharedState;
2896
+ if (state.answerValidationBlocked === true && state.answerValidation !== undefined) {
2897
+ throw new AnswerValidationError(state.answerValidation);
2898
+ }
2899
+ if (state.answerValidation === undefined ||
2900
+ state.answerValidationCommitted !== true ||
2901
+ typeof state.finalContent !== 'string') {
2902
+ const config = this.answerValidationConfig;
2903
+ throw new AnswerValidationError({
2904
+ validatorId: config.id,
2905
+ validatorVersion: config.version,
2906
+ mode: config.mode,
2907
+ status: 'unverified',
2908
+ checked: 0,
2909
+ failed: 0,
2910
+ unreachable: 0,
2911
+ notApplicable: 0,
2912
+ checks: [],
2913
+ resolvedRefs: [],
2914
+ schemaAccepted: false,
2915
+ reason: 'delivery-incomplete',
2916
+ });
2917
+ }
2918
+ return state.finalContent;
2919
+ }
2847
2920
  if (typeof result === 'string')
2848
2921
  return result;
2849
2922
  throw new Error('Agent: unexpected result shape — expected final-answer string');
@@ -2923,6 +2996,14 @@ export class Agent extends RunnerBase {
2923
2996
  this.pendingResumeHistory = undefined;
2924
2997
  return h;
2925
2998
  },
2999
+ ...(this.evidenceGate !== undefined &&
3000
+ this.evidenceGate.posture !== 'assist' && {
3001
+ consumePendingEvidenceRecovery: () => {
3002
+ const recovery = this.pendingEvidenceRecovery;
3003
+ this.pendingEvidenceRecovery = undefined;
3004
+ return recovery;
3005
+ },
3006
+ }),
2926
3007
  consumePendingResumeFolded: () => {
2927
3008
  const f = this.pendingResumeFolded;
2928
3009
  this.pendingResumeFolded = undefined;
@@ -3254,6 +3335,11 @@ export class Agent extends RunnerBase {
3254
3335
  // callLLM extracted to ./agent/stages/callLLM.ts (v2.11.2). Same
3255
3336
  // late-binding pattern as seed for toolSchemas (computed below).
3256
3337
  const callLLM = buildCallLLMStage({
3338
+ ...(this.evidenceGate !== undefined &&
3339
+ this.evidenceGate.posture !== 'assist' && {
3340
+ hasEvidenceRecovery: true,
3341
+ }),
3342
+ ...(this.answerValidationConfig !== undefined && { suppressDraftTokens: true }),
3257
3343
  // The receipt's salt (9.88.0) — read per call, like seed's own accessor.
3258
3344
  getRunId: () => this.currentRunContext?.runId,
3259
3345
  // …and its off switch. Value-conditional, so an agent on the default
@@ -3381,13 +3467,16 @@ export class Agent extends RunnerBase {
3381
3467
  // question a build-time mount can answer.
3382
3468
  const canCallTools = registryByName.size > 0 || this.externalToolProvider !== undefined;
3383
3469
  const hasWrapUp = canCallTools && this.wrapUpAtMaxIterations !== false;
3384
- const routeDecider = buildRouteDeciderStage(this.messageMiddleware, this.outputEnforcement, stepPlanFor, this.evidenceGate, hasWrapUp, this.claimContract, this.integrityLedgerHolder,
3470
+ const baseRouteDecider = buildRouteDeciderStage(this.messageMiddleware, this.outputEnforcement, stepPlanFor, this.evidenceGate, hasWrapUp, this.claimContract, this.integrityLedgerHolder,
3385
3471
  // THE CLAIM SEAM'S RECENCY READ (9.83.0). Value-conditional on both
3386
3472
  // halves, so an agent that armed neither hands the decider builder
3387
3473
  // exactly the arguments it always did — and `buildRouteDeciderStage`'s
3388
3474
  // no-judge fast path still returns the very function reference every
3389
3475
  // pre-9.83.0 chart was given.
3390
3476
  this.noticePriorTurnEvidence && this.evidenceGate !== undefined ? true : undefined);
3477
+ const routeDecider = this.answerValidationConfig === undefined
3478
+ ? baseRouteDecider
3479
+ : withAnswerValidation(baseRouteDecider, this.answerValidationConfig, this.outputSchemaParser, artifactStore, () => this.consentOutstanding.size > 0);
3391
3480
  // toolCallsHandler extracted to ./agent/stages/toolCalls.ts (v2.11.2).
3392
3481
  const toolCallsHandler = buildToolCallsHandler({
3393
3482
  registryByName,
@@ -3595,6 +3684,7 @@ export class Agent extends RunnerBase {
3595
3684
  // agent that did not ask, so both builders mount the final-branch stage
3596
3685
  // function they have always mounted.
3597
3686
  ...(this.limitsTravelWithTheAnswerValue && { attachCoverageLimits: true }),
3687
+ ...(this.answerValidationConfig !== undefined && { hasAnswerValidation: true }),
3598
3688
  // The out-of-budget wrap-up branch (9.56.0) — the conditional-mount law
3599
3689
  // above, decided once beside the Route decider that routes to it so the
3600
3690
  // two can never disagree about whether the branch exists.