Skip to content

refactor(contracts): move runtime-fact exports into their own manifest - #1428

Open
doublewhy wants to merge 2 commits into
devfrom
1418-runtime-fact-exports
Open

doublewhy wants to merge 2 commits into
devfrom
1418-runtime-fact-exports

Conversation

@doublewhy

@doublewhy doublewhy commented Oct 9, 2026 •

Copy link
Copy Markdown
Contributor

Summary

implementations/python/packages/raes_contracts/contracts/_exports.py is 499 lines. Package files are capped at 500 lines, and the oversized-file allowlist is empty. Publishing the #1366 inject-trigger contracts through the raes_contracts.contracts facade adds a manifest import and a spread entry, which would push the file over the cap. This PR moves the contiguous runtime-fact binding-plane family (18 names) into _runtime_fact_exports.py and spreads it where the names were. PUBLIC_EXPORTS keeps the same membership and order, and _exports.py drops to 483 lines.

Any .py change under implementations/python/packages changes the implementation digest that the research-evidence captures pin. This PR therefore also republishes both captures against this source, as #1404 did. Outcomes and claim limits are unchanged.

Requirement UIDs

  • None. This is a behavior-neutral refactor of the facade's export manifest with no requirement scope.

Related Issues

Closes #1418

ADR Impact

  • None.

Changes

  • raes_contracts/contracts/_runtime_fact_exports.py: new RUNTIME_FACT_EXPORTS list with the same 18 names in the same order, following _mixed_composition_exports.py.
  • raes_contracts/contracts/_exports.py: imports RUNTIME_FACT_EXPORTS and spreads it in place of the 18 literal names.
  • Research evidence: specification-coverage release 69.0.0 and formal-validation release 70.0.0 (baseline 69.0.0, no deviations) record this source's implementation and contract-models digests. Their revision pins advance in tools/check_specification_coverage.py, tools/formal_semantic_validation/, the three evidence test modules and both research indexes, and the stale "through 66.0.0" historical-validation message in _releases.py is corrected to 69.0.0 (dev's historical retest set already ends at 68.0.0). The formal current-release assertion now expects no deviations, because nothing changed compiled output.

Test Plan

  • Unit tests pass
  • Integration tests pass if applicable
  • Full completion suite required in CI before merge
  • No coverage regression: not measured locally. The new module is a list of names that _exports.py imports, and canonical / coverage-reduce runs in CI.

PUBLIC_EXPORTS built from origin/dev's _exports.py and from this branch are identical in order and membership (570 names), and raes_contracts.contracts.__all__ == PUBLIC_EXPORTS.

Before the republish, at 0e79e14, tools/check_specification_coverage.py reported research-evidence-source-state and a stale contract-models digest, and tools/check_formal_semantic_validation.py reported research-evidence-source-state. After it, both checkers pass.

pytest over test_specification_coverage.py, test_formal_semantic_validation.py, test_issue_989_versioned_evidence.py, test_contracts_facade_exports.py and test_conformance_facade_parity.py passed: 214 passed and 19 deselected in the default selection, and 19 passed and 214 deselected with -m integration. test_conformance_facade_parity.py covers the separate raes_conformance.conformance facade and is unrelated to this change.

nox -s contracts -- --base-rev origin/dev passed all 14 stages, including schema publication, generated-schema drift, specification coverage, formal semantic validation and JSON artifact validation. nox -s lint and make policy passed. nox -s verify-fast-feedback -- --base-rev origin/dev passed every stage it ran. It skipped YAML syntax because no YAML changed, and requirement governance because the branch carries no requirement UID.

Ground Control Checks

  • Repository policy command passes
  • Pre-push code review and test-quality review: not run for this lane; an independent review runs before the PR is marked ready.

make policy passed locally, with requirement governance skipped as described in the Test Plan.

Traceability

  • IMPLEMENTS: (none; requirement-free refactor)
  • TESTS: (none added; test_contracts_facade_exports.py checks that PUBLIC_EXPORTS names are unique and resolve on the facade, but no test pins the manifest's order or that the 18 moved names stay in it. Order and membership were compared once against origin/dev (570 names), as the Test Plan records, not by a test)

Checklist

  • Code follows the project coding standards; ruff format and ruff check pass on both modules
  • FM: not applicable, no semantic change; no executable or runtime adoption is claimed
  • No published schema, fixture, model or public name changes; tools/check_generated_schemas.py passes
  • PR title is a Conventional Commit; refactor because nothing user-visible changes
  • No architectural docs describe the manifest layout; the API reference documents modules with automodule, not the facade's __all__

Documentation

Updated: the specification-coverage and formal-validation research indexes record the new releases.

The facade manifest _exports.py is at 499 of 500 lines. Move the contiguous runtime-fact binding-plane family into _runtime_fact_exports.py and spread it in place, so PUBLIC_EXPORTS keeps identical order and membership and the next contract family fits under the cap.
Specification-coverage release 69.0.0 and formal-validation release 70.0.0 bind the current implementation digest; outcomes and claim limits are unchanged.
@doublewhy

doublewhy commented Oct 9, 2026 •

Copy link
Copy Markdown
Contributor Author

Open pull requests from doublewhy: index and suggested merge order

This lists the 81 open pull requests from this account across rae, lilrae, env-packs, hub, adapters and workbench, grouped by area, with a suggested merge order. Nothing here needs a reply. Any order works: when something merges, I rebase the PRs that depend on it and republish evidence where needed. The order below needs the fewest rebases and evidence regenerations.

State at 2026-10-10 14:10 UTC:

Second review, 2026-10-10

A second, independent review of every ready PR found a real problem in 37 of the 49 that were ready on 2026-10-09. All 37 are now fixed: three needed only a description change (#1424, #1440 and #1456), and the other 34 were fixed and then re-reviewed by a separate reviewer, who passed each one. Each PR's description says what changed.

Every required check passes on those PRs except where a known secret problem applies: sonar fails on rae pushes since 16:25Z and on env-packs, with the SONAR_TOKEN 403 described in OpenRAE/hub#46; adapters and workbench still fail SonarCloud on their older token; and workbench audit fails on #71 to #73 until #74 merges.

rae: changes that leave the research evidence alone

These PRs touch nothing the research evidence binds, so they never force a republish. They can merge at any time, in any order, including between the evidence merges below. One exception: #1426 asserts the exact text of a diagnostic that #1446 rewords. Whichever of the two merges second needs a one-line test update, and I will push it.

PR Issue Change
#1415 #1414 Release workflow names the repository when it uploads assets
#1417 #1416 Protect-files hook drops the stale generated-schema rule
#1432 #1427 Post-edit policy hook checks repository-relative paths
#1455 #1454 Policy gate fails when conftest cannot evaluate its policies
#1420 #954 Public docs publication-boundary guard and reporting contact
#1424 #627 Environment pack terminology across docs and specs
#1452 #1412 VS Code support assessment for SDL authoring
#1461 #1460 Fixture provenance audit record
#1426 #297 Behavior authoring verification tests
#1443 #1435 API-404 clauses mapped to each profile's evidence
#1447 #253 Shared-state and derived-context contract composition tests
#1453 none (#1344 audit) Libvirt TechVault fakes from a captured readback
#1459 none (#1344 audit) A lease closed in a forked child keeps the parent's locks
#1470 none The first-scenario tutorial shows what format --check reports, then a check that passes
#1471 #219 The behavior-model spec drops retired classification fields (one slice of #219)
#1472 none (#1344 audit) Atomicity fakes fail from SQLite's own COMMIT
#1474 #1473 Gates list changed paths NUL-separated, so names git quotes reach them
#1476 #1475 Maintained-client downloads pin HTTP/1.1
#1478 none The controlled-vocabularies page calls the three behavior catalogs closed, as their records say

Two stacks. I rebase the next PR after each merge.

#1422 (#712) adds a gate over every schema under contracts/schemas/: each one needs a live IMPLEMENTS → SPEC owner. Six schemas added by #1436, #1449 and #1442 have no owner yet:

  • inject-trigger-request-v1
  • inject-occurrence-v1
  • inject-occurrence-outcome-v1
  • inject-occurrence-correlation-v1
  • mixed-backend-execution-binding-v1
  • mixed-backend-stage-report-v1

Git sees no conflict, so whichever side merges second would turn verify red on dev. #1422 is a draft until #1449 and #1442 merge; I will then rebase it, add the owners and mark it ready.

rae: changes bound by the research evidence

These 20 PRs change source that the research evidence binds. Each one carries the next releases, so only one can merge at a time.

  • After each evidence merge, the other evidence PRs conflict, but only in docs/research/** and the revision pins.
  • I then republish the next PR in the list on top of dev. That takes about 10 minutes, plus 20 to 30 minutes of CI.
  • The others wait their turn instead of rerunning CI after every merge. To take a different one next, comment on it and I will republish it first.

The stacked PRs (#1436, #1449, #1444, #1465, #1467, #1469) already carry releases one above the PR below them. After the lower PR merges, a stacked PR conflicts until I rebase it to drop the lower PR's commits. That rebase needs no regeneration, but CI runs again.

About 1,800 added lines in each evidence PR are the regenerated captures and pins. The code change is in the commits before the last one.

Order PR Issue Carries now (spec/formal) In this order At its turn
1 #1428 #1418 69/70 69/70 merge as is
2 #1436 #1423 70/71, on #1428 70/71 rebase
3 #1449 #1366 71/72, on #1436 71/72 rebase
4 #1442 #1371 69/70 72/73 resolve with the #1366 chain, republish
5 #1440 #298 69/70 73/74 republish
6 #1464 #1462 69/70 74/75 republish
7 #1431 #1091 69/70 75/76 republish, with #1444
8 #1444 #8 70/71, on #1431 76/77 rebase
9 #1429 #1421 69/70 77/78 republish
10 #1433 #1425 69/70 78/79 republish
11 #1441 #1434 69/70 79/80 republish
12 #1448 #1439 69/70 80/81 republish
13 #1456 #1450 69/70 81/82 republish
14 #1457 #1451 69/70 82/83 republish
15 #1463 #307 69/70 83/84 republish, with #1465
16 #1465 #309 70/71, on #1463 84/85 rebase
17 #1446 #1339 69/70 85/86 republish
18 #1466 (draft) #306 69/70 86/87 resolve with #1463 and #1465, republish, with #1467 and #1469
19 #1467 (draft) #308 70/71, on #1466 87/88 rebase
20 #1469 (draft) #310 71/72, on #1467 88/89 rebase
21 #1480 #1479 69/70 89/90 republish
22 #1483 #1482 69/70 90/91 republish
23 #1484 #297 70/71, on #1480 91/92 rebase after #1480, then republish

dev carries specification coverage 68.0.0 and formal validation 69.0.0. If all 23 merge in this order, it ends at 91.0.0 and 92.0.0.

One size limit also shapes the order. test_issue_1241 caps contracts/schemas/sdl/materialized-scenario-v1.json at 512,000 bytes. dev has 506,235 bytes, and #1463 with #1465 brings it to 511,867. #1467 now also shares repeated propertyNames rules in the existing lossless schema factoring, which saves 4,505 bytes. In a local merge of this whole order, the file ends at 508,366 bytes.

Why this order:

lilrae

OpenRAE/lilrae#1270 goes first. It fixes the dependency-vulnerability and Trivy filesystem scans and every image lane except web, whose caddy binary still carries Go and x/net advisories: no caddy:2-alpine build with Go 1.26.9 or later exists yet. Once one is published, a digest bump in web/Dockerfile clears that last lane. The 18 drafts below stay drafts until the scans pass on dev.

Once the scans pass on dev, I suggest this order:

  1. docs(requirements): reconcile remaining records with their issues and ADR-035 lilrae#1252 (issue 1245) and docs: remove the workflow platform product name from public docs lilrae#1254 (issue 1243).
  2. chore: remove the unused in-tree Kali wrapper lilrae#1258 (issue 987), then docs: align Kali, published-port and Docker socket docs with the realized runtime lilrae#1263 (docs half of issue 954).
  3. fix: remove the stale all-interface DNS publication from the Compose stub lilrae#1255 (issue 1004), then test: check TechVault runtime properties on the rendered pack, not the Compose stub lilrae#1261 (tests half of issue 954).
  4. fix(mcp): harvest Kali captures from the workspace-scoped capture container lilrae#1257 (issue 1242), fix(workbench): enforce provider deadlines and clean up owned child processes lilrae#1260 (issue 963) and fix(deployment): explain how to recover from an unowned service index lilrae#1264 (issue 990).
  5. fix: write generated environment files safely lilrae#1256 (issue 966), then fix!: bind base-container operational secrets explicitly lilrae#1262 and fix!: bind compose operational secrets explicitly lilrae#1269 (issue 965).
  6. fix: refuse rootless Docker before lab start and drop the cert-generator mapping lilrae#1253 (issue 1053), then fix: start from cached images without registry lookups and report admission time lilrae#1259 (issue 953), feat: report what a failed lab start leaves behind and add --teardown-on-failure lilrae#1265 (issue 952), and feat(cli): add aptl doctor to check the host and Docker runtime before a start lilrae#1266, feat(cli): give doctor, lab start, stop and status stable JSON output and exit status lilrae#1267 and feat(cli): add aptl lab reset to return the lab to a clean state lilrae#1268 (issue 1218).

The issue 965 and issue 1218 stacks each add a row at the same place in docs/reviews/962-lilrae-readiness/tracked-file-inventory.tsv. Whichever merges second keeps both rows. Both earlier to-dos are done: every stack now sits on the current heads of the PRs below it, and OpenRAE/lilrae#1263 no longer has a line that the new Vale rule in OpenRAE/lilrae#1254 refuses.

env-packs

OpenRAE/env-packs#433 (part of issue 413), then OpenRAE/env-packs#434 (completes issue 413). #434 contains #433's commit, so I will rebase it after #433 merges. Issue 414 is blocked by #1481, and neither PR addresses it.

hub

OpenRAE/hub#44 (issue 41) and OpenRAE/hub#45 (issue 39), in either order. Both wait on OpenRAE/hub#46.

adapters

OpenRAE/adapters#98, #99, #100, then #101: the inventories for issues 87, 85, 86 and 88.

  • They are stacked only because each one adds a single mkdocs.yml nav line.
  • dev requires up-to-date branches, so I rebase each one after the previous merge. That push dismisses earlier approvals.
  • All four wait on ci: SonarCloud rejects the repository SONAR_TOKEN adapters#102.
  • Each PR only references its issue, so issues 85 to 88 stay open.

workbench

  1. chore(deps): update locked cryptography, django, pyjwt and sqlparse for published advisories workbench#74 (issue 76) first, because it fixes the audit job.
  2. Then ci: run lint as its own job and spread pytest over the runner's CPUs workbench#73 (issue 61). It also edits uv.lock, so I will rerun uv lock --check after rebasing it.
  3. Then ci: add an OpenSSF Scorecard workflow and README badge workbench#71 (issue 53) and chore: use one pre-push Codex review and disable automatic review disposition workbench#72 (issue 60).

After #74 merges, I will rebase #71 to #73 so that audit runs again.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant