@riddledc/riddle-proof 0.5.21 → 0.5.23

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.
@@ -124,6 +124,16 @@ function fullRiddleState(result, state) {
124
124
  function workdirFromState(state) {
125
125
  return nonEmptyString(state?.after_worktree) || nonEmptyString(state?.worktree_path) || null;
126
126
  }
127
+ function parseGitStatusPaths(status) {
128
+ return status.split(/\r?\n/).map((line) => line.trimEnd()).filter(Boolean).map((line) => {
129
+ let item = line.length > 3 ? line.slice(3) : line;
130
+ if (item.includes(" -> ")) item = item.split(" -> ").pop() || item;
131
+ return item.trim();
132
+ }).filter(Boolean);
133
+ }
134
+ function isToolNoisePath(filePath) {
135
+ return filePath === ".codex" || filePath.startsWith(".codex/") || filePath === ".oc-smoke" || filePath.startsWith(".oc-smoke/");
136
+ }
127
137
  function hasGitDiff(workdir) {
128
138
  if (!workdir || !existsSync(workdir)) return false;
129
139
  try {
@@ -132,7 +142,7 @@ function hasGitDiff(workdir) {
132
142
  encoding: "utf-8",
133
143
  timeout: 1e4
134
144
  });
135
- return status.trim().length > 0;
145
+ return parseGitStatusPaths(status).some((filePath) => !isToolNoisePath(filePath));
136
146
  } catch {
137
147
  return false;
138
148
  }
@@ -3126,6 +3126,16 @@ function fullRiddleState(result, state) {
3126
3126
  function workdirFromState(state) {
3127
3127
  return nonEmptyString(state?.after_worktree) || nonEmptyString(state?.worktree_path) || null;
3128
3128
  }
3129
+ function parseGitStatusPaths(status) {
3130
+ return status.split(/\r?\n/).map((line) => line.trimEnd()).filter(Boolean).map((line) => {
3131
+ let item = line.length > 3 ? line.slice(3) : line;
3132
+ if (item.includes(" -> ")) item = item.split(" -> ").pop() || item;
3133
+ return item.trim();
3134
+ }).filter(Boolean);
3135
+ }
3136
+ function isToolNoisePath(filePath) {
3137
+ return filePath === ".codex" || filePath.startsWith(".codex/") || filePath === ".oc-smoke" || filePath.startsWith(".oc-smoke/");
3138
+ }
3129
3139
  function hasGitDiff(workdir) {
3130
3140
  if (!workdir || !(0, import_node_fs3.existsSync)(workdir)) return false;
3131
3141
  try {
@@ -3134,7 +3144,7 @@ function hasGitDiff(workdir) {
3134
3144
  encoding: "utf-8",
3135
3145
  timeout: 1e4
3136
3146
  });
3137
- return status.trim().length > 0;
3147
+ return parseGitStatusPaths(status).some((filePath) => !isToolNoisePath(filePath));
3138
3148
  } catch {
3139
3149
  return false;
3140
3150
  }
@@ -2,7 +2,7 @@ import {
2
2
  createDisabledRiddleProofAgentAdapter,
3
3
  readRiddleProofRunStatus,
4
4
  runRiddleProofEngineHarness
5
- } from "./chunk-PJ3RTT5D.js";
5
+ } from "./chunk-M4MISBQV.js";
6
6
  import "./chunk-7ZJAUEUN.js";
7
7
  import "./chunk-TMMKRKY5.js";
8
8
  export {
package/dist/index.cjs CHANGED
@@ -3682,6 +3682,16 @@ function fullRiddleState(result, state) {
3682
3682
  function workdirFromState(state) {
3683
3683
  return nonEmptyString(state?.after_worktree) || nonEmptyString(state?.worktree_path) || null;
3684
3684
  }
3685
+ function parseGitStatusPaths(status) {
3686
+ return status.split(/\r?\n/).map((line) => line.trimEnd()).filter(Boolean).map((line) => {
3687
+ let item = line.length > 3 ? line.slice(3) : line;
3688
+ if (item.includes(" -> ")) item = item.split(" -> ").pop() || item;
3689
+ return item.trim();
3690
+ }).filter(Boolean);
3691
+ }
3692
+ function isToolNoisePath(filePath) {
3693
+ return filePath === ".codex" || filePath.startsWith(".codex/") || filePath === ".oc-smoke" || filePath.startsWith(".oc-smoke/");
3694
+ }
3685
3695
  function hasGitDiff(workdir) {
3686
3696
  if (!workdir || !(0, import_node_fs3.existsSync)(workdir)) return false;
3687
3697
  try {
@@ -3690,7 +3700,7 @@ function hasGitDiff(workdir) {
3690
3700
  encoding: "utf-8",
3691
3701
  timeout: 1e4
3692
3702
  });
3693
- return status.trim().length > 0;
3703
+ return parseGitStatusPaths(status).some((filePath) => !isToolNoisePath(filePath));
3694
3704
  } catch {
3695
3705
  return false;
3696
3706
  }
package/dist/index.js CHANGED
@@ -13,7 +13,7 @@ import {
13
13
  createDisabledRiddleProofAgentAdapter,
14
14
  readRiddleProofRunStatus,
15
15
  runRiddleProofEngineHarness
16
- } from "./chunk-PJ3RTT5D.js";
16
+ } from "./chunk-M4MISBQV.js";
17
17
  import {
18
18
  runRiddleProof
19
19
  } from "./chunk-F6VFKS7K.js";
package/dist/openclaw.cjs CHANGED
@@ -106,6 +106,14 @@ function parseOpenClawAssertions(value) {
106
106
  return trimmed;
107
107
  }
108
108
  }
109
+ function normalizeOpenClawReference(value) {
110
+ if (value !== "prod" && value !== "before" && value !== "both") return void 0;
111
+ return value;
112
+ }
113
+ function ignoredOpenClawReference(value) {
114
+ if (value === void 0 || value === null || value === "") return void 0;
115
+ return normalizeOpenClawReference(value) ? void 0 : String(value);
116
+ }
109
117
  function openClawIntegrationContext(params) {
110
118
  const hasDiscordContext = Boolean(params.discord_channel || params.discord_thread_id || params.discord_message_id || params.discord_source_url);
111
119
  return normalizeIntegrationContext({
@@ -116,7 +124,8 @@ function openClawIntegrationContext(params) {
116
124
  source_url: params.discord_source_url,
117
125
  metadata: compactRecord({
118
126
  wrapper: "openclaw",
119
- tool: "riddle_proof_change"
127
+ tool: "riddle_proof_change",
128
+ reference_input_ignored: ignoredOpenClawReference(params.reference)
120
129
  })
121
130
  }, "openclaw");
122
131
  }
@@ -131,7 +140,7 @@ function toRiddleProofRunParams(params) {
131
140
  success_criteria: params.success_criteria,
132
141
  assertions: parseOpenClawAssertions(params.assertions_json),
133
142
  verification_mode: params.verification_mode,
134
- reference: params.reference,
143
+ reference: normalizeOpenClawReference(params.reference),
135
144
  base_branch: params.base_branch,
136
145
  before_ref: params.before_ref,
137
146
  allow_static_preview_fallback: params.allow_static_preview_fallback,
@@ -10,7 +10,7 @@ interface OpenClawProofedChangeParams {
10
10
  success_criteria?: string;
11
11
  assertions_json?: string;
12
12
  verification_mode?: string;
13
- reference?: "prod" | "before" | "both";
13
+ reference?: "prod" | "before" | "both" | (string & {});
14
14
  base_branch?: string;
15
15
  before_ref?: string;
16
16
  allow_static_preview_fallback?: boolean;
@@ -10,7 +10,7 @@ interface OpenClawProofedChangeParams {
10
10
  success_criteria?: string;
11
11
  assertions_json?: string;
12
12
  verification_mode?: string;
13
- reference?: "prod" | "before" | "both";
13
+ reference?: "prod" | "before" | "both" | (string & {});
14
14
  base_branch?: string;
15
15
  before_ref?: string;
16
16
  allow_static_preview_fallback?: boolean;
package/dist/openclaw.js CHANGED
@@ -18,6 +18,14 @@ function parseOpenClawAssertions(value) {
18
18
  return trimmed;
19
19
  }
20
20
  }
21
+ function normalizeOpenClawReference(value) {
22
+ if (value !== "prod" && value !== "before" && value !== "both") return void 0;
23
+ return value;
24
+ }
25
+ function ignoredOpenClawReference(value) {
26
+ if (value === void 0 || value === null || value === "") return void 0;
27
+ return normalizeOpenClawReference(value) ? void 0 : String(value);
28
+ }
21
29
  function openClawIntegrationContext(params) {
22
30
  const hasDiscordContext = Boolean(params.discord_channel || params.discord_thread_id || params.discord_message_id || params.discord_source_url);
23
31
  return normalizeIntegrationContext({
@@ -28,7 +36,8 @@ function openClawIntegrationContext(params) {
28
36
  source_url: params.discord_source_url,
29
37
  metadata: compactRecord({
30
38
  wrapper: "openclaw",
31
- tool: "riddle_proof_change"
39
+ tool: "riddle_proof_change",
40
+ reference_input_ignored: ignoredOpenClawReference(params.reference)
32
41
  })
33
42
  }, "openclaw");
34
43
  }
@@ -43,7 +52,7 @@ function toRiddleProofRunParams(params) {
43
52
  success_criteria: params.success_criteria,
44
53
  assertions: parseOpenClawAssertions(params.assertions_json),
45
54
  verification_mode: params.verification_mode,
46
- reference: params.reference,
55
+ reference: normalizeOpenClawReference(params.reference),
47
56
  base_branch: params.base_branch,
48
57
  before_ref: params.before_ref,
49
58
  allow_static_preview_fallback: params.allow_static_preview_fallback,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@riddledc/riddle-proof",
3
- "version": "0.5.21",
3
+ "version": "0.5.23",
4
4
  "description": "Reusable Riddle Proof contracts and helpers for evidence-backed agent changes.",
5
5
  "license": "MIT",
6
6
  "author": "RiddleDC",
@@ -9,6 +9,8 @@ import json, os, sys
9
9
  sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
10
10
  from util import load_state, save_state, git, shell_quote
11
11
 
12
+ TOOL_NOISE_PATHS = ('.codex', '.oc-smoke')
13
+
12
14
 
13
15
  def unique_nonempty(items):
14
16
  seen = set()
@@ -37,6 +39,15 @@ def parse_status_paths(lines):
37
39
  return unique_nonempty(paths)
38
40
 
39
41
 
42
+ def is_tool_noise_path(path):
43
+ text = str(path or '').strip()
44
+ return any(text == prefix or text.startswith(prefix + '/') for prefix in TOOL_NOISE_PATHS)
45
+
46
+
47
+ def material_paths(paths):
48
+ return [path for path in unique_nonempty(paths) if not is_tool_noise_path(path)]
49
+
50
+
40
51
  s = load_state()
41
52
  after_dir = (s.get('after_worktree') or '').strip()
42
53
  if not after_dir or not os.path.exists(after_dir):
@@ -45,7 +56,9 @@ if not after_dir or not os.path.exists(after_dir):
45
56
  base_branch = s.get('base_branch', 'main')
46
57
  base_ref = (s.get('before_ref') or '').strip() or ('origin/' + base_branch)
47
58
  dirty = [ln for ln in git('git status --short', after_dir).stdout.splitlines() if ln.strip()]
48
- dirty_paths = parse_status_paths(dirty)
59
+ dirty_paths_all = parse_status_paths(dirty)
60
+ dirty_paths = material_paths(dirty_paths_all)
61
+ ignored_dirty_paths = [path for path in dirty_paths_all if is_tool_noise_path(path)]
49
62
 
50
63
  diff_probes = []
51
64
 
@@ -70,7 +83,9 @@ if diff_result.returncode != 0:
70
83
  if diff_result.returncode != 0 and not committed:
71
84
  fallback, committed = run_diff_probe('head_parent', 'git diff --name-only HEAD~1 HEAD')
72
85
 
73
- changed = unique_nonempty(dirty_paths + committed)
86
+ committed_material = material_paths(committed)
87
+ ignored_committed_paths = [path for path in committed if is_tool_noise_path(path)]
88
+ changed = unique_nonempty(dirty_paths + committed_material)
74
89
  authored = bool((s.get('capture_script') or '').strip()) and bool((s.get('proof_plan') or '').strip())
75
90
 
76
91
  detection = {
@@ -81,9 +96,13 @@ detection = {
81
96
  'base_ref_requested': base_ref,
82
97
  'dirty_status_lines': dirty[:20],
83
98
  'dirty_paths': dirty_paths[:20],
99
+ 'ignored_dirty_paths': ignored_dirty_paths[:20],
84
100
  'dirty_path_count': len(dirty_paths),
85
- 'committed_paths': committed[:20],
86
- 'committed_path_count': len(committed),
101
+ 'dirty_path_count_including_noise': len(dirty_paths_all),
102
+ 'committed_paths': committed_material[:20],
103
+ 'ignored_committed_paths': ignored_committed_paths[:20],
104
+ 'committed_path_count': len(committed_material),
105
+ 'committed_path_count_including_noise': len(committed),
87
106
  'changed_paths': changed[:20],
88
107
  'changed_path_count': len(changed),
89
108
  'diff_probes': diff_probes[:6],
@@ -637,6 +637,7 @@ def run_implement_records_detection_when_changes_missing():
637
637
  })
638
638
  write_state(state_path, state)
639
639
  os.environ['RIDDLE_PROOF_STATE_FILE'] = str(state_path)
640
+ load_module('util', UTIL_PATH)
640
641
 
641
642
  try:
642
643
  load_module('implement_changes_missing_state', IMPLEMENT_PATH)
@@ -673,6 +674,56 @@ def run_implement_records_detection_when_changes_missing():
673
674
  shutil.rmtree(tempdir, ignore_errors=True)
674
675
 
675
676
 
677
+ def run_implement_ignores_tool_noise_when_detecting_changes():
678
+ tempdir = Path(tempfile.mkdtemp(prefix='riddle-proof-implement-noise-'))
679
+ state_path = tempdir / 'state.json'
680
+ previous_state_file = os.environ.get('RIDDLE_PROOF_STATE_FILE')
681
+ try:
682
+ state = base_state(tempdir, reference='before')
683
+ after_dir = Path(state['after_worktree'])
684
+ init_git_repo(after_dir)
685
+ codex_dir = after_dir / '.codex'
686
+ codex_dir.mkdir(parents=True, exist_ok=True)
687
+ (codex_dir / 'session.json').write_text('{}\n')
688
+ state.update({
689
+ 'recon_status': 'ready_for_proof_plan',
690
+ 'author_status': 'ready',
691
+ 'proof_plan_status': 'ready',
692
+ 'proof_plan': 'Capture the pricing CTA after the implementation is applied.',
693
+ 'capture_script': "await page.waitForSelector('[data-testid=pricing-cta]'); await saveScreenshot('after-proof');",
694
+ })
695
+ write_state(state_path, state)
696
+ os.environ['RIDDLE_PROOF_STATE_FILE'] = str(state_path)
697
+ load_module('util', UTIL_PATH)
698
+
699
+ try:
700
+ load_module('implement_ignores_tool_noise', IMPLEMENT_PATH)
701
+ except SystemExit as exc:
702
+ assert 'No implementation detected on the after worktree.' in str(exc), exc
703
+ else:
704
+ raise AssertionError('implement stage should have halted when only tool noise changed')
705
+
706
+ after_state = json.loads(state_path.read_text())
707
+ detection = after_state['implementation_detection']
708
+ assert detection['outcome'] == 'no_changes_detected'
709
+ assert detection['diff_detected'] is False
710
+ assert detection['dirty_path_count'] == 0
711
+ assert detection['dirty_path_count_including_noise'] >= 1
712
+ assert any(str(path).startswith('.codex') for path in detection['ignored_dirty_paths'])
713
+ assert detection['changed_path_count'] == 0
714
+ assert after_state['changed_files'] == []
715
+ return {
716
+ 'ok': True,
717
+ 'ignored_dirty_paths': detection['ignored_dirty_paths'],
718
+ }
719
+ finally:
720
+ if previous_state_file is None:
721
+ os.environ.pop('RIDDLE_PROOF_STATE_FILE', None)
722
+ else:
723
+ os.environ['RIDDLE_PROOF_STATE_FILE'] = previous_state_file
724
+ shutil.rmtree(tempdir, ignore_errors=True)
725
+
726
+
676
727
  def run_recon_then_author_request():
677
728
  tempdir = Path(tempfile.mkdtemp(prefix='riddle-proof-supervisor-request-'))
678
729
  state_path = tempdir / 'state.json'
@@ -1481,6 +1532,7 @@ if __name__ == '__main__':
1481
1532
  'apply_auth_context': run_apply_auth_context_passes_supported_auth_payloads(),
1482
1533
  'run_project_build_retries_after_clean_failure': run_project_build_retries_after_clean_failure(),
1483
1534
  'implement_records_detection_when_changes_missing': run_implement_records_detection_when_changes_missing(),
1535
+ 'implement_ignores_tool_noise_when_detecting_changes': run_implement_ignores_tool_noise_when_detecting_changes(),
1484
1536
  'verify_quality_ignores_proof_telemetry_console_text': run_verify_quality_ignores_proof_telemetry_console_text(),
1485
1537
  'recon_then_author_request': run_recon_then_author_request(),
1486
1538
  'recon_preserves_query_route': run_recon_preserves_query_route(),