@riddledc/riddle-proof 0.7.132 → 0.7.134

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.
package/dist/cli.cjs CHANGED
@@ -6998,7 +6998,8 @@ var RIDDLE_PROOF_PROFILE_SETUP_ACTION_TYPES = [
6998
6998
  "wait",
6999
6999
  "wait_for_selector",
7000
7000
  "wait_for_text",
7001
- "window_call"
7001
+ "window_call",
7002
+ "window_call_until"
7002
7003
  ];
7003
7004
  var RIDDLE_PROOF_PROFILE_NETWORK_ABORT_ERROR_CODES = [
7004
7005
  "aborted",
@@ -7388,6 +7389,19 @@ function profileSetupActionCounts(results) {
7388
7389
  function profileSetupScreenshotLabels(results) {
7389
7390
  return results.filter((result) => profileSetupResultAction(result) === "screenshot" && result.ok !== false && typeof result.screenshot_label === "string").map((result) => result.screenshot_label).filter(Boolean);
7390
7391
  }
7392
+ function profileSetupWindowCallUntilReceipts(results) {
7393
+ return results.filter((result) => profileSetupResultAction(result) === "window_call_until").map((result) => ({
7394
+ ordinal: result.ordinal ?? null,
7395
+ ok: result.ok !== false,
7396
+ path: result.path ?? null,
7397
+ until_path: result.until_path ?? null,
7398
+ until_value: result.until_value ?? null,
7399
+ until_expected_value: result.until_expected_value ?? null,
7400
+ call_count: result.call_count ?? null,
7401
+ max_calls: result.max_calls ?? null,
7402
+ reason: result.reason ?? result.error ?? null
7403
+ }));
7404
+ }
7391
7405
  function sampleProfileSetupSummaryItems(items, limit) {
7392
7406
  if (items.length <= limit) return items;
7393
7407
  const firstCount = Math.floor(limit / 2);
@@ -7413,6 +7427,9 @@ function profileSetupSummary(viewports, actionCount, expectedActionCountByViewpo
7413
7427
  const optionalFailed = results.filter((result) => result.ok === false && result.optional === true);
7414
7428
  const successfulClicks = results.filter((result) => profileSetupResultAction(result) === "click" && result.ok !== false);
7415
7429
  const clickCountValues = successfulClicks.map((result) => typeof result.click_count === "number" && Number.isFinite(result.click_count) && result.click_count > 1 ? result.click_count : void 0).filter((value) => value !== void 0);
7430
+ const windowCallUntilReceipts = profileSetupWindowCallUntilReceipts(results);
7431
+ const windowCallUntilCallCounts = windowCallUntilReceipts.map((result) => typeof result.call_count === "number" && Number.isFinite(result.call_count) ? result.call_count : void 0).filter((value) => value !== void 0);
7432
+ const sampledWindowCallUntilReceipts = sampleProfileSetupSummaryItems(windowCallUntilReceipts, 8);
7416
7433
  const clickedItems = results.filter((result) => profileSetupResultAction(result) === "click" && result.ok !== false).map((result) => {
7417
7434
  const clickCount = typeof result.click_count === "number" && Number.isFinite(result.click_count) && result.click_count > 1 ? result.click_count : void 0;
7418
7435
  return {
@@ -7445,6 +7462,10 @@ function profileSetupSummary(viewports, actionCount, expectedActionCountByViewpo
7445
7462
  clicked_truncated: clickedItems.length > clicked.length,
7446
7463
  click_count_action_total: clickCountValues.length,
7447
7464
  click_count_value_total: clickCountValues.reduce((sum, value) => sum + value, 0),
7465
+ window_call_until_total: windowCallUntilReceipts.length,
7466
+ window_call_until_call_total: windowCallUntilCallCounts.reduce((sum, value) => sum + value, 0),
7467
+ window_call_until_truncated: windowCallUntilReceipts.length > sampledWindowCallUntilReceipts.length,
7468
+ window_call_until: sampledWindowCallUntilReceipts,
7448
7469
  clicked,
7449
7470
  text_samples,
7450
7471
  failed: failed.map((result) => ({
@@ -7497,7 +7518,7 @@ function isSupportedCheckType(value) {
7497
7518
  }
7498
7519
  function normalizeSetupActionType(value, index) {
7499
7520
  const normalizedInput = String(value || "").trim().replace(/-/g, "_");
7500
- const normalized = normalizedInput === "clear_browser_storage" ? "clear_storage" : normalizedInput === "reset_console" || normalizedInput === "clear_browser_console" || normalizedInput === "reset_browser_console" ? "clear_console" : normalizedInput === "pointer_drag" || normalizedInput === "mouse_drag" || normalizedInput === "drag_to" ? "drag" : normalizedInput === "keyboard_press" || normalizedInput === "key_press" ? "press" : normalizedInput === "capture_screenshot" || normalizedInput === "save_screenshot" || normalizedInput === "setup_screenshot" ? "screenshot" : normalizedInput === "accept_dialog" || normalizedInput === "accept_dialogs" || normalizedInput === "confirm_dialog" || normalizedInput === "set_dialog_response" ? "dialog_response" : normalizedInput === "dismiss_dialog" || normalizedInput === "dismiss_dialogs" || normalizedInput === "cancel_dialog" ? "dialog_response" : normalizedInput;
7521
+ const normalized = normalizedInput === "clear_browser_storage" ? "clear_storage" : normalizedInput === "reset_console" || normalizedInput === "clear_browser_console" || normalizedInput === "reset_browser_console" ? "clear_console" : normalizedInput === "pointer_drag" || normalizedInput === "mouse_drag" || normalizedInput === "drag_to" ? "drag" : normalizedInput === "keyboard_press" || normalizedInput === "key_press" ? "press" : normalizedInput === "capture_screenshot" || normalizedInput === "save_screenshot" || normalizedInput === "setup_screenshot" ? "screenshot" : normalizedInput === "accept_dialog" || normalizedInput === "accept_dialogs" || normalizedInput === "confirm_dialog" || normalizedInput === "set_dialog_response" ? "dialog_response" : normalizedInput === "dismiss_dialog" || normalizedInput === "dismiss_dialogs" || normalizedInput === "cancel_dialog" ? "dialog_response" : normalizedInput === "window_call_until" || normalizedInput === "call_until" || normalizedInput === "window_call_repeat_until" || normalizedInput === "repeat_window_call_until" ? "window_call_until" : normalizedInput;
7501
7522
  if (RIDDLE_PROOF_PROFILE_SETUP_ACTION_TYPES.includes(normalized)) {
7502
7523
  return normalized;
7503
7524
  }
@@ -7628,10 +7649,10 @@ function normalizeSetupAction(input, index) {
7628
7649
  throw new Error(`target.setup_actions[${index}] ${type} requires value.`);
7629
7650
  }
7630
7651
  const path7 = stringFromOwn(input, "path", "function_path", "functionPath", "window_path", "windowPath", "state_path", "statePath");
7631
- if ((type === "window_call" || type === "assert_window_value" || type === "assert_window_number") && !path7) {
7652
+ if ((type === "window_call" || type === "window_call_until" || type === "assert_window_value" || type === "assert_window_number") && !path7) {
7632
7653
  throw new Error(`target.setup_actions[${index}] ${type} requires path.`);
7633
7654
  }
7634
- const args = type === "window_call" ? normalizeSetupActionArgs(input, index) : void 0;
7655
+ const args = type === "window_call" || type === "window_call_until" ? normalizeSetupActionArgs(input, index) : void 0;
7635
7656
  const hasExpectedValue = hasOwn(input, "expected_value") || hasOwn(input, "expectedValue") || hasOwn(input, "expected") || hasOwn(input, "expect_value") || hasOwn(input, "expectValue") || hasOwn(input, "expect");
7636
7657
  if (type === "assert_window_value" && !hasExpectedValue) {
7637
7658
  throw new Error(`target.setup_actions[${index}] ${type} requires expected_value.`);
@@ -7648,6 +7669,24 @@ function normalizeSetupAction(input, index) {
7648
7669
  }
7649
7670
  }
7650
7671
  const hasExpectedReturn = hasOwn(input, "expect_return") || hasOwn(input, "expectReturn") || hasOwn(input, "expected_return") || hasOwn(input, "expectedReturn");
7672
+ const untilPath = stringFromOwn(input, "until_path", "untilPath", "until_state_path", "untilStatePath", "until_window_path", "untilWindowPath", "until");
7673
+ const hasUntilExpectedValue = hasOwn(input, "until_expected_value") || hasOwn(input, "untilExpectedValue") || hasOwn(input, "until_expected") || hasOwn(input, "untilExpected") || hasOwn(input, "until_value") || hasOwn(input, "untilValue") || hasOwn(input, "expected_value") || hasOwn(input, "expectedValue") || hasOwn(input, "expected");
7674
+ if (type === "window_call_until") {
7675
+ if (!untilPath) {
7676
+ throw new Error(`target.setup_actions[${index}] ${type} requires until_path.`);
7677
+ }
7678
+ if (!hasUntilExpectedValue) {
7679
+ throw new Error(`target.setup_actions[${index}] ${type} requires until_expected_value.`);
7680
+ }
7681
+ }
7682
+ const maxCalls = numberValue(valueFromOwn(input, "max_calls", "maxCalls", "max_attempts", "maxAttempts", "attempts"));
7683
+ if (type === "window_call_until" && (maxCalls === void 0 || !Number.isInteger(maxCalls) || maxCalls < 1 || maxCalls > 100)) {
7684
+ throw new Error(`target.setup_actions[${index}].max_calls must be an integer from 1 to 100.`);
7685
+ }
7686
+ const intervalMs = numberValue(valueFromOwn(input, "interval_ms", "intervalMs", "poll_ms", "pollMs", "call_interval_ms", "callIntervalMs"));
7687
+ if (type === "window_call_until" && intervalMs !== void 0 && (!Number.isInteger(intervalMs) || intervalMs < 0 || intervalMs > 5e3)) {
7688
+ throw new Error(`target.setup_actions[${index}].interval_ms must be an integer from 0 to 5000.`);
7689
+ }
7651
7690
  const steps = numberValue(input.steps);
7652
7691
  if (type === "drag" && steps !== void 0 && (!Number.isInteger(steps) || steps < 1 || steps > 100)) {
7653
7692
  throw new Error(`target.setup_actions[${index}].steps must be an integer from 1 to 100.`);
@@ -7674,6 +7713,10 @@ function normalizeSetupAction(input, index) {
7674
7713
  path: path7,
7675
7714
  args,
7676
7715
  expect_return: hasExpectedReturn ? toJsonValue(valueFromOwn(input, "expect_return", "expectReturn", "expected_return", "expectedReturn")) : void 0,
7716
+ until_path: untilPath,
7717
+ until_expected_value: hasUntilExpectedValue ? toJsonValue(valueFromOwn(input, "until_expected_value", "untilExpectedValue", "until_expected", "untilExpected", "until_value", "untilValue", "expected_value", "expectedValue", "expected")) : void 0,
7718
+ max_calls: maxCalls,
7719
+ interval_ms: intervalMs,
7677
7720
  expected_value: hasExpectedValue ? toJsonValue(rawExpectedValue) : void 0,
7678
7721
  min_value: minValue,
7679
7722
  max_value: maxValue,
@@ -11534,6 +11577,34 @@ async function setupReadWindowValue(context, path) {
11534
11577
  return { ok: true, value: toJsonValue(current) };
11535
11578
  }, { path });
11536
11579
  }
11580
+ async function setupCallWindowFunction(context, path, args) {
11581
+ return await context.evaluate(async ({ path, args }) => {
11582
+ const toJsonValue = (value) => {
11583
+ if (value === null || value === undefined) return null;
11584
+ if (typeof value === "string" || typeof value === "boolean") return value;
11585
+ if (typeof value === "number") return Number.isFinite(value) ? value : null;
11586
+ if (Array.isArray(value)) return value.map(toJsonValue);
11587
+ if (typeof value === "object") {
11588
+ return Object.fromEntries(Object.entries(value).map(([key, child]) => [key, toJsonValue(child)]));
11589
+ }
11590
+ return String(value);
11591
+ };
11592
+ const pathParts = String(path || "").split(".").map((part) => part.trim()).filter(Boolean);
11593
+ let parent = window;
11594
+ let current = window;
11595
+ for (const part of pathParts) {
11596
+ parent = current;
11597
+ current = current?.[part];
11598
+ }
11599
+ if (typeof current !== "function") return { ok: false, reason: "missing_function" };
11600
+ try {
11601
+ const returned = await current.apply(parent, Array.isArray(args) ? args : []);
11602
+ return { ok: true, returned: toJsonValue(returned) };
11603
+ } catch (error) {
11604
+ return { ok: false, reason: "function_threw", error: String(error && error.message ? error.message : error).slice(0, 1000) };
11605
+ }
11606
+ }, { path, args });
11607
+ }
11537
11608
  function setupFrameSelector(action) {
11538
11609
  return String(action?.frame_selector || action?.frameSelector || action?.iframe_selector || action?.iframeSelector || "").trim();
11539
11610
  }
@@ -12051,32 +12122,7 @@ async function executeSetupAction(action, ordinal, viewport) {
12051
12122
  if (!path) return { ...base, path, reason: "missing_path" };
12052
12123
  const scope = await setupActionScope(action, timeout);
12053
12124
  if (!scope.ok) return setupScopeFailure(base, scope);
12054
- const result = await scope.context.evaluate(async ({ path, args }) => {
12055
- const toJsonValue = (value) => {
12056
- if (value === null || value === undefined) return null;
12057
- if (typeof value === "string" || typeof value === "boolean") return value;
12058
- if (typeof value === "number") return Number.isFinite(value) ? value : null;
12059
- if (Array.isArray(value)) return value.map(toJsonValue);
12060
- if (typeof value === "object") {
12061
- return Object.fromEntries(Object.entries(value).map(([key, child]) => [key, toJsonValue(child)]));
12062
- }
12063
- return String(value);
12064
- };
12065
- const pathParts = String(path || "").split(".").map((part) => part.trim()).filter(Boolean);
12066
- let parent = window;
12067
- let current = window;
12068
- for (const part of pathParts) {
12069
- parent = current;
12070
- current = current?.[part];
12071
- }
12072
- if (typeof current !== "function") return { ok: false, reason: "missing_function" };
12073
- try {
12074
- const returned = await current.apply(parent, Array.isArray(args) ? args : []);
12075
- return { ok: true, returned: toJsonValue(returned) };
12076
- } catch (error) {
12077
- return { ok: false, reason: "function_threw", error: String(error && error.message ? error.message : error).slice(0, 1000) };
12078
- }
12079
- }, { path, args });
12125
+ const result = await setupCallWindowFunction(scope.context, path, args);
12080
12126
  const hasExpectation = setupHasOwn(action, "expect_return")
12081
12127
  || setupHasOwn(action, "expectReturn")
12082
12128
  || setupHasOwn(action, "expected_return")
@@ -12101,6 +12147,126 @@ async function executeSetupAction(action, ordinal, viewport) {
12101
12147
  error: result.error || undefined,
12102
12148
  };
12103
12149
  }
12150
+ if (type === "window_call_until") {
12151
+ const path = String(action.path || action.function_path || action.functionPath || "");
12152
+ const untilPath = String(action.until_path || action.untilPath || action.until_state_path || action.untilStatePath || action.until_window_path || action.untilWindowPath || action.until || "");
12153
+ const args = Array.isArray(action.args) ? action.args : [];
12154
+ if (!path) return { ...base, path, reason: "missing_path" };
12155
+ if (!untilPath) return { ...base, path, reason: "missing_until_path" };
12156
+ const hasUntilExpected = setupHasOwn(action, "until_expected_value")
12157
+ || setupHasOwn(action, "untilExpectedValue")
12158
+ || setupHasOwn(action, "until_expected")
12159
+ || setupHasOwn(action, "untilExpected")
12160
+ || setupHasOwn(action, "until_value")
12161
+ || setupHasOwn(action, "untilValue")
12162
+ || setupHasOwn(action, "expected_value")
12163
+ || setupHasOwn(action, "expectedValue")
12164
+ || setupHasOwn(action, "expected");
12165
+ const untilExpected = setupHasOwn(action, "until_expected_value")
12166
+ ? action.until_expected_value
12167
+ : setupHasOwn(action, "untilExpectedValue")
12168
+ ? action.untilExpectedValue
12169
+ : setupHasOwn(action, "until_expected")
12170
+ ? action.until_expected
12171
+ : setupHasOwn(action, "untilExpected")
12172
+ ? action.untilExpected
12173
+ : setupHasOwn(action, "until_value")
12174
+ ? action.until_value
12175
+ : setupHasOwn(action, "untilValue")
12176
+ ? action.untilValue
12177
+ : setupHasOwn(action, "expected_value")
12178
+ ? action.expected_value
12179
+ : setupHasOwn(action, "expectedValue")
12180
+ ? action.expectedValue
12181
+ : action.expected;
12182
+ if (!hasUntilExpected) return { ...base, path, until_path: untilPath, reason: "missing_until_expected_value" };
12183
+ const maxCalls = Math.min(100, Math.max(1, Math.floor(setupNumber(action.max_calls ?? action.maxCalls ?? action.max_attempts ?? action.maxAttempts ?? action.attempts, 1) || 1)));
12184
+ const intervalMs = Math.min(5000, Math.max(0, Math.floor(setupNumber(action.interval_ms ?? action.intervalMs ?? action.poll_ms ?? action.pollMs ?? action.call_interval_ms ?? action.callIntervalMs, 100) || 0)));
12185
+ const hasReturnExpectation = setupHasOwn(action, "expect_return")
12186
+ || setupHasOwn(action, "expectReturn")
12187
+ || setupHasOwn(action, "expected_return")
12188
+ || setupHasOwn(action, "expectedReturn");
12189
+ const expectedReturn = setupHasOwn(action, "expect_return")
12190
+ ? action.expect_return
12191
+ : setupHasOwn(action, "expectReturn")
12192
+ ? action.expectReturn
12193
+ : setupHasOwn(action, "expected_return")
12194
+ ? action.expected_return
12195
+ : action.expectedReturn;
12196
+ const scope = await setupActionScope(action, timeout);
12197
+ if (!scope.ok) return setupScopeFailure(base, scope);
12198
+ const startedAt = Date.now();
12199
+ let callCount = 0;
12200
+ let lastCallResult = null;
12201
+ let lastPredicateResult = await setupReadWindowValue(scope.context, untilPath);
12202
+ if (lastPredicateResult.ok && setupValuesEqual(lastPredicateResult.value, untilExpected)) {
12203
+ return {
12204
+ ...base,
12205
+ ...setupScopeEvidence(scope),
12206
+ ok: true,
12207
+ path,
12208
+ arg_count: args.length,
12209
+ until_path: untilPath,
12210
+ until_value: setupJsonValue(lastPredicateResult.value),
12211
+ until_expected_value: setupJsonValue(untilExpected),
12212
+ call_count: callCount,
12213
+ max_calls: maxCalls,
12214
+ interval_ms: intervalMs,
12215
+ timeout_ms: timeout,
12216
+ };
12217
+ }
12218
+ while (callCount < maxCalls && Date.now() - startedAt <= timeout) {
12219
+ lastCallResult = await setupCallWindowFunction(scope.context, path, args);
12220
+ callCount += 1;
12221
+ if (!lastCallResult.ok) break;
12222
+ if (hasReturnExpectation && !setupValuesEqual(lastCallResult.returned, expectedReturn)) break;
12223
+ lastPredicateResult = await setupReadWindowValue(scope.context, untilPath);
12224
+ if (lastPredicateResult.ok && setupValuesEqual(lastPredicateResult.value, untilExpected)) {
12225
+ return {
12226
+ ...base,
12227
+ ...setupScopeEvidence(scope),
12228
+ ok: true,
12229
+ path,
12230
+ arg_count: args.length,
12231
+ returned: setupJsonValue(lastCallResult.returned),
12232
+ expected_return: hasReturnExpectation ? setupJsonValue(expectedReturn) : undefined,
12233
+ until_path: untilPath,
12234
+ until_value: setupJsonValue(lastPredicateResult.value),
12235
+ until_expected_value: setupJsonValue(untilExpected),
12236
+ call_count: callCount,
12237
+ max_calls: maxCalls,
12238
+ interval_ms: intervalMs,
12239
+ timeout_ms: timeout,
12240
+ };
12241
+ }
12242
+ if (callCount < maxCalls && intervalMs) await page.waitForTimeout(intervalMs);
12243
+ }
12244
+ const returnExpectationMet = !hasReturnExpectation || setupValuesEqual(lastCallResult?.returned, expectedReturn);
12245
+ return {
12246
+ ...base,
12247
+ ...setupScopeEvidence(scope),
12248
+ path,
12249
+ arg_count: args.length,
12250
+ returned: setupJsonValue(lastCallResult?.returned),
12251
+ expected_return: hasReturnExpectation ? setupJsonValue(expectedReturn) : undefined,
12252
+ until_path: untilPath,
12253
+ until_value: setupJsonValue(lastPredicateResult?.value),
12254
+ until_expected_value: setupJsonValue(untilExpected),
12255
+ call_count: callCount,
12256
+ max_calls: maxCalls,
12257
+ interval_ms: intervalMs,
12258
+ timeout_ms: timeout,
12259
+ reason: lastCallResult && !lastCallResult.ok
12260
+ ? lastCallResult.reason
12261
+ : hasReturnExpectation && !returnExpectationMet
12262
+ ? "unexpected_return_value"
12263
+ : Date.now() - startedAt > timeout
12264
+ ? "timeout"
12265
+ : "until_condition_not_met",
12266
+ error: lastCallResult?.error || undefined,
12267
+ missing_part: lastPredicateResult?.missing_part || undefined,
12268
+ };
12269
+ }
12104
12270
  if (type === "assert_window_value") {
12105
12271
  const path = String(action.path || action.window_path || action.windowPath || "");
12106
12272
  const hasExpected = setupHasOwn(action, "expected_value")
@@ -14246,6 +14412,16 @@ function cliFiniteNumber(value) {
14246
14412
  function cliString(value) {
14247
14413
  return typeof value === "string" && value.trim() ? value.trim() : void 0;
14248
14414
  }
14415
+ function cliValueLabel(value) {
14416
+ if (value === void 0) return void 0;
14417
+ if (typeof value === "string") return value.trim() || void 0;
14418
+ try {
14419
+ const serialized = JSON.stringify(value);
14420
+ return typeof serialized === "string" && serialized ? serialized : String(value);
14421
+ } catch {
14422
+ return String(value);
14423
+ }
14424
+ }
14249
14425
  function cliStringArray(value) {
14250
14426
  return Array.isArray(value) ? value.filter((entry) => typeof entry === "string" && Boolean(entry.trim())) : [];
14251
14427
  }
@@ -14310,6 +14486,8 @@ function profileSetupSummaryMarkdown(result) {
14310
14486
  const clickedTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.clicked_total) || 0), 0);
14311
14487
  const clickCountActionTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.click_count_action_total) || 0), 0);
14312
14488
  const clickCountValueTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.click_count_value_total) || 0), 0);
14489
+ const windowCallUntilTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.window_call_until_total) || 0), 0);
14490
+ const windowCallUntilCallTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.window_call_until_call_total) || 0), 0);
14313
14491
  const failedTotal = viewports.reduce((sum, viewport) => sum + (Array.isArray(viewport.failed) ? viewport.failed.length : 0), 0);
14314
14492
  const lines = [
14315
14493
  `- setup actions: ${declaredActions === void 0 ? "unknown" : declaredActions} declared, ${totalResults} recorded result(s) across ${viewports.length} viewport(s)`,
@@ -14319,6 +14497,9 @@ function profileSetupSummaryMarkdown(result) {
14319
14497
  if (clickCountActionTotal) {
14320
14498
  lines.push(`- click counts: ${clickCountActionTotal} action(s), click_count total ${clickCountValueTotal}`);
14321
14499
  }
14500
+ if (windowCallUntilTotal) {
14501
+ lines.push(`- window_call_until: ${windowCallUntilTotal} action(s), call_count total ${windowCallUntilCallTotal}`);
14502
+ }
14322
14503
  for (const viewport of viewports.slice(0, 8)) {
14323
14504
  const name = cliString(viewport.name) || "viewport";
14324
14505
  const ok = viewport.ok === false ? "failed" : "ok";
@@ -14326,9 +14507,29 @@ function profileSetupSummaryMarkdown(result) {
14326
14507
  const screenshotCount = Array.isArray(viewport.setup_screenshots) ? viewport.setup_screenshots.filter((label) => typeof label === "string" && label.trim()).length : 0;
14327
14508
  const clicked = cliFiniteNumber(viewport.clicked_total) || 0;
14328
14509
  const clickCountActions = cliFiniteNumber(viewport.click_count_action_total) || 0;
14510
+ const windowCallUntilActions = cliFiniteNumber(viewport.window_call_until_total) || 0;
14511
+ const windowCallUntilCalls = cliFiniteNumber(viewport.window_call_until_call_total) || 0;
14329
14512
  const observedPath = cliString(viewport.observed_path);
14330
- lines.push(`- ${name}: ${ok}, ${resultCount} result(s), ${screenshotCount} setup screenshot(s), ${clicked} click(s)${clickCountActions ? `, ${clickCountActions} click_count action(s)` : ""}${observedPath ? `, path ${observedPath}` : ""}`);
14513
+ lines.push(`- ${name}: ${ok}, ${resultCount} result(s), ${screenshotCount} setup screenshot(s), ${clicked} click(s)${clickCountActions ? `, ${clickCountActions} click_count action(s)` : ""}${windowCallUntilActions ? `, ${windowCallUntilActions} window_call_until action(s), ${windowCallUntilCalls} call(s)` : ""}${observedPath ? `, path ${observedPath}` : ""}`);
14331
14514
  }
14515
+ const windowCallUntilDetails = viewports.flatMap((viewport) => {
14516
+ const name = cliString(viewport.name) || "viewport";
14517
+ const receipts = Array.isArray(viewport.window_call_until) ? viewport.window_call_until.map(cliRecord).filter((item) => Boolean(item)) : [];
14518
+ return receipts.map((receipt) => ({ name, receipt }));
14519
+ });
14520
+ for (const { name, receipt } of windowCallUntilDetails.slice(0, 12)) {
14521
+ const path7 = cliString(receipt.path) || "window_function";
14522
+ const untilPath = cliString(receipt.until_path) || "until_path";
14523
+ const expected = cliValueLabel(receipt.until_expected_value);
14524
+ const actual = cliValueLabel(receipt.until_value);
14525
+ const callCount = cliFiniteNumber(receipt.call_count);
14526
+ const maxCalls = cliFiniteNumber(receipt.max_calls);
14527
+ const ok = receipt.ok === false ? "failed" : "ok";
14528
+ const reason = cliString(receipt.reason);
14529
+ const callText = callCount === void 0 ? "" : ` in ${callCount}${maxCalls === void 0 ? "" : `/${maxCalls}`} call(s)`;
14530
+ lines.push(`- ${name} window_call_until: ${ok}, ${markdownInlineCode(path7)} until ${markdownInlineCode(untilPath)}${expected === void 0 ? "" : ` == ${markdownInlineCode(expected, 80)}`}${callText}${actual === void 0 ? "" : `, observed ${markdownInlineCode(actual, 80)}`}${reason ? `, reason ${markdownInlineCode(reason, 100)}` : ""}`);
14531
+ }
14532
+ if (windowCallUntilDetails.length > 12) lines.push(`- ${windowCallUntilDetails.length - 12} additional window_call_until receipt(s) omitted.`);
14332
14533
  const failedDetails = viewports.flatMap((viewport) => {
14333
14534
  const name = cliString(viewport.name) || "viewport";
14334
14535
  const failed = Array.isArray(viewport.failed) ? viewport.failed.map(cliRecord).filter((item) => Boolean(item)) : [];
package/dist/cli.js CHANGED
@@ -12,7 +12,7 @@ import {
12
12
  profileStatusExitCode,
13
13
  resolveRiddleProofProfileTargetUrl,
14
14
  resolveRiddleProofProfileTimeoutSec
15
- } from "./chunk-PKE223TX.js";
15
+ } from "./chunk-TALHK3NV.js";
16
16
  import {
17
17
  createRiddleApiClient,
18
18
  parseRiddleViewport
@@ -522,6 +522,16 @@ function cliFiniteNumber(value) {
522
522
  function cliString(value) {
523
523
  return typeof value === "string" && value.trim() ? value.trim() : void 0;
524
524
  }
525
+ function cliValueLabel(value) {
526
+ if (value === void 0) return void 0;
527
+ if (typeof value === "string") return value.trim() || void 0;
528
+ try {
529
+ const serialized = JSON.stringify(value);
530
+ return typeof serialized === "string" && serialized ? serialized : String(value);
531
+ } catch {
532
+ return String(value);
533
+ }
534
+ }
525
535
  function cliStringArray(value) {
526
536
  return Array.isArray(value) ? value.filter((entry) => typeof entry === "string" && Boolean(entry.trim())) : [];
527
537
  }
@@ -586,6 +596,8 @@ function profileSetupSummaryMarkdown(result) {
586
596
  const clickedTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.clicked_total) || 0), 0);
587
597
  const clickCountActionTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.click_count_action_total) || 0), 0);
588
598
  const clickCountValueTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.click_count_value_total) || 0), 0);
599
+ const windowCallUntilTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.window_call_until_total) || 0), 0);
600
+ const windowCallUntilCallTotal = viewports.reduce((sum, viewport) => sum + (cliFiniteNumber(viewport.window_call_until_call_total) || 0), 0);
589
601
  const failedTotal = viewports.reduce((sum, viewport) => sum + (Array.isArray(viewport.failed) ? viewport.failed.length : 0), 0);
590
602
  const lines = [
591
603
  `- setup actions: ${declaredActions === void 0 ? "unknown" : declaredActions} declared, ${totalResults} recorded result(s) across ${viewports.length} viewport(s)`,
@@ -595,6 +607,9 @@ function profileSetupSummaryMarkdown(result) {
595
607
  if (clickCountActionTotal) {
596
608
  lines.push(`- click counts: ${clickCountActionTotal} action(s), click_count total ${clickCountValueTotal}`);
597
609
  }
610
+ if (windowCallUntilTotal) {
611
+ lines.push(`- window_call_until: ${windowCallUntilTotal} action(s), call_count total ${windowCallUntilCallTotal}`);
612
+ }
598
613
  for (const viewport of viewports.slice(0, 8)) {
599
614
  const name = cliString(viewport.name) || "viewport";
600
615
  const ok = viewport.ok === false ? "failed" : "ok";
@@ -602,9 +617,29 @@ function profileSetupSummaryMarkdown(result) {
602
617
  const screenshotCount = Array.isArray(viewport.setup_screenshots) ? viewport.setup_screenshots.filter((label) => typeof label === "string" && label.trim()).length : 0;
603
618
  const clicked = cliFiniteNumber(viewport.clicked_total) || 0;
604
619
  const clickCountActions = cliFiniteNumber(viewport.click_count_action_total) || 0;
620
+ const windowCallUntilActions = cliFiniteNumber(viewport.window_call_until_total) || 0;
621
+ const windowCallUntilCalls = cliFiniteNumber(viewport.window_call_until_call_total) || 0;
605
622
  const observedPath = cliString(viewport.observed_path);
606
- lines.push(`- ${name}: ${ok}, ${resultCount} result(s), ${screenshotCount} setup screenshot(s), ${clicked} click(s)${clickCountActions ? `, ${clickCountActions} click_count action(s)` : ""}${observedPath ? `, path ${observedPath}` : ""}`);
623
+ lines.push(`- ${name}: ${ok}, ${resultCount} result(s), ${screenshotCount} setup screenshot(s), ${clicked} click(s)${clickCountActions ? `, ${clickCountActions} click_count action(s)` : ""}${windowCallUntilActions ? `, ${windowCallUntilActions} window_call_until action(s), ${windowCallUntilCalls} call(s)` : ""}${observedPath ? `, path ${observedPath}` : ""}`);
607
624
  }
625
+ const windowCallUntilDetails = viewports.flatMap((viewport) => {
626
+ const name = cliString(viewport.name) || "viewport";
627
+ const receipts = Array.isArray(viewport.window_call_until) ? viewport.window_call_until.map(cliRecord).filter((item) => Boolean(item)) : [];
628
+ return receipts.map((receipt) => ({ name, receipt }));
629
+ });
630
+ for (const { name, receipt } of windowCallUntilDetails.slice(0, 12)) {
631
+ const path2 = cliString(receipt.path) || "window_function";
632
+ const untilPath = cliString(receipt.until_path) || "until_path";
633
+ const expected = cliValueLabel(receipt.until_expected_value);
634
+ const actual = cliValueLabel(receipt.until_value);
635
+ const callCount = cliFiniteNumber(receipt.call_count);
636
+ const maxCalls = cliFiniteNumber(receipt.max_calls);
637
+ const ok = receipt.ok === false ? "failed" : "ok";
638
+ const reason = cliString(receipt.reason);
639
+ const callText = callCount === void 0 ? "" : ` in ${callCount}${maxCalls === void 0 ? "" : `/${maxCalls}`} call(s)`;
640
+ lines.push(`- ${name} window_call_until: ${ok}, ${markdownInlineCode(path2)} until ${markdownInlineCode(untilPath)}${expected === void 0 ? "" : ` == ${markdownInlineCode(expected, 80)}`}${callText}${actual === void 0 ? "" : `, observed ${markdownInlineCode(actual, 80)}`}${reason ? `, reason ${markdownInlineCode(reason, 100)}` : ""}`);
641
+ }
642
+ if (windowCallUntilDetails.length > 12) lines.push(`- ${windowCallUntilDetails.length - 12} additional window_call_until receipt(s) omitted.`);
608
643
  const failedDetails = viewports.flatMap((viewport) => {
609
644
  const name = cliString(viewport.name) || "viewport";
610
645
  const failed = Array.isArray(viewport.failed) ? viewport.failed.map(cliRecord).filter((item) => Boolean(item)) : [];