project-tiny-context-harness 0.8.1 → 0.8.2

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 (132) hide show
  1. package/LICENSE +21 -21
  2. package/README.md +401 -395
  3. package/assets/README.md +628 -549
  4. package/assets/README.zh-CN.md +345 -339
  5. package/assets/agents/.gitkeep +1 -1
  6. package/assets/agents/AGENTS_CORE.md +70 -70
  7. package/assets/context_templates/architecture.md +28 -28
  8. package/assets/context_templates/area.md +34 -34
  9. package/assets/context_templates/context.toml +30 -30
  10. package/assets/context_templates/deployment.md +35 -35
  11. package/assets/context_templates/global.md +57 -57
  12. package/assets/context_templates/product-surface-contract.md +70 -70
  13. package/assets/context_templates/screen-contract.md +189 -189
  14. package/assets/context_templates/verification.md +32 -32
  15. package/assets/github/.gitkeep +1 -1
  16. package/assets/github/harness.yml +39 -39
  17. package/assets/make/.gitkeep +1 -1
  18. package/assets/make/ty-context.mk +48 -48
  19. package/assets/skills/context_development_engineer/SKILL.md +137 -137
  20. package/assets/skills/context_full_project_export/SKILL.md +28 -28
  21. package/assets/skills/context_harness_upgrade/SKILL.md +60 -60
  22. package/assets/skills/context_product_plan/SKILL.md +88 -88
  23. package/assets/skills/context_surface_contract/SKILL.md +191 -191
  24. package/assets/skills/context_uiux_design/SKILL.md +172 -172
  25. package/assets/skills/design-resource-authoring/SKILL.md +85 -85
  26. package/assets/skills/design-resource-authoring/references/downstream-handoff.md +136 -136
  27. package/assets/skills/design-resource-authoring/references/open-design-provider.md +135 -135
  28. package/assets/skills/design-resource-authoring/references/resource-selection.md +173 -173
  29. package/assets/skills/design-system-authoring/SKILL.md +57 -57
  30. package/assets/skills/design-system-authoring/agents/openai.yaml +6 -6
  31. package/assets/skills/design-system-authoring/references/authority-adoption.md +48 -48
  32. package/assets/skills/design-system-authoring/references/open-design-design-system-provider.md +110 -110
  33. package/assets/skills/long-task-workflow/SKILL.md +100 -100
  34. package/assets/skills/long-task-workflow/references/authority-lifecycle.md +75 -73
  35. package/assets/skills/long-task-workflow/references/contract-authoring.md +119 -115
  36. package/assets/skills/long-task-workflow/references/evidence-design.md +77 -76
  37. package/assets/skills/long-task-workflow/references/source-authoring.md +102 -99
  38. package/assets/skills/source-plan-authoring/SKILL.md +14 -14
  39. package/assets/tools/validate_context.py +442 -442
  40. package/dist/commands/design-resource.js +2 -2
  41. package/dist/commands/index.js +26 -26
  42. package/dist/commands/long-task-authoring.js +83 -9
  43. package/dist/commands/long-task.js +15 -15
  44. package/dist/lib/context-graph-snapshot.js +7 -0
  45. package/dist/lib/design-resource-handoff-shape-evidence.js +3 -0
  46. package/dist/lib/design-resource-handoff-types.d.ts +2 -0
  47. package/dist/lib/design-resource-handoff-validation-coverage.js +1 -0
  48. package/dist/lib/design-resource-handoff-validation-structure.js +2 -0
  49. package/dist/lib/execution-target-capabilities.d.ts +2 -0
  50. package/dist/lib/execution-target-capabilities.js +31 -0
  51. package/dist/lib/long-task-acceptance-shape.js +81 -20
  52. package/dist/lib/long-task-applicability-shape.d.ts +4 -0
  53. package/dist/lib/long-task-applicability-shape.js +54 -0
  54. package/dist/lib/long-task-assertions-v2.js +8 -0
  55. package/dist/lib/long-task-authoring-preflight-diagnostics.js +5 -0
  56. package/dist/lib/long-task-authoring-preflight-repair-order.js +3 -0
  57. package/dist/lib/long-task-authoring-preflight.js +12 -8
  58. package/dist/lib/long-task-authority-materials.js +46 -4
  59. package/dist/lib/long-task-authority-policy.d.ts +54 -0
  60. package/dist/lib/long-task-authority-policy.js +61 -0
  61. package/dist/lib/long-task-authority-types.d.ts +12 -2
  62. package/dist/lib/long-task-authority.js +9 -2
  63. package/dist/lib/long-task-check-shape.js +6 -1
  64. package/dist/lib/long-task-claim-definitions.js +27 -42
  65. package/dist/lib/long-task-claims.js +275 -146
  66. package/dist/lib/long-task-contract-types.d.ts +42 -8
  67. package/dist/lib/long-task-control-fields.d.ts +12 -0
  68. package/dist/lib/long-task-control-fields.js +66 -0
  69. package/dist/lib/long-task-control-types.d.ts +1 -0
  70. package/dist/lib/long-task-control-types.js +1 -0
  71. package/dist/lib/long-task-counterfactual-claim-policy.js +7 -0
  72. package/dist/lib/long-task-counterfactual-types.d.ts +12 -0
  73. package/dist/lib/long-task-delivery-compiler.js +1 -0
  74. package/dist/lib/long-task-delivery-preflight.js +24 -0
  75. package/dist/lib/long-task-delivery-shape.d.ts +1 -0
  76. package/dist/lib/long-task-delivery-shape.js +1 -0
  77. package/dist/lib/long-task-delivery-types.d.ts +1 -0
  78. package/dist/lib/long-task-delivery-types.js +1 -0
  79. package/dist/lib/long-task-delivery-validation.js +46 -0
  80. package/dist/lib/long-task-design-resource-handoff.js +48 -7
  81. package/dist/lib/long-task-evidence-capability-codec.js +37 -0
  82. package/dist/lib/long-task-evidence-capability-policy.js +80 -38
  83. package/dist/lib/long-task-evidence-capability-runtime.js +36 -0
  84. package/dist/lib/long-task-evidence-capability-types.d.ts +13 -1
  85. package/dist/lib/long-task-evidence-findings.js +3 -0
  86. package/dist/lib/long-task-evidence-sensitivity-policy.js +38 -0
  87. package/dist/lib/long-task-evidence-v2.js +7 -1
  88. package/dist/lib/long-task-final-integrity.d.ts +16 -0
  89. package/dist/lib/long-task-final-integrity.js +98 -0
  90. package/dist/lib/long-task-final-v2.js +17 -34
  91. package/dist/lib/long-task-outcome-parser.js +22 -4
  92. package/dist/lib/long-task-playwright-case-evidence.d.ts +2 -0
  93. package/dist/lib/long-task-playwright-case-evidence.js +10 -2
  94. package/dist/lib/long-task-playwright-evidence.d.ts +1 -0
  95. package/dist/lib/long-task-playwright-evidence.js +32 -0
  96. package/dist/lib/long-task-product-shape.d.ts +3 -1
  97. package/dist/lib/long-task-product-shape.js +100 -4
  98. package/dist/lib/long-task-requirement-shape.js +3 -0
  99. package/dist/lib/long-task-root-shape.js +12 -6
  100. package/dist/lib/long-task-runner-freeze.js +16 -0
  101. package/dist/lib/long-task-runtime-types.d.ts +11 -2
  102. package/dist/lib/long-task-semantic-assurance-policy.d.ts +4 -0
  103. package/dist/lib/long-task-semantic-assurance-policy.js +52 -0
  104. package/dist/lib/long-task-semantic-contract-types.d.ts +18 -1
  105. package/dist/lib/long-task-semantic-drift-migration.js +33 -2
  106. package/dist/lib/long-task-semantic-mutation.d.ts +7 -0
  107. package/dist/lib/long-task-semantic-mutation.js +81 -0
  108. package/dist/lib/long-task-shape-primitives.d.ts +1 -1
  109. package/dist/lib/long-task-shape-primitives.js +1 -0
  110. package/dist/lib/long-task-source-authority-types.d.ts +2 -0
  111. package/dist/lib/long-task-source-item-parser.d.ts +1 -1
  112. package/dist/lib/long-task-source-item-parser.js +150 -104
  113. package/dist/lib/long-task-source-markers.d.ts +12 -0
  114. package/dist/lib/long-task-source-markers.js +146 -0
  115. package/dist/lib/long-task-source-target-continuity.d.ts +1 -1
  116. package/dist/lib/long-task-source-target-continuity.js +80 -55
  117. package/dist/lib/long-task-source-target-index.js +7 -29
  118. package/dist/lib/long-task-status-v2.d.ts +1 -0
  119. package/dist/lib/long-task-status-v2.js +2 -2
  120. package/dist/lib/long-task-target-policy.js +20 -0
  121. package/dist/lib/long-task-ui-design-policy.js +27 -1
  122. package/dist/lib/long-task-ui-surface-shape.js +21 -1
  123. package/dist/lib/long-task-ui-surface-types.d.ts +7 -0
  124. package/dist/lib/long-task-verification-preview.d.ts +10 -0
  125. package/dist/lib/long-task-verifier-dependency-closure.d.ts +3 -0
  126. package/dist/lib/long-task-verifier-dependency-closure.js +179 -0
  127. package/dist/lib/long-task-verifier-v2.js +12 -2
  128. package/dist/lib/long-task-workspace.js +5 -1
  129. package/dist/schemas/long-task-delivery-v2/long-task-delivery-v2.schema.json +99 -25
  130. package/migrations/README.md +15 -15
  131. package/package.json +84 -84
  132. package/source-mappings.yaml +25 -25
@@ -319,8 +319,8 @@ function nextAction(status) {
319
319
  if (status.ready_outcomes.length) {
320
320
  const outcome = status.ready_outcomes[0];
321
321
  if (status.outcomes[outcome] === "progress_stale")
322
- return `Targeted evidence for ready Outcome ${outcome} is stale. This is a freshness fact, not an immediate per-edit rerun instruction: coalesce relevant changes, use the cheapest reliable project-owned feedback, and refresh the declared Check before relying on this Outcome or entering Final Gate.`;
323
- return `Implement and verify ready Outcome: ${outcome}.`;
322
+ return `Targeted evidence for Outcome ${outcome} on the acceptance/verification frontier is stale. This is a freshness fact, not an implementation gate or immediate per-edit rerun instruction: coalesce relevant changes and refresh the cheapest reliable declared Check only before relying on this Progress. Implementation may continue, and Final Gate needs no targeted refresh because it reruns every Check.`;
323
+ return `Outcome ${outcome} is on the advisory acceptance/verification frontier. Implementation order remains Goal-owned; run its declared Check when the feedback value justifies the cost, or continue in-scope implementation before the complete Final Gate.`;
324
324
  }
325
325
  return "Create a clean candidate commit; Stop will run the authoritative Live Final Gate.";
326
326
  }
@@ -1,3 +1,11 @@
1
+ const FAMILY_CAPABILITY = {
2
+ browser: "browser-runtime",
3
+ native: "native-runtime",
4
+ desktop: "desktop-runtime",
5
+ service: "service-runtime",
6
+ process: "process-runtime",
7
+ external: "external-runtime",
8
+ };
1
9
  export function validateExecutionTargets(contract, report) {
2
10
  const targets = indexExecutionTargets(contract, report);
3
11
  const requiredTargetRefs = contract.task.target_profile.required_target_refs;
@@ -12,6 +20,13 @@ function indexExecutionTargets(contract, report) {
12
20
  if (targets.has(target.key))
13
21
  issue(report, "execution_target_key_duplicate", target.key);
14
22
  targets.set(target.key, target);
23
+ if (!target.capabilities.length)
24
+ issue(report, "execution_target_capability_required", target.key);
25
+ if (new Set(target.capabilities).size !== target.capabilities.length)
26
+ issue(report, "execution_target_capability_duplicate", target.key);
27
+ const familyCapability = FAMILY_CAPABILITY[target.runtime_family];
28
+ if (!target.capabilities.includes(familyCapability))
29
+ issue(report, "execution_target_family_capability_required", `${target.key}:${familyCapability}`);
15
30
  }
16
31
  if (![...targets.values()].some((target) => target.role === "product"))
17
32
  issue(report, "product_execution_target_required", contract.task.id);
@@ -29,6 +44,11 @@ function validateRequiredTargetRefs(contract, targets, report) {
29
44
  issue(report, "target_profile_required_target_ref_unknown", targetRef);
30
45
  else if (target.role !== "product")
31
46
  issue(report, "target_profile_required_target_must_be_product", targetRef);
47
+ else {
48
+ for (const capability of ["cold-start", "production-root"])
49
+ if (!target.capabilities.includes(capability))
50
+ issue(report, "required_target_capability_missing", `${targetRef}:${capability}`);
51
+ }
32
52
  }
33
53
  }
34
54
  function validateCheckTarget(outcomeKey, check, targets, report) {
@@ -18,6 +18,7 @@ function validateDesignTargets({ outcome, binding, outcomeClaims, checks, carrie
18
18
  unique(target.verification_method_bindings.map((item) => item.assertion_ref), "ui_design_target_verification_assertion_duplicate", label, report);
19
19
  if (!target.verification_method_bindings.length)
20
20
  issue(report, "ui_design_target_verification_methods_required", label);
21
+ const methodArtifactPaths = new Set();
21
22
  for (const [name, values] of [
22
23
  ["source_paths", target.source_paths],
23
24
  ["condition_keys", target.condition_keys],
@@ -49,12 +50,37 @@ function validateDesignTargets({ outcome, binding, outcomeClaims, checks, carrie
49
50
  issue(report, "ui_design_target_assertion_duplicate", `${label}:${methodBinding.assertion_ref}`);
50
51
  if (methodBinding.assertion_ref !== target.conformance_assertion_ref)
51
52
  designAssertionRefs.add(identity);
52
- if (!check.positive_assertions.some((item) => item.key === methodBinding.assertion_ref))
53
+ const methodAssertion = check.positive_assertions.find((item) => item.key === methodBinding.assertion_ref);
54
+ if (!methodAssertion)
53
55
  issue(report, "ui_design_target_verification_assertion_unknown", `${label}:${methodBinding.method}:${methodBinding.assertion_ref}`);
56
+ else if (!methodAssertion.evidence_capabilities.includes("design_method"))
57
+ issue(report, "ui_design_target_verification_capability_required", `${label}:${methodBinding.method}:design_method`);
58
+ const conditionKeys = methodBinding.evidence_artifacts.map((item) => item.condition_key);
59
+ unique(conditionKeys, "ui_design_method_evidence_condition_duplicate", `${label}:${methodBinding.method}`, report);
60
+ if (!sameSet(conditionKeys, target.condition_keys))
61
+ issue(report, "ui_design_method_evidence_conditions_mismatch", `${label}:${methodBinding.method}`);
62
+ for (const artifact of methodBinding.evidence_artifacts) {
63
+ for (const [kind, artifactPath] of [
64
+ ["record", artifact.path],
65
+ ["observation", artifact.observation_path],
66
+ ]) {
67
+ if (methodArtifactPaths.has(artifactPath))
68
+ issue(report, "ui_design_method_evidence_artifact_reused", `${label}:${kind}:${artifactPath}`);
69
+ methodArtifactPaths.add(artifactPath);
70
+ if (!check.artifact_globs.some((pattern) => matchesRepoPattern(artifactPath, pattern)))
71
+ issue(report, "ui_design_method_evidence_artifact_glob_missing", `${label}:${methodBinding.method}:${kind}:${artifactPath}`);
72
+ }
73
+ }
54
74
  }
55
75
  validateDesignFiles(target, check, label, report);
56
76
  }
57
77
  }
78
+ function sameSet(left, right) {
79
+ const leftSet = [...new Set(left)].sort();
80
+ const rightSet = [...new Set(right)].sort();
81
+ return (leftSet.length === rightSet.length &&
82
+ leftSet.every((value, index) => value === rightSet[index]));
83
+ }
58
84
  function validateDesignAssertion(target, check, label, report) {
59
85
  const assertion = check.positive_assertions.find((item) => item.key === target.conformance_assertion_ref);
60
86
  if (!assertion) {
@@ -1,4 +1,5 @@
1
1
  import { DESIGN_RESOURCE_VERIFICATION_METHODS } from "./design-resource-handoff-types.js";
2
+ import { EXECUTION_TARGET_CAPABILITIES } from "./execution-target-capabilities.js";
2
3
  import { array, key, literal, object, repositoryFile, repositoryFiles, string, strings, } from "./long-task-shape-primitives.js";
3
4
  export function parseSurfaceBindings(value, label) {
4
5
  return array(value, label).map((item, index) => {
@@ -67,6 +68,7 @@ function parseAcceptanceBlockers(value, label) {
67
68
  "refs",
68
69
  "source_item_refs",
69
70
  "verification_methods",
71
+ "required_capabilities",
70
72
  "rationale",
71
73
  ]);
72
74
  return {
@@ -75,6 +77,7 @@ function parseAcceptanceBlockers(value, label) {
75
77
  refs: strings(row.refs, `${itemLabel}.refs`),
76
78
  source_item_refs: strings(row.source_item_refs, `${itemLabel}.source_item_refs`),
77
79
  verification_methods: array(row.verification_methods, `${itemLabel}.verification_methods`).map((method, methodIndex) => literal(method, DESIGN_RESOURCE_VERIFICATION_METHODS, `${itemLabel}.verification_methods[${methodIndex}]`)),
80
+ required_capabilities: array(row.required_capabilities, `${itemLabel}.required_capabilities`).map((capability, capabilityIndex) => literal(capability, EXECUTION_TARGET_CAPABILITIES, `${itemLabel}.required_capabilities[${capabilityIndex}]`)),
78
81
  rationale: string(row.rationale, `${itemLabel}.rationale`),
79
82
  };
80
83
  });
@@ -82,10 +85,27 @@ function parseAcceptanceBlockers(value, label) {
82
85
  function parseVerificationMethodBindings(value, label) {
83
86
  return array(value, label).map((item, index) => {
84
87
  const itemLabel = `${label}[${index}]`;
85
- const row = object(item, itemLabel, ["method", "assertion_ref"]);
88
+ const row = object(item, itemLabel, [
89
+ "method",
90
+ "assertion_ref",
91
+ "evidence_artifacts",
92
+ ]);
86
93
  return {
87
94
  method: literal(row.method, DESIGN_RESOURCE_VERIFICATION_METHODS, `${itemLabel}.method`),
88
95
  assertion_ref: key(row.assertion_ref, `${itemLabel}.assertion_ref`),
96
+ evidence_artifacts: array(row.evidence_artifacts, `${itemLabel}.evidence_artifacts`).map((artifact, artifactIndex) => {
97
+ const artifactLabel = `${itemLabel}.evidence_artifacts[${artifactIndex}]`;
98
+ const entry = object(artifact, artifactLabel, [
99
+ "condition_key",
100
+ "path",
101
+ "observation_path",
102
+ ]);
103
+ return {
104
+ condition_key: key(entry.condition_key, `${artifactLabel}.condition_key`),
105
+ path: repositoryFile(entry.path, `${artifactLabel}.path`),
106
+ observation_path: repositoryFile(entry.observation_path, `${artifactLabel}.observation_path`),
107
+ };
108
+ }),
89
109
  };
90
110
  });
91
111
  }
@@ -1,8 +1,14 @@
1
1
  import type { DesignResourceVerificationMethod } from "./design-resource-handoff-types.js";
2
+ import type { ExecutionTargetCapabilityV2 } from "./execution-target-capabilities.js";
2
3
  export type DesignTargetInterpretationV2 = "exact_target" | "constraint";
3
4
  export interface DeliveryDesignVerificationBindingV2 {
4
5
  method: DesignResourceVerificationMethod;
5
6
  assertion_ref: string;
7
+ evidence_artifacts: Array<{
8
+ condition_key: string;
9
+ path: string;
10
+ observation_path: string;
11
+ }>;
6
12
  }
7
13
  export interface DeliveryDesignTargetV2 {
8
14
  key: string;
@@ -23,6 +29,7 @@ export interface DeliveryDesignAcceptanceBlockerV2 {
23
29
  refs: string[];
24
30
  source_item_refs: string[];
25
31
  verification_methods: DesignResourceVerificationMethod[];
32
+ required_capabilities: ExecutionTargetCapabilityV2[];
26
33
  rationale: string;
27
34
  }
28
35
  export interface DeliverySurfaceBindingV2 {
@@ -40,6 +40,16 @@ interface CounterfactualExecutionPreviewV1 {
40
40
  type: "replace_file";
41
41
  path: string;
42
42
  fixture_path: string;
43
+ } | {
44
+ type: "replace_json_value";
45
+ path: string;
46
+ pointer: string;
47
+ value: unknown;
48
+ } | {
49
+ type: "replace_text";
50
+ path: string;
51
+ match: string;
52
+ replacement: string;
43
53
  };
44
54
  runner: RunnerPreviewV1;
45
55
  }
@@ -0,0 +1,3 @@
1
+ import type { WorkspaceManifestV2 } from "./long-task-delivery-types.js";
2
+ export declare function freezeLocalVerifierDependencyClosure(repository: string, roots: Iterable<string>, manifest: WorkspaceManifestV2, runtimeOwnedPatterns?: readonly string[]): Promise<Record<string, string>>;
3
+ export declare function packageScriptVerifierRoots(script: string, packageFile: string, manifest: WorkspaceManifestV2): string[];
@@ -0,0 +1,179 @@
1
+ import { readFile } from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { classifyRepositoryPatternOverlap, matchesRepoPattern, } from "./long-task-paths.js";
4
+ import { assertProtectedRepositoryFile } from "./long-task-protected-files.js";
5
+ import { sha256Hex } from "./strict-codec.js";
6
+ const SCRIPT_EXTENSIONS = new Set([
7
+ ".js",
8
+ ".jsx",
9
+ ".mjs",
10
+ ".cjs",
11
+ ".ts",
12
+ ".tsx",
13
+ ".mts",
14
+ ".cts",
15
+ ]);
16
+ const RESOLUTION_EXTENSIONS = [
17
+ "",
18
+ ".js",
19
+ ".mjs",
20
+ ".cjs",
21
+ ".jsx",
22
+ ".ts",
23
+ ".mts",
24
+ ".cts",
25
+ ".tsx",
26
+ ".json",
27
+ ];
28
+ export async function freezeLocalVerifierDependencyClosure(repository, roots, manifest, runtimeOwnedPatterns = []) {
29
+ const available = new Set(manifest.files.map((file) => file.path));
30
+ const result = {};
31
+ const queued = [...new Set(roots)].filter((file) => SCRIPT_EXTENSIONS.has(path.posix.extname(file).toLowerCase()));
32
+ const visited = new Set();
33
+ while (queued.length) {
34
+ const relative = queued.shift();
35
+ if (visited.has(relative))
36
+ continue;
37
+ visited.add(relative);
38
+ if (!available.has(relative))
39
+ throw new Error(`verification_dependency_not_found:${relative}`);
40
+ const absolute = await assertProtectedRepositoryFile(repository, path.join(repository, ...relative.split("/")), "verification_dependency");
41
+ const bytes = await readFile(absolute);
42
+ result[relative] = sha256Hex(bytes);
43
+ const source = bytes.toString("utf8");
44
+ if (hasNonLiteralLoader(source))
45
+ throw new Error(`verification_dependency_dynamic_unresolved:${relative}`);
46
+ for (const specifier of staticSpecifiers(source)) {
47
+ if (!isLocalSpecifier(specifier))
48
+ continue;
49
+ const dependency = resolveLocalSpecifier(relative, specifier, available);
50
+ const unresolvedBase = localSpecifierBase(relative, specifier);
51
+ if ((dependency &&
52
+ runtimeOwnedPatterns.some((pattern) => matchesRepoPattern(dependency, pattern))) ||
53
+ (!dependency &&
54
+ unresolvedBase &&
55
+ runtimeOwnedPatterns.some((pattern) => runtimePatternOwns(unresolvedBase, pattern))))
56
+ continue;
57
+ if (!dependency)
58
+ throw new Error(`verification_dependency_not_found:${relative}:${specifier}`);
59
+ if (SCRIPT_EXTENSIONS.has(path.posix.extname(dependency).toLowerCase()))
60
+ queued.push(dependency);
61
+ else {
62
+ const dependencyFile = await assertProtectedRepositoryFile(repository, path.join(repository, ...dependency.split("/")), "verification_dependency");
63
+ result[dependency] = sha256Hex(await readFile(dependencyFile));
64
+ }
65
+ }
66
+ }
67
+ return sortRecord(result);
68
+ }
69
+ export function packageScriptVerifierRoots(script, packageFile, manifest) {
70
+ const tokens = staticPackageScriptTokens(script);
71
+ if (!tokens.length || !["node", "node.exe"].includes(tokens[0].toLowerCase()))
72
+ throw new Error("package_script_dependency_closure_unresolved:node_entry_required");
73
+ if (tokens.length < 2 || tokens[1].startsWith("-"))
74
+ throw new Error("package_script_dependency_closure_unresolved:static_entry_required");
75
+ const packageDirectory = path.posix.dirname(packageFile);
76
+ const candidate = path.posix.normalize(path.posix.join(packageDirectory === "." ? "" : packageDirectory, tokens[1]));
77
+ if (candidate === ".." ||
78
+ candidate.startsWith("../") ||
79
+ !manifest.files.some((file) => file.path === candidate) ||
80
+ !SCRIPT_EXTENSIONS.has(path.posix.extname(candidate).toLowerCase()))
81
+ throw new Error(`package_script_dependency_closure_unresolved:entry_not_found:${tokens[1]}`);
82
+ return [candidate];
83
+ }
84
+ function staticPackageScriptTokens(script) {
85
+ const tokens = [];
86
+ let current = "";
87
+ let quote = null;
88
+ for (let index = 0; index < script.length; index += 1) {
89
+ const character = script[index];
90
+ if (!quote && /\s/u.test(character)) {
91
+ if (current) {
92
+ tokens.push(current);
93
+ current = "";
94
+ }
95
+ continue;
96
+ }
97
+ if (character === "'" || character === '"') {
98
+ if (!quote) {
99
+ quote = character;
100
+ continue;
101
+ }
102
+ if (quote === character) {
103
+ quote = null;
104
+ continue;
105
+ }
106
+ }
107
+ if ((!quote && /[&|;<>()]/u.test(character)) ||
108
+ character === "`" ||
109
+ character === "$" ||
110
+ character === "%" ||
111
+ character === "!")
112
+ throw new Error("package_script_dependency_closure_unresolved:dynamic_shell_syntax");
113
+ current += character;
114
+ }
115
+ if (quote)
116
+ throw new Error("package_script_dependency_closure_unresolved:unterminated_quote");
117
+ if (current)
118
+ tokens.push(current);
119
+ return tokens;
120
+ }
121
+ function staticSpecifiers(source) {
122
+ const result = [];
123
+ const patterns = [
124
+ /\b(?:import|export)\s+(?:[^"'`]*?\s+from\s+)?["']([^"']+)["']/gu,
125
+ /\bimport\s*\(\s*["']([^"']+)["']\s*\)/gu,
126
+ /\brequire\s*\(\s*["']([^"']+)["']\s*\)/gu,
127
+ /\brequire\.resolve\s*\(\s*["']([^"']+)["']\s*\)/gu,
128
+ /\bmodule\.require\s*\(\s*["']([^"']+)["']\s*\)/gu,
129
+ /\bnew\s+URL\s*\(\s*["']([^"']+)["']\s*,\s*import\.meta\.url\s*\)/gu,
130
+ ];
131
+ for (const pattern of patterns)
132
+ for (const match of source.matchAll(pattern))
133
+ result.push(match[1]);
134
+ return [...new Set(result)];
135
+ }
136
+ function hasNonLiteralLoader(source) {
137
+ return (/\b(?:import|require)\s*\(\s*(?!["'])[^)]/u.test(source) ||
138
+ /\brequire\.resolve\s*\(\s*(?!["'])[^)]/u.test(source) ||
139
+ /\bmodule\.require\s*\(\s*(?!["'])[^)]/u.test(source) ||
140
+ /\bnew\s+URL\s*\(\s*(?!["'])[^,]+,\s*import\.meta\.url\s*\)/u.test(source) ||
141
+ /\bcreateRequire\b/u.test(source));
142
+ }
143
+ function isLocalSpecifier(specifier) {
144
+ return (specifier.startsWith("./") ||
145
+ specifier.startsWith("../") ||
146
+ specifier.startsWith("/"));
147
+ }
148
+ function resolveLocalSpecifier(importer, specifier, available) {
149
+ const base = localSpecifierBase(importer, specifier);
150
+ if (!base)
151
+ return null;
152
+ if (base.startsWith("../") || base === "..")
153
+ return null;
154
+ for (const extension of RESOLUTION_EXTENSIONS) {
155
+ const candidate = `${base}${extension}`;
156
+ if (available.has(candidate))
157
+ return candidate;
158
+ }
159
+ for (const extension of RESOLUTION_EXTENSIONS.slice(1)) {
160
+ const candidate = `${base}/index${extension}`;
161
+ if (available.has(candidate))
162
+ return candidate;
163
+ }
164
+ return null;
165
+ }
166
+ function localSpecifierBase(importer, specifier) {
167
+ const base = specifier.startsWith("/")
168
+ ? specifier.slice(1)
169
+ : path.posix.normalize(path.posix.join(path.posix.dirname(importer), specifier));
170
+ return base === ".." || base.startsWith("../") ? null : base;
171
+ }
172
+ function runtimePatternOwns(base, pattern) {
173
+ return (matchesRepoPattern(base, pattern) ||
174
+ classifyRepositoryPatternOverlap(`${base}/**`, pattern).status ===
175
+ "proven_overlap");
176
+ }
177
+ function sortRecord(value) {
178
+ return Object.fromEntries(Object.entries(value).sort(([left], [right]) => left.localeCompare(right)));
179
+ }
@@ -109,8 +109,17 @@ export async function runDeliveryChecks(compiled, snapshot, checks, includeCount
109
109
  }
110
110
  const counterfactualFindings = [];
111
111
  if (includeCounterfactuals) {
112
+ // Counterfactual sensitivity is a closure condition for an otherwise
113
+ // passing proof. A failed or externally blocked owning Check already
114
+ // blocks acceptance; rerunning its oracle in a mutated sandbox can only
115
+ // obscure that primary status (for example, by turning a typed external
116
+ // blocker into an integrity failure).
117
+ const passingCheckIds = new Set(mainCheckResults
118
+ .filter((result) => result.status === "passed")
119
+ .map((result) => result.internal_id));
112
120
  const selectedGlobalCheckKeys = new Set(checks
113
- .filter((check) => check.outcome_key === null)
121
+ .filter((check) => check.outcome_key === null &&
122
+ passingCheckIds.has(check.internal_id))
114
123
  .map((check) => check.key));
115
124
  if (selectedGlobalCheckKeys.size)
116
125
  counterfactualFindings.push(...(await evaluateGlobalCounterfactuals(compiled, snapshot.root, selectedGlobalCheckKeys, snapshot.manifest)));
@@ -119,7 +128,8 @@ export async function runDeliveryChecks(compiled, snapshot, checks, includeCount
119
128
  .filter((key) => Boolean(key)));
120
129
  for (const outcome of compiled.outcomes.filter((item) => outcomeKeys.has(item.key))) {
121
130
  const selectedKeys = new Set(checks
122
- .filter((check) => check.outcome_key === outcome.key)
131
+ .filter((check) => check.outcome_key === outcome.key &&
132
+ passingCheckIds.has(check.internal_id))
123
133
  .map((check) => check.key));
124
134
  counterfactualFindings.push(...(await evaluateOutcomeCounterfactuals({
125
135
  ...outcome,
@@ -4,7 +4,11 @@ import os from "node:os";
4
4
  import path from "node:path";
5
5
  import { canonicalValueJson, sha256Hex } from "./strict-codec.js";
6
6
  export async function repositoryRoot(start) {
7
- return path.resolve(await gitOutput(path.resolve(start), ["rev-parse", "--show-toplevel"]));
7
+ const resolved = path.resolve(start);
8
+ const gitEntry = await stat(path.join(resolved, ".git")).catch(() => null);
9
+ if (gitEntry?.isDirectory() || gitEntry?.isFile())
10
+ return resolved;
11
+ return path.resolve(await gitOutput(resolved, ["rev-parse", "--show-toplevel"]));
8
12
  }
9
13
  export async function gitCommonDir(root) {
10
14
  return path.resolve(await gitOutput(root, [