@riddledc/riddle-proof 0.8.4 → 0.8.6

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 (41) hide show
  1. package/dist/adapters/codex-exec-agent.cjs +1 -0
  2. package/dist/adapters/codex-exec-agent.js +1 -1
  3. package/dist/adapters/codex.cjs +1 -0
  4. package/dist/adapters/codex.js +1 -1
  5. package/dist/adapters/local-agent.cjs +1 -0
  6. package/dist/adapters/local-agent.js +1 -1
  7. package/dist/advanced/engine-harness.cjs +1 -1
  8. package/dist/advanced/engine-harness.js +1 -1
  9. package/dist/advanced/index.cjs +1 -1
  10. package/dist/advanced/index.d.cts +1 -1
  11. package/dist/advanced/index.d.ts +1 -1
  12. package/dist/advanced/index.js +2 -2
  13. package/dist/advanced/proof-run-engine.cjs +1 -1
  14. package/dist/advanced/proof-run-engine.d.cts +1 -1
  15. package/dist/advanced/proof-run-engine.d.ts +1 -1
  16. package/dist/advanced/proof-run-engine.js +1 -1
  17. package/dist/{chunk-7F5LNUGR.js → chunk-5MILMRQY.js} +1 -0
  18. package/dist/{chunk-P22V26PS.js → chunk-GMZ57RRY.js} +1 -1
  19. package/dist/{chunk-LZFCIHDT.js → chunk-NAFJ4KSF.js} +2 -2
  20. package/dist/cli/index.js +3 -3
  21. package/dist/cli.cjs +2 -1
  22. package/dist/cli.js +3 -3
  23. package/dist/codex-exec-agent.cjs +1 -0
  24. package/dist/codex-exec-agent.js +1 -1
  25. package/dist/engine-harness.cjs +1 -1
  26. package/dist/engine-harness.js +1 -1
  27. package/dist/index.cjs +2 -1
  28. package/dist/index.js +2 -2
  29. package/dist/local-agent.cjs +1 -0
  30. package/dist/local-agent.js +1 -1
  31. package/dist/{proof-run-engine-B7DCPzpK.d.cts → proof-run-engine-BO1h0Bmy.d.cts} +3 -3
  32. package/dist/{proof-run-engine-BomAcXhA.d.ts → proof-run-engine-CIdpWNh6.d.ts} +3 -3
  33. package/dist/proof-run-engine.cjs +1 -1
  34. package/dist/proof-run-engine.d.cts +1 -1
  35. package/dist/proof-run-engine.d.ts +1 -1
  36. package/dist/proof-run-engine.js +1 -1
  37. package/package.json +1 -1
  38. package/runtime/lib/author.py +1 -0
  39. package/runtime/lib/verify.py +116 -9
  40. package/runtime/tests/recon_verify_smoke.py +107 -0
  41. /package/dist/{chunk-IP64JLLR.js → chunk-BDFSMWTI.js} +0 -0
@@ -649,6 +649,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
649
649
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
650
650
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
651
651
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
652
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
652
653
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
653
654
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
654
655
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -3,7 +3,7 @@ import {
3
3
  createCodexExecAgentAdapter,
4
4
  createCodexExecJsonRunner,
5
5
  runCodexExecAgentDoctor
6
- } from "../chunk-7F5LNUGR.js";
6
+ } from "../chunk-5MILMRQY.js";
7
7
  import "../chunk-VY4Y5U57.js";
8
8
  import "../chunk-MLKGABMK.js";
9
9
  export {
@@ -649,6 +649,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
649
649
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
650
650
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
651
651
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
652
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
652
653
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
653
654
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
654
655
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -3,7 +3,7 @@ import {
3
3
  createCodexExecAgentAdapter,
4
4
  createCodexExecJsonRunner,
5
5
  runCodexExecAgentDoctor
6
- } from "../chunk-7F5LNUGR.js";
6
+ } from "../chunk-5MILMRQY.js";
7
7
  import "../chunk-VY4Y5U57.js";
8
8
  import "../chunk-MLKGABMK.js";
9
9
  export {
@@ -649,6 +649,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
649
649
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
650
650
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
651
651
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
652
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
652
653
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
653
654
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
654
655
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -3,7 +3,7 @@ import {
3
3
  createCodexExecAgentAdapter,
4
4
  createCodexExecJsonRunner,
5
5
  runCodexExecAgentDoctor
6
- } from "../chunk-7F5LNUGR.js";
6
+ } from "../chunk-5MILMRQY.js";
7
7
  import "../chunk-VY4Y5U57.js";
8
8
  import "../chunk-MLKGABMK.js";
9
9
  export {
@@ -2465,7 +2465,7 @@ ${implementRes.stderr || ""}`;
2465
2465
  state = readState(config.statePath);
2466
2466
  }
2467
2467
  const checkpointName = "verify_capture_retry";
2468
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2468
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2469
2469
  recordAttempt("verify", "checkpoint", summary, {
2470
2470
  autoApproved: verifyRes.autoApproved || false,
2471
2471
  checkpoint: checkpointName,
@@ -2,7 +2,7 @@ import {
2
2
  createDisabledRiddleProofAgentAdapter,
3
3
  readRiddleProofRunStatus,
4
4
  runRiddleProofEngineHarness
5
- } from "../chunk-IP64JLLR.js";
5
+ } from "../chunk-BDFSMWTI.js";
6
6
  import "../chunk-YZUVEJ5B.js";
7
7
  import "../chunk-FMOYUYH2.js";
8
8
  import "../chunk-RV6LK7HU.js";
@@ -2495,7 +2495,7 @@ ${implementRes.stderr || ""}`;
2495
2495
  state = readState(config.statePath);
2496
2496
  }
2497
2497
  const checkpointName = "verify_capture_retry";
2498
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2498
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2499
2499
  recordAttempt("verify", "checkpoint", summary, {
2500
2500
  autoApproved: verifyRes.autoApproved || false,
2501
2501
  checkpoint: checkpointName,
@@ -1,5 +1,5 @@
1
1
  export { b as runner } from '../runner-4LJ5z0D-.cjs';
2
2
  export { l as engineHarness } from '../engine-harness-LBfqbFSe.cjs';
3
3
  export { p as proofRunCore } from '../proof-run-core-CE0jx7wL.cjs';
4
- export { p as proofRunEngine } from '../proof-run-engine-B7DCPzpK.cjs';
4
+ export { p as proofRunEngine } from '../proof-run-engine-BO1h0Bmy.cjs';
5
5
  import '../types.cjs';
@@ -1,5 +1,5 @@
1
1
  export { b as runner } from '../runner-BdQpOkZD.js';
2
2
  export { l as engineHarness } from '../engine-harness-CMACHP6A.js';
3
3
  export { p as proofRunCore } from '../proof-run-core-CE0jx7wL.js';
4
- export { p as proofRunEngine } from '../proof-run-engine-BomAcXhA.js';
4
+ export { p as proofRunEngine } from '../proof-run-engine-CIdpWNh6.js';
5
5
  import '../types.js';
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  proof_run_engine_exports
3
- } from "../chunk-P22V26PS.js";
3
+ } from "../chunk-GMZ57RRY.js";
4
4
  import {
5
5
  runner_exports
6
6
  } from "../chunk-UIJ7X63P.js";
7
7
  import {
8
8
  engine_harness_exports
9
- } from "../chunk-IP64JLLR.js";
9
+ } from "../chunk-BDFSMWTI.js";
10
10
  import "../chunk-YZUVEJ5B.js";
11
11
  import "../chunk-FMOYUYH2.js";
12
12
  import {
@@ -2465,7 +2465,7 @@ ${implementRes.stderr || ""}`;
2465
2465
  state = readState(config.statePath);
2466
2466
  }
2467
2467
  const checkpointName = "verify_capture_retry";
2468
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2468
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2469
2469
  recordAttempt("verify", "checkpoint", summary, {
2470
2470
  autoApproved: verifyRes.autoApproved || false,
2471
2471
  checkpoint: checkpointName,
@@ -1,2 +1,2 @@
1
- export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from '../proof-run-engine-B7DCPzpK.cjs';
1
+ export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from '../proof-run-engine-BO1h0Bmy.cjs';
2
2
  import '../proof-run-core-CE0jx7wL.cjs';
@@ -1,2 +1,2 @@
1
- export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from '../proof-run-engine-BomAcXhA.js';
1
+ export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from '../proof-run-engine-CIdpWNh6.js';
2
2
  import '../proof-run-core-CE0jx7wL.js';
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  createRiddleProofEngine,
3
3
  executeWorkflow
4
- } from "../chunk-P22V26PS.js";
4
+ } from "../chunk-GMZ57RRY.js";
5
5
  import "../chunk-RV6LK7HU.js";
6
6
  import "../chunk-MLKGABMK.js";
7
7
  export {
@@ -608,6 +608,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
608
608
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
609
609
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
610
610
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
611
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
611
612
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
612
613
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
613
614
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -1447,7 +1447,7 @@ ${implementRes.stderr || ""}`;
1447
1447
  state = readState(config.statePath);
1448
1448
  }
1449
1449
  const checkpointName = "verify_capture_retry";
1450
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
1450
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
1451
1451
  recordAttempt("verify", "checkpoint", summary, {
1452
1452
  autoApproved: verifyRes.autoApproved || false,
1453
1453
  checkpoint: checkpointName,
@@ -22,14 +22,14 @@ import {
22
22
  createDisabledRiddleProofAgentAdapter,
23
23
  readRiddleProofRunStatus,
24
24
  runRiddleProofEngineHarness
25
- } from "./chunk-IP64JLLR.js";
25
+ } from "./chunk-BDFSMWTI.js";
26
26
  import {
27
27
  createCheckpointResponseTemplate
28
28
  } from "./chunk-4FOHZ7JG.js";
29
29
  import {
30
30
  createCodexExecAgentAdapter,
31
31
  runCodexExecAgentDoctor
32
- } from "./chunk-7F5LNUGR.js";
32
+ } from "./chunk-5MILMRQY.js";
33
33
 
34
34
  // src/cli.ts
35
35
  import { existsSync, mkdirSync, readdirSync, readFileSync, statSync, writeFileSync } from "fs";
package/dist/cli/index.js CHANGED
@@ -1,12 +1,12 @@
1
- import "../chunk-LZFCIHDT.js";
1
+ import "../chunk-NAFJ4KSF.js";
2
2
  import "../chunk-PEWAIEER.js";
3
3
  import "../chunk-TWTEUS7R.js";
4
- import "../chunk-IP64JLLR.js";
4
+ import "../chunk-BDFSMWTI.js";
5
5
  import "../chunk-YZUVEJ5B.js";
6
6
  import "../chunk-FMOYUYH2.js";
7
7
  import "../chunk-RV6LK7HU.js";
8
8
  import "../chunk-4FOHZ7JG.js";
9
9
  import "../chunk-JFQXAJH2.js";
10
- import "../chunk-7F5LNUGR.js";
10
+ import "../chunk-5MILMRQY.js";
11
11
  import "../chunk-VY4Y5U57.js";
12
12
  import "../chunk-MLKGABMK.js";
package/dist/cli.cjs CHANGED
@@ -2465,7 +2465,7 @@ ${implementRes.stderr || ""}`;
2465
2465
  state = readState(config.statePath);
2466
2466
  }
2467
2467
  const checkpointName = "verify_capture_retry";
2468
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2468
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2469
2469
  recordAttempt("verify", "checkpoint", summary, {
2470
2470
  autoApproved: verifyRes.autoApproved || false,
2471
2471
  checkpoint: checkpointName,
@@ -6412,6 +6412,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
6412
6412
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
6413
6413
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
6414
6414
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
6415
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
6415
6416
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
6416
6417
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
6417
6418
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
package/dist/cli.js CHANGED
@@ -1,13 +1,13 @@
1
1
  #!/usr/bin/env node
2
- import "./chunk-LZFCIHDT.js";
2
+ import "./chunk-NAFJ4KSF.js";
3
3
  import "./chunk-PEWAIEER.js";
4
4
  import "./chunk-TWTEUS7R.js";
5
- import "./chunk-IP64JLLR.js";
5
+ import "./chunk-BDFSMWTI.js";
6
6
  import "./chunk-YZUVEJ5B.js";
7
7
  import "./chunk-FMOYUYH2.js";
8
8
  import "./chunk-RV6LK7HU.js";
9
9
  import "./chunk-4FOHZ7JG.js";
10
10
  import "./chunk-JFQXAJH2.js";
11
- import "./chunk-7F5LNUGR.js";
11
+ import "./chunk-5MILMRQY.js";
12
12
  import "./chunk-VY4Y5U57.js";
13
13
  import "./chunk-MLKGABMK.js";
@@ -647,6 +647,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
647
647
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
648
648
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
649
649
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
650
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
650
651
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
651
652
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
652
653
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -2,7 +2,7 @@ import {
2
2
  createCodexExecAgentAdapter,
3
3
  createCodexExecJsonRunner,
4
4
  runCodexExecAgentDoctor
5
- } from "./chunk-7F5LNUGR.js";
5
+ } from "./chunk-5MILMRQY.js";
6
6
  import "./chunk-VY4Y5U57.js";
7
7
  import "./chunk-MLKGABMK.js";
8
8
  export {
@@ -2465,7 +2465,7 @@ ${implementRes.stderr || ""}`;
2465
2465
  state = readState(config.statePath);
2466
2466
  }
2467
2467
  const checkpointName = "verify_capture_retry";
2468
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2468
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2469
2469
  recordAttempt("verify", "checkpoint", summary, {
2470
2470
  autoApproved: verifyRes.autoApproved || false,
2471
2471
  checkpoint: checkpointName,
@@ -2,7 +2,7 @@ import {
2
2
  createDisabledRiddleProofAgentAdapter,
3
3
  readRiddleProofRunStatus,
4
4
  runRiddleProofEngineHarness
5
- } from "./chunk-IP64JLLR.js";
5
+ } from "./chunk-BDFSMWTI.js";
6
6
  import "./chunk-YZUVEJ5B.js";
7
7
  import "./chunk-FMOYUYH2.js";
8
8
  import "./chunk-RV6LK7HU.js";
package/dist/index.cjs CHANGED
@@ -2465,7 +2465,7 @@ ${implementRes.stderr || ""}`;
2465
2465
  state = readState(config.statePath);
2466
2466
  }
2467
2467
  const checkpointName = "verify_capture_retry";
2468
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2468
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2469
2469
  recordAttempt("verify", "checkpoint", summary, {
2470
2470
  autoApproved: verifyRes.autoApproved || false,
2471
2471
  checkpoint: checkpointName,
@@ -7075,6 +7075,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
7075
7075
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
7076
7076
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
7077
7077
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
7078
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
7078
7079
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
7079
7080
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
7080
7081
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
package/dist/index.js CHANGED
@@ -95,7 +95,7 @@ import {
95
95
  createDisabledRiddleProofAgentAdapter,
96
96
  readRiddleProofRunStatus,
97
97
  runRiddleProofEngineHarness
98
- } from "./chunk-IP64JLLR.js";
98
+ } from "./chunk-BDFSMWTI.js";
99
99
  import {
100
100
  RIDDLE_PROOF_RUN_STATE_VERSION,
101
101
  appendRunEvent,
@@ -134,7 +134,7 @@ import {
134
134
  createCodexExecAgentAdapter,
135
135
  createCodexExecJsonRunner,
136
136
  runCodexExecAgentDoctor
137
- } from "./chunk-7F5LNUGR.js";
137
+ } from "./chunk-5MILMRQY.js";
138
138
  import {
139
139
  applyTerminalMetadata,
140
140
  compactRecord,
@@ -649,6 +649,7 @@ function createCodexExecAgentAdapter(config = {}, runner = createCodexExecJsonRu
649
649
  "Use the recon-approved route and baseline context; make the plan name the concrete target, expected before state, expected after state, and stop condition.",
650
650
  "Choose the evidence modality from verification_mode and success_criteria: screenshots for visual/UI proof, interactions plus screenshots for interaction proof, structured metrics/logs/JSON/audio analysis for non-visual proof.",
651
651
  "For playable/gameplay proof, treat screenshots as supporting artifacts only: start the game, send keyboard or pointer input, measure state before/after, measure non-HUD canvas/playfield pixel deltas across time, and return playability evidence with version riddle-proof.playability.v1.",
652
+ "For interaction proof, return a structured evidence object with start route/state, terminal route/state, action, assertions, and matched UI text. Catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.",
652
653
  "For structured proof, collect meaningful measurements inside page.evaluate, assign them to an evidence variable, and return that object from capture_script. Screenshots are optional supporting context for data/audio/log/metric/custom modes.",
653
654
  "Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.",
654
655
  "Do not call Playwright page.* APIs inside page.evaluate; page.evaluate runs in the browser page, while page.waitForFunction, page.waitForSelector, page.click, and saveScreenshot belong in the outer capture script.",
@@ -3,7 +3,7 @@ import {
3
3
  createCodexExecAgentAdapter,
4
4
  createCodexExecJsonRunner,
5
5
  runCodexExecAgentDoctor
6
- } from "./chunk-7F5LNUGR.js";
6
+ } from "./chunk-5MILMRQY.js";
7
7
  import "./chunk-VY4Y5U57.js";
8
8
  import "./chunk-MLKGABMK.js";
9
9
  export {
@@ -292,7 +292,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
292
292
  blocking?: boolean;
293
293
  details?: Record<string, unknown>;
294
294
  ok: boolean;
295
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
295
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship" | "run";
296
296
  state_path: string;
297
297
  stage: any;
298
298
  summary: string;
@@ -382,7 +382,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
382
382
  continueWithStage?: WorkflowStage | null;
383
383
  blocking?: boolean;
384
384
  details?: Record<string, unknown>;
385
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
385
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship" | "run";
386
386
  state_path: string;
387
387
  stage: any;
388
388
  checkpoint: string;
@@ -659,7 +659,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
659
659
  error?: undefined;
660
660
  } | {
661
661
  ok: boolean;
662
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup";
662
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship";
663
663
  state_path: string;
664
664
  stage: any;
665
665
  summary: string;
@@ -292,7 +292,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
292
292
  blocking?: boolean;
293
293
  details?: Record<string, unknown>;
294
294
  ok: boolean;
295
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
295
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship" | "run";
296
296
  state_path: string;
297
297
  stage: any;
298
298
  summary: string;
@@ -382,7 +382,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
382
382
  continueWithStage?: WorkflowStage | null;
383
383
  blocking?: boolean;
384
384
  details?: Record<string, unknown>;
385
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
385
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship" | "run";
386
386
  state_path: string;
387
387
  stage: any;
388
388
  checkpoint: string;
@@ -659,7 +659,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
659
659
  error?: undefined;
660
660
  } | {
661
661
  ok: boolean;
662
- action: "author" | "recon" | "ship" | "implement" | "verify" | "setup";
662
+ action: "setup" | "recon" | "author" | "implement" | "verify" | "ship";
663
663
  state_path: string;
664
664
  stage: any;
665
665
  summary: string;
@@ -2463,7 +2463,7 @@ ${implementRes.stderr || ""}`;
2463
2463
  state = readState(config.statePath);
2464
2464
  }
2465
2465
  const checkpointName = "verify_capture_retry";
2466
- const summary = "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2466
+ const summary = stringValue(proofAssessment.summary) || "Verify ran, but the proof packet still needs internal capture-plan work before it should ship.";
2467
2467
  recordAttempt("verify", "checkpoint", summary, {
2468
2468
  autoApproved: verifyRes.autoApproved || false,
2469
2469
  checkpoint: checkpointName,
@@ -1,2 +1,2 @@
1
1
  import './proof-run-core-CE0jx7wL.cjs';
2
- export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from './proof-run-engine-B7DCPzpK.cjs';
2
+ export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from './proof-run-engine-BO1h0Bmy.cjs';
@@ -1,2 +1,2 @@
1
1
  import './proof-run-core-CE0jx7wL.js';
2
- export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from './proof-run-engine-BomAcXhA.js';
2
+ export { R as RiddleProofEngine, c as createRiddleProofEngine, e as executeWorkflow } from './proof-run-engine-CIdpWNh6.js';
@@ -1,7 +1,7 @@
1
1
  import {
2
2
  createRiddleProofEngine,
3
3
  executeWorkflow
4
- } from "./chunk-P22V26PS.js";
4
+ } from "./chunk-GMZ57RRY.js";
5
5
  import "./chunk-RV6LK7HU.js";
6
6
  import "./chunk-MLKGABMK.js";
7
7
  export {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@riddledc/riddle-proof",
3
- "version": "0.8.4",
3
+ "version": "0.8.6",
4
4
  "description": "Reusable Riddle Proof contracts and helpers for evidence-backed agent changes.",
5
5
  "license": "MIT",
6
6
  "author": "RiddleDC",
@@ -158,6 +158,7 @@ def author_request_payload(state, reference, baselines, current_plan, hypothesis
158
158
  'Keep capture_script concise Playwright statements.',
159
159
  'For visual/UI proof, include saveScreenshot(\'after-proof\') exactly once.',
160
160
  'For interaction proof, preserve the interaction contract and name the expected terminal route/state separately from the initial route.',
161
+ 'For interaction proof, return a JSON-serializable evidence object with start route/state, terminal route/state, action, assertions, and matched UI text; catch waitForURL or selector timeouts and record them as failed assertions instead of throwing before evidence is emitted.',
161
162
  'For playable/gameplay proof, start the experience, send keyboard or pointer input, sample state before/after, measure non-HUD playfield/canvas pixel deltas across time, and return a JSON-serializable evidence object with playability or playability_evidence version riddle-proof.playability.v1.',
162
163
  'For data/audio/log/metric/custom proof, screenshots are optional; collect measurements inside page.evaluate, assign the result to an evidence variable, and return that evidence object from capture_script.',
163
164
  'Do not assign globalThis.__riddleProofEvidence, window.__riddleProofEvidence, or self.__riddleProofEvidence in the worker context. Avoid global evidence assignment unless it is inside page.evaluate for compatibility with older packets.',
@@ -558,6 +558,83 @@ def extract_proof_evidence(payload):
558
558
  return evidence
559
559
 
560
560
 
561
+ def attach_interaction_capture_failure_evidence(state, payload, expected_path, after_observation):
562
+ if not isinstance(payload, dict):
563
+ return payload, None
564
+ mode = normalized_verification_mode(state.get('verification_mode'))
565
+ if mode not in INTERACTION_MODES:
566
+ return payload, None
567
+ if extract_proof_evidence(payload) is not None:
568
+ return payload, None
569
+
570
+ details = after_observation.get('details') if isinstance(after_observation, dict) else {}
571
+ if not isinstance(details, dict):
572
+ details = {}
573
+ expected = normalize_observed_path(expected_path)
574
+ observed_raw = str(details.get('observed_path_raw') or details.get('observed_path') or '').strip()
575
+ observed = normalize_observed_path(observed_raw)
576
+ route_matches = route_matches_expected(expected, observed_raw or observed) if expected and (observed_raw or observed) else None
577
+ error_messages = [
578
+ str(item).strip()
579
+ for item in (details.get('capture_error_messages') or [])
580
+ if str(item).strip()
581
+ ]
582
+ if route_matches is not False and not error_messages:
583
+ return payload, None
584
+
585
+ route_expectation = state.get('route_expectation') if isinstance(state.get('route_expectation'), dict) else {}
586
+ expected_parts = route_parts(expected)
587
+ observed_parts = route_parts(observed_raw or observed)
588
+ evidence = {
589
+ 'version': 'riddle-proof.interaction.capture-failure.v1',
590
+ 'synthetic': True,
591
+ 'source': 'verify_capture_failure',
592
+ 'mode': mode,
593
+ 'passed': False,
594
+ 'proofReady': False,
595
+ 'authored_proof_evidence_present': False,
596
+ 'evidence_summary': 'Interaction capture failed before the authored script emitted structured proof evidence.',
597
+ 'expected': {
598
+ 'path': expected,
599
+ 'pathname': expected_parts.get('pathname') or '',
600
+ 'query': expected_parts.get('query') or '',
601
+ 'hash': expected_parts.get('hash') or '',
602
+ },
603
+ 'observed': {
604
+ 'path': observed,
605
+ 'raw_path': observed_raw,
606
+ 'pathname': observed_parts.get('pathname') or '',
607
+ 'query': observed_parts.get('query') or '',
608
+ 'hash': observed_parts.get('hash') or '',
609
+ },
610
+ 'checks': {
611
+ 'scriptCompleted': len(error_messages) == 0,
612
+ 'routeMatches': bool(route_matches),
613
+ 'authoredEvidenceReturned': False,
614
+ },
615
+ 'route_expectation_source': route_expectation.get('source') or '',
616
+ }
617
+ if error_messages:
618
+ evidence['capture_error'] = error_messages[0][:1000]
619
+ if route_matches is False:
620
+ evidence['evidence_summary'] = (
621
+ 'Interaction capture reached a different terminal route than expected before authored proof evidence was emitted.'
622
+ )
623
+
624
+ enriched = enrich_capture_payload(payload)
625
+ patched = dict(enriched)
626
+ result = dict(patched.get('result') or {})
627
+ result['proofEvidence'] = evidence
628
+ patched['result'] = result
629
+ console = list(patched.get('console') or [])
630
+ try:
631
+ console.append(PROOF_EVIDENCE_PREFIX + json.dumps(evidence, sort_keys=True))
632
+ except Exception:
633
+ pass
634
+ patched['console'] = console
635
+ return patched, evidence
636
+
637
+
561
638
  def proof_evidence_records(value):
562
639
  if isinstance(value, dict):
563
640
  return [value]
@@ -2442,7 +2519,7 @@ def evaluate_capture_quality(payload, expected_path, verification_mode='proof'):
2442
2519
  }
2443
2520
 
2444
2521
 
2445
- def build_capture_retry_decision(after_observation, required_baseline_present, proof_evidence_blocker=''):
2522
+ def build_capture_retry_decision(after_observation, required_baseline_present, proof_evidence_blocker='', route_expectation=None):
2446
2523
  reasons = []
2447
2524
  if not required_baseline_present:
2448
2525
  reasons.append('Recon baseline is missing, so verify should return to recon instead of guessing a new reference context.')
@@ -2455,6 +2532,7 @@ def build_capture_retry_decision(after_observation, required_baseline_present, p
2455
2532
  }
2456
2533
 
2457
2534
  details = after_observation.get('details') if isinstance(after_observation.get('details'), dict) else {}
2535
+ route_expectation = route_expectation if isinstance(route_expectation, dict) else {}
2458
2536
  route_mismatch = None
2459
2537
  reason_text = str(after_observation.get('reason') or '')
2460
2538
  if 'wrong route' in reason_text:
@@ -2466,6 +2544,11 @@ def build_capture_retry_decision(after_observation, required_baseline_present, p
2466
2544
  'expected_path': expected,
2467
2545
  'observed_after_path': observed,
2468
2546
  }
2547
+ error_messages = [
2548
+ str(item).strip()
2549
+ for item in (details.get('capture_error_messages') or [])
2550
+ if str(item).strip()
2551
+ ]
2469
2552
 
2470
2553
  if proof_evidence_blocker:
2471
2554
  reasons.append(proof_evidence_blocker)
@@ -2493,6 +2576,9 @@ def build_capture_retry_decision(after_observation, required_baseline_present, p
2493
2576
  (route_mismatch.get('observed_after_path') or '(unknown)') +
2494
2577
  '.'
2495
2578
  )
2579
+ if error_messages:
2580
+ reasons.append('Capture script error: ' + error_messages[0][:500])
2581
+ summary += ' Capture script error: ' + error_messages[0][:300]
2496
2582
  return {
2497
2583
  'decision': decision,
2498
2584
  'summary': summary,
@@ -2504,12 +2590,14 @@ def build_capture_retry_decision(after_observation, required_baseline_present, p
2504
2590
 
2505
2591
  reason = after_observation.get('reason') or 'after capture is not usable yet'
2506
2592
  reasons.append('The after evidence is not usable yet: ' + reason)
2507
- recommended_stage = 'recon' if 'wrong route' in reason else 'author'
2508
- error_messages = [
2509
- str(item).strip()
2510
- for item in (details.get('capture_error_messages') or [])
2511
- if str(item).strip()
2512
- ]
2593
+ route_expectation_source = str(route_expectation.get('source') or '')
2594
+ authored_terminal_route = bool(
2595
+ route_mismatch
2596
+ and route_expectation.get('mode') in INTERACTION_MODES
2597
+ and route_expectation.get('terminal_path')
2598
+ and route_expectation_source != 'recon_start_path'
2599
+ )
2600
+ recommended_stage = 'recon' if 'wrong route' in reason and not authored_terminal_route else 'author'
2513
2601
  mismatch = None
2514
2602
  if recommended_stage == 'recon':
2515
2603
  expected = details.get('expected_path') or ''
@@ -2526,7 +2614,17 @@ def build_capture_retry_decision(after_observation, required_baseline_present, p
2526
2614
  summary = 'Verify capture route mismatch needs recon to refresh the reference path.'
2527
2615
  reasons.append('The capture appears to be on the wrong route or baseline context, so recon should refresh the reference path.')
2528
2616
  else:
2529
- if error_messages:
2617
+ if route_mismatch:
2618
+ expected = route_mismatch.get('expected_path') or ''
2619
+ observed = route_mismatch.get('observed_after_path') or ''
2620
+ mismatch = route_mismatch
2621
+ reasons.append('Route mismatch: expected after capture path ' + (expected or '(unknown)') + ', observed ' + (observed or '(unknown)') + '.')
2622
+ reasons.append('The terminal route came from the authored interaction proof packet, so the capture plan should be revised instead of refreshing recon.')
2623
+ summary = 'Verify capture route mismatch after authored interaction: expected ' + (expected or '(unknown)') + ', got ' + (observed or '(unknown)') + '.'
2624
+ if error_messages:
2625
+ reasons.append('Capture script error: ' + error_messages[0][:500])
2626
+ summary += ' Capture script error: ' + error_messages[0][:300]
2627
+ elif error_messages:
2530
2628
  reasons.append('Capture script error: ' + error_messages[0][:500])
2531
2629
  summary = 'Verify capture script failed: ' + error_messages[0][:300]
2532
2630
  else:
@@ -3092,6 +3190,15 @@ after_observation = evaluate_capture_quality(after_payload, expected_path, verif
3092
3190
  details = after_observation.get('details') if isinstance(after_observation.get('details'), dict) else {}
3093
3191
  details['viewport_matrix'] = after_viewport_matrix
3094
3192
  after_observation['details'] = details
3193
+ after_payload, synthetic_interaction_failure_evidence = attach_interaction_capture_failure_evidence(s, after_payload, expected_path, after_observation)
3194
+ if synthetic_interaction_failure_evidence is not None:
3195
+ s['synthetic_interaction_failure_evidence'] = synthetic_interaction_failure_evidence
3196
+ if isinstance(results.get('after'), dict):
3197
+ results['after']['raw'] = after_payload
3198
+ after_observation = evaluate_capture_quality(after_payload, expected_path, verification_mode)
3199
+ details = after_observation.get('details') if isinstance(after_observation.get('details'), dict) else {}
3200
+ details['viewport_matrix'] = after_viewport_matrix
3201
+ after_observation['details'] = details
3095
3202
  if after_viewport_matrix.get('status') == 'incomplete':
3096
3203
  missing_names = [
3097
3204
  str(item.get('name') or item.get('slug') or '').strip()
@@ -3298,7 +3405,7 @@ if has_good_evidence:
3298
3405
  summary_lines.append('Proof assessment: awaiting supervising agent judgment')
3299
3406
  summary_lines.append('Proof next stage: supervising agent decides after reviewing the evidence packet')
3300
3407
  else:
3301
- capture_retry = visual_delta_recovery or build_capture_retry_decision(after_observation, required_baseline_present, proof_evidence_blocker)
3408
+ capture_retry = visual_delta_recovery or build_capture_retry_decision(after_observation, required_baseline_present, proof_evidence_blocker, s.get('route_expectation') or {})
3302
3409
  next_stage_options = ['author', 'verify', 'recon'] if no_implementation_mode else ['author', 'verify', 'implement', 'recon']
3303
3410
  s['verify_status'] = 'capture_incomplete'
3304
3411
  s['merge_recommendation'] = 'do-not-merge'
@@ -290,6 +290,41 @@ class FakeRiddle:
290
290
  'totalPixels': 972000,
291
291
  },
292
292
  }
293
+ if 'pricingQueryHashDropsTerminal' in script:
294
+ message = (
295
+ 'page.waitForURL: Timeout 15000ms exceeded.\n'
296
+ '=========================== logs ===========================\n'
297
+ 'waiting for navigation until "load"\n'
298
+ ' navigated to "https://riddledc.com/pricing/"'
299
+ )
300
+ page_state = {
301
+ 'bodyTextLength': 260,
302
+ 'visibleTextSample': 'Pricing One rate Browser Compute Example Costs',
303
+ 'interactiveElements': 8,
304
+ 'visibleInteractiveElements': 8,
305
+ 'pathname': '/pricing/',
306
+ 'search': '',
307
+ 'hash': '',
308
+ 'title': 'Pricing',
309
+ 'buttons': [],
310
+ 'headings': ['Pricing', 'Browser Compute'],
311
+ 'links': [{'text': 'Pricing', 'href': '/pricing/?rp_probe=1#pricing-probe'}],
312
+ 'canvasCount': 0,
313
+ 'largeVisibleElements': [{'tag': 'main', 'text': 'Pricing'}],
314
+ }
315
+ return {
316
+ 'ok': True,
317
+ 'screenshots': [{'url': 'https://cdn.example.com/pricing-no-query-hash.png'}],
318
+ 'outputs': [{'name': 'after-pricing-query-hash.png', 'url': 'https://cdn.example.com/pricing-no-query-hash.png'}],
319
+ 'result': {'pageState': page_state},
320
+ 'console': [
321
+ 'RIDDLE_PROOF_STATE:' + json.dumps(page_state),
322
+ 'Uncaught exception: ' + message,
323
+ ],
324
+ '_artifact_json': {
325
+ 'proof.json': {'script_error': message},
326
+ },
327
+ }
293
328
  if 'clickedProofNavigation' in script:
294
329
  page_state = {
295
330
  'bodyTextLength': 180,
@@ -2495,6 +2530,77 @@ def run_verify_interaction_hash_terminal_route_from_proof_evidence():
2495
2530
  shutil.rmtree(tempdir, ignore_errors=True)
2496
2531
 
2497
2532
 
2533
+ def run_verify_interaction_authored_query_hash_mismatch_returns_author():
2534
+ tempdir = Path(tempfile.mkdtemp(prefix='riddle-proof-interaction-query-hash-mismatch-'))
2535
+ state_path = tempdir / 'state.json'
2536
+ try:
2537
+ state = base_state(tempdir, reference='before')
2538
+ state.update({
2539
+ 'recon_status': 'ready_for_proof_plan',
2540
+ 'author_status': 'ready',
2541
+ 'proof_plan_status': 'ready',
2542
+ 'implementation_status': 'changes_detected',
2543
+ 'implementation_mode': 'none',
2544
+ 'require_diff': False,
2545
+ 'allow_code_changes': False,
2546
+ 'verification_mode': 'interaction',
2547
+ 'server_path': '/',
2548
+ 'before_cdn': 'https://cdn.example.com/before-home.png',
2549
+ 'proof_plan': 'Start at /, click Pricing, and verify /pricing/?rp_probe=1#pricing-probe.',
2550
+ 'capture_script': "pricingQueryHashDropsTerminal(); await page.waitForURL('/pricing/?rp_probe=1#pricing-probe');",
2551
+ 'supervisor_author_packet': {
2552
+ 'proof_plan': 'Click Pricing and prove the terminal query/hash route.',
2553
+ 'capture_script': "pricingQueryHashDropsTerminal(); await page.waitForURL('/pricing/?rp_probe=1#pricing-probe');",
2554
+ 'refined_inputs': {
2555
+ 'server_path': '/',
2556
+ 'expected_terminal_path': '/pricing/?rp_probe=1#pricing-probe',
2557
+ },
2558
+ },
2559
+ 'recon_results': {
2560
+ 'baselines': {'before': {'path': '/', 'url': 'https://cdn.example.com/before-home.png'}},
2561
+ },
2562
+ })
2563
+ write_state(state_path, state)
2564
+ os.environ['RIDDLE_PROOF_STATE_FILE'] = str(state_path)
2565
+
2566
+ fake = FakeRiddle()
2567
+ load_util_with_fake(fake)
2568
+ load_module('verify_interaction_authored_query_hash_mismatch', VERIFY_PATH)
2569
+ after_verify = json.loads(state_path.read_text())
2570
+
2571
+ request = after_verify['verify_decision_request']
2572
+ capture_quality = request['capture_quality']
2573
+ assert after_verify['verify_status'] == 'capture_incomplete'
2574
+ assert after_verify['route_expectation']['expected_query'] == 'rp_probe=1'
2575
+ assert after_verify['route_expectation']['expected_hash'] == '#pricing-probe'
2576
+ assert request['recommended_stage'] == 'author'
2577
+ assert request['continue_with_stage'] == 'author'
2578
+ assert capture_quality['recommended_stage'] == 'author'
2579
+ assert capture_quality['mismatch']['expected_path'] == '/pricing?rp_probe=1#pricing-probe'
2580
+ assert capture_quality['mismatch']['observed_after_path'] == '/pricing/'
2581
+ assert 'page.waitForURL: Timeout 15000ms exceeded' in capture_quality['summary']
2582
+ assert any('capture plan should be revised' in reason for reason in capture_quality['reasons'])
2583
+ supporting = after_verify['verify_results']['after']['supporting_artifacts']
2584
+ assert supporting['proof_evidence_present'] is True
2585
+ assert supporting['has_structured_payload'] is True
2586
+ synthetic_evidence = after_verify['evidence_bundle']['proof_evidence']
2587
+ assert synthetic_evidence['version'] == 'riddle-proof.interaction.capture-failure.v1'
2588
+ assert synthetic_evidence['passed'] is False
2589
+ assert synthetic_evidence['authored_proof_evidence_present'] is False
2590
+ assert synthetic_evidence['checks']['routeMatches'] is False
2591
+ assert synthetic_evidence['expected']['query'] == 'rp_probe=1'
2592
+ assert synthetic_evidence['expected']['hash'] == '#pricing-probe'
2593
+ assert synthetic_evidence['observed']['path'] == '/pricing'
2594
+ assert 'page.waitForURL: Timeout 15000ms exceeded' in synthetic_evidence['capture_error']
2595
+ return {
2596
+ 'ok': True,
2597
+ 'summary': capture_quality['summary'],
2598
+ 'recommended_stage': request['recommended_stage'],
2599
+ }
2600
+ finally:
2601
+ shutil.rmtree(tempdir, ignore_errors=True)
2602
+
2603
+
2498
2604
  def run_verify_capture_retry_surfaces_script_timeout():
2499
2605
  tempdir = Path(tempfile.mkdtemp(prefix='riddle-proof-capture-timeout-'))
2500
2606
  state_path = tempdir / 'state.json'
@@ -2914,6 +3020,7 @@ if __name__ == '__main__':
2914
3020
  'verify_interaction_terminal_route_from_proof_evidence': run_verify_interaction_terminal_route_from_proof_evidence(),
2915
3021
  'verify_interaction_reverse_terminal_route_from_proof_evidence': run_verify_interaction_reverse_terminal_route_from_proof_evidence(),
2916
3022
  'verify_interaction_hash_terminal_route_from_proof_evidence': run_verify_interaction_hash_terminal_route_from_proof_evidence(),
3023
+ 'verify_interaction_authored_query_hash_mismatch_returns_author': run_verify_interaction_authored_query_hash_mismatch_returns_author(),
2917
3024
  'verify_capture_retry_surfaces_script_timeout': run_verify_capture_retry_surfaces_script_timeout(),
2918
3025
  'missing_baseline_guard': run_verify_missing_baseline(),
2919
3026
  'ship_supervisor_gate': run_ship_missing_supervisor_gate(),
File without changes