Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
45 changes: 42 additions & 3 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,44 @@

### Changed

- Repository-pack access and the evidence path rules leave the package root
(Refs #451). Root `_repo_pack_data.py` and `evidence_paths.py` are removed in the
same change, with no forwarding shells or `sys.modules` aliases:
- `inferrsi._repo_pack_data` → `inferrsi.resources.repository_packs`
(`REPO_TYPES`, `repository_pack`).
- `inferrsi.evidence_paths` → `inferrsi.contracts.evidence` for
`EVIDENCE_SEGMENTS`, `campaign_evidence_root` and `evidence_subpaths`, and
`inferrsi.apps.evidence_layout` for `ensure_evidence_layout`.
- Importing either old module path fails, and a pickle that names one of these
functions by an old module path no longer loads. Such external pickles need
explicit migration or the prior release; new pickles name the canonical
modules above. `src/` has no pickle usage, and frozen evidence is not
rewritten.
- Signatures, return values and errors are unchanged. `REPO_TYPES` stays one
seven-entry tuple object for every remaining consumer: root `catalog`,
`knowledge.catalog` and the CLI arguments. The reader keeps the anchor
`files("inferrsi").joinpath("harness", "data", "repo_packs", ...)` and imports
no `inferrsi` module, and `resources/__init__.py` imports nothing. The seven
`pack.json` files keep their bytes and stay under `harness/data/`.
- `contracts.evidence` only builds paths and does no filesystem I/O.
`apps.evidence_layout` creates the four directories in the same order with
the same `mkdir(parents=True, exist_ok=True)` call. `contracts/__init__.py`
still re-exports only `RunSpec`.
- `docs/legacy-knowledge-manifest.json` relocks the neutral leaf's module and
file path and points the `catalog` and `infra.inspection` pairs at the new
module. The leaf's bytes and locked hash value are unchanged, and the nine
compatibility pairs remain. That relock requires formal architecture review:
passing tests do not supply it, and the implementer does not self-approve it.
- The exact root inventory in `tests/test_package_root_inventory.py` shrinks
from 23 to 21 tracked files: `__init__.py`, `__main__.py`,
`_mindie_read_worker.py`, `_skill_selection.py`, `_source_snapshot.py`,
`arguments.py`, `benchmark_operations.py`, `catalog.py`, `cli.py`,
`evaluation.py`, `execution.py`, `inspection.py`, `knowledge_operations.py`,
`knowledge_store.py`, `mindie_context.py`, `mindie_mcp.py`,
`mindie_project.py`, `reporting.py`, `research.py`, `skill_catalog.py` and
`summary_chart.py`. It is an exact set that each later removal shrinks, not
the final two-file root. The build-generated `_version.py` is wheel metadata,
not a tracked root file.
- Shared technical contracts now live in `inferrsi.contracts` (Refs #451). The four
root files `_json_v1.py`, `runspec.py`, `claim.py`, and `contracts.py` are removed
in the same change. Canonical implementations are `contracts/json_v1.py`,
Expand All @@ -17,9 +55,10 @@
prior release; new pickles name the canonical implementation modules.
- Canonical JSON bytes, error stages, RunSpec serialization/validation, and
Verdict values are unchanged. Frozen evidence is not rewritten.
- `tests/test_package_root_inventory.py` locks the exact current 23-file root
inventory and rejects unexpected additions; each later removal must shrink
that set in its own PR, rather than requiring the final two-file root now.
- `tests/test_package_root_inventory.py` locked the exact 23-file root
inventory that this change left and rejects unexpected additions; each later
removal must shrink that set in its own PR, rather than requiring the final
two-file root now. The entry above shrinks it to 21.
- The `inferrsi.observability` package is dissolved into its owning packages. No forwarding
modules remain, so imports must use the new paths:
- `campaign_records`, `campaign_trace`, `optimization_log`, `optimization_trace`,
Expand Down
12 changes: 9 additions & 3 deletions docs/architecture.md
Original file line number Diff line number Diff line change
Expand Up @@ -169,17 +169,23 @@ src/inferrsi/
run.py Old run composed from Harness, Benchmark and the report
evaluation.py Old evaluate entry: RunSpec to the Benchmark gates
reporting.py HTML evidence report
runspec.py, contracts.py Immutable experiment contract and compatibility export
contracts/
runspec.py Immutable experiment contract; the initializer re-exports only RunSpec
json_v1.py Canonical inferrsi-json-v1 encoder and decoder
claim.py Campaign verdict labels PASS/FAIL/INCONCLUSIVE; rules only
evidence.py Evidence segments and per-campaign path rules; no filesystem I/O
resources/
__init__.py Import-free initializer
repository_packs.py Neutral REPO_TYPES and pack.json reader; imports no inferrsi module
catalog.py Knowledge search and cited context
skill_catalog.py Packaged/default or custom skill metadata/body/resource resolution
knowledge_operations.py Normalized reads and bounded Collect (KnowledgeReader)
knowledge_store.py Authorized local store Create/Update (KnowledgeStore)
research.py Read-only model-aware discovery joined over catalog queries
_skill_selection.py Deterministic lexical skill ranking and context view
claim.py Campaign verdict labels PASS/FAIL/INCONCLUSIVE; rules only
evidence_paths.py Per-campaign evidence tree: plan/results/patch/validator
summary_chart.py Stdlib SVG gain chart (chain/branch) and report figure spec
apps/
evidence_layout.py Create the plan/results/patch/validator evidence directories
campaign.py Knowledge values connected to Harness campaign records
views/
optimization_chart.py Managed optimization objective/token curves and final result
Expand Down
7 changes: 4 additions & 3 deletions docs/contracts/current-design.md
Original file line number Diff line number Diff line change
Expand Up @@ -25,15 +25,16 @@ Historical candidate text, review dispositions, and the earlier Proposed drafts

## D001 — One distribution, three cores plus Apps, document contracts rather than shared business DTOs

Decision: keep Knowledge, Harness, and Benchmark as sibling independent cores; Apps is the only assembler. Each core owns its types. Cross-boundary traffic uses versioned JSON envelopes with explicit conversion; there is no shared business `contracts` package. The technical-only `inferrsi.contracts` package re-exports only `RunSpec`, defined once in `contracts/runspec.py`; `contracts/claim.py` owns the same Verdict enum re-exported by Harness. These are not shared business DTOs. The old root `contracts.py`, `runspec.py`, `claim.py`, and `_json_v1.py` files are retired without forwarding shells.
Decision: keep Knowledge, Harness, and Benchmark as sibling independent cores; Apps is the only assembler. Each core owns its types. Cross-boundary traffic uses versioned JSON envelopes with explicit conversion; there is no shared business `contracts` package. The technical-only `inferrsi.contracts` package re-exports only `RunSpec`, defined once in `contracts/runspec.py`; `contracts/claim.py` owns the same Verdict enum re-exported by Harness. These are not shared business DTOs. The old root `contracts.py`, `runspec.py`, `claim.py`, and `_json_v1.py` files are retired without forwarding shells, and so are the old root `_repo_pack_data.py` and `evidence_paths.py`.

Permitted shared technical leaves are only:

- `inferrsi.contracts.json_v1` — the canonical encoder (D002);
- `inferrsi.contracts.runspec` and `inferrsi.contracts.claim` — the existing RunSpec and Verdict technical types, with only RunSpec re-exported by the package initializer;
- `inferrsi._repo_pack_data` — the neutral raw pack-data reader and the existing static data enumeration (D020).
- `inferrsi.contracts.evidence` — the existing evidence segment names and pure path rules; it reads and writes no filesystem state and is not re-exported by the package initializer;
- `inferrsi.resources.repository_packs` — the neutral raw pack-data reader and the existing static data enumeration (D020), formerly root `inferrsi._repo_pack_data`. Its parent initializer `resources/__init__.py` imports nothing.

The neutral leaf carries no target selection, task, scoring, scheduling, or public business DTO, and imports none of K/H/B/Apps.
The neutral leaf carries no target selection, task, scoring, scheduling, or public business DTO, and imports none of K/H/B/Apps. It still finds the Harness-owned `pack.json` through `files("inferrsi").joinpath("harness", "data", "repo_packs", ...)`, so reading it never imports Harness. Creating the evidence directories is host I/O and stays in Apps, in `inferrsi.apps.evidence_layout`; that module is not a shared leaf. The list is exact: a `contracts.` or `resources.` prefix admits no other module.

Why: this matches the accepted A–D direction and removes the reverse dependency that a shared DTO package creates. Rejected: a shared business DTO package; Apps owning scoring/sampling/budget algorithms; creating empty packages to declare migration done.

Expand Down
49 changes: 37 additions & 12 deletions docs/legacy-knowledge-manifest.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"$schema": "urn:inferrsi:docs:legacy-knowledge-manifest:v1",
"description": "First-wave compatibility exceptions for seven root Knowledge leaves plus the neutral technical data leaf. P0b froze the first revision at 0da7e2f960cd4ec994ae8eddea5b71023c5379ca and K01 re-recorded every leaf hash before the code move. This K02 revision changes only the neutral data leaf's locked file hash, because the pack.json resource moved to the Harness root. It is not a wildcard approval and changes only through formal review. D018/D020 chose these exact edges. file_sha256 is the old root leaf before the move, and line references are at the recorded base_commit.",
"base_commit": "d7de7f3a7a4c089da08cc17a0117a54d89466dee",
"description": "First-wave compatibility exceptions for seven root Knowledge leaves plus the neutral technical data leaf. P0b froze the first revision at 0da7e2f960cd4ec994ae8eddea5b71023c5379ca and K01 re-recorded every leaf hash before the code move. K02 changed only the neutral data leaf's locked file hash, because the pack.json resource moved to the Harness root. This C2 revision (#451) changes only where that leaf lives: it moves byte for byte from inferrsi._repo_pack_data to inferrsi.resources.repository_packs, and the two declared importers of the leaf point at the new module. The leaf's bytes and locked file hash, the seven root leaf hashes and the nine-pair count are unchanged. It is not a wildcard approval and changes only through formal review. D018/D020 chose these exact edges. file_sha256 is the old root leaf before the move, and line references are at the base_commit recorded by the revision that wrote them; this revision re-records none of them.",
"base_commit": "cd8fcb452bd2c7969a7a6e2544aa1cb5f8ad5332",
"revision_history": [
{
"base_commit": "0da7e2f960cd4ec994ae8eddea5b71023c5379ca",
Expand All @@ -21,6 +21,16 @@
"changed_file_sha256": {
"src/inferrsi/_repo_pack_data.py": "a14edac8283b1f7b6b5794381c44d7c2632dda5cc01f03c557dc293d05523afd"
}
},
{
"base_commit": "d7de7f3a7a4c089da08cc17a0117a54d89466dee",
"stage": "K02",
"superseded_by": "C2 module-path revision at cd8fcb452bd2c7969a7a6e2544aa1cb5f8ad5332",
"reason": "C2 (#451) moves the neutral data leaf from src/inferrsi/_repo_pack_data.py to src/inferrsi/resources/repository_packs.py and deletes the root file in the same change. The file bytes are unchanged, so the locked file hash keeps its value. The leaf's module and file, the neutral_leaf_export target and the targets of the catalog and infra.inspection pairs change to the new module. The seven root leaf hashes and the nine-pair count are unchanged.",
"changed_technical_leaf": {
"module": "inferrsi._repo_pack_data",
"file": "src/inferrsi/_repo_pack_data.py"
}
}
],
"compatibility_pairs": [
Expand Down Expand Up @@ -55,7 +65,7 @@
},
{
"importer": "catalog",
"target": "inferrsi._repo_pack_data",
"target": "inferrsi.resources.repository_packs",
"note": "Root catalog statically re-exports REPO_TYPES and repository_pack from the business-free neutral technical leaf"
},
{
Expand Down Expand Up @@ -216,8 +226,8 @@
},
{
"importer": "infra.inspection",
"target": "inferrsi._repo_pack_data",
"note": "infra.inspection imports the neutral leaf directly, never via catalog or H. D020 requires the import rewrite; K01 implementation must change only the import line (currently L10: from ..catalog import repository_pack → from .._repo_pack_data import repository_pack) and keep original functions, injected parameters, and returns unchanged"
"target": "inferrsi.resources.repository_packs",
"note": "infra.inspection imports the neutral leaf directly, never via catalog or H. D020 required the import rewrite; K01 changed only the import line (L10: from ..catalog import repository_pack → from .._repo_pack_data import repository_pack) and kept original functions, injected parameters, and returns unchanged. C2 (#451) changes that same line to from ..resources.repository_packs import repository_pack and nothing else in the module."
}
],
"catalog_two_routes": {
Expand All @@ -239,7 +249,7 @@
"note": "K.catalog does not export repository_pack; the named-symbol-only K export excludes repository_pack"
},
"neutral_leaf_export": {
"target": "inferrsi._repo_pack_data",
"target": "inferrsi.resources.repository_packs",
"symbols": [
"REPO_TYPES",
"repository_pack"
Expand All @@ -248,9 +258,9 @@
}
},
"technical_leaf": {
"module": "inferrsi._repo_pack_data",
"note": "K01 created src/inferrsi/_repo_pack_data.py from the recorded original fragment plus a leading comment, the future import, and the three listed stdlib imports. K02 repointed the reader to the Harness resource root and extended that comment, so file_sha256 is relocked here. original_fragment keeps the P0b provenance text; current_fragment is the body in the file today. P0b recorded only the fragment.",
"file": "src/inferrsi/_repo_pack_data.py",
"module": "inferrsi.resources.repository_packs",
"note": "K01 created src/inferrsi/_repo_pack_data.py from the recorded original fragment plus a leading comment, the future import, and the three listed stdlib imports. K02 repointed the reader to the Harness resource root and extended that comment, so file_sha256 was relocked then. C2 (#451) moved the file byte for byte to src/inferrsi/resources/repository_packs.py and deleted the root file; file_sha256 is checked against the relocated file and keeps its K02 value. original_fragment keeps the P0b provenance text; current_fragment is the body in the file today. P0b recorded only the fragment.",
"file": "src/inferrsi/resources/repository_packs.py",
"file_sha256": "751d7bf663318962a2e73cf9d75369e0f8f8c2bda27964c56e44021b9f86c992",
"allowed_imports": [
"json",
Expand All @@ -262,7 +272,7 @@
"REPO_TYPES",
"repository_pack"
],
"top_level_shape": "module docstring, a future import, the two symbols only, and no other business definitions or core imports",
"top_level_shape": "a leading comment (a module docstring is also accepted), the future import, exactly the three listed stdlib imports, the two symbols only, and no other definition, inferrsi import or dynamic import. Its one parent initializer, src/inferrsi/resources/__init__.py, is a module docstring and no other statement, so it imports nothing",
"original_fragment": {
"description": "REPO_TYPES and repository_pack body from current catalog.py (lines 12, 171-175)",
"hash_convention": "fragment_sha256 is the SHA-256 of source plus one trailing newline",
Expand All @@ -285,13 +295,28 @@
"new_line": "path = files(\"inferrsi\").joinpath(\"harness\", \"data\", \"repo_packs\", repo_type, \"pack.json\")",
"unchanged": "The importlib anchor stays files(\"inferrsi\") and joins the physical path, so the leaf still imports no inferrsi module. allowed_imports, the two symbols, the top-level shape, REPO_TYPES object identity and the two permitted importers are unchanged, and infra gains no edge into Harness.",
"review": "This manifest revision requires formal architecture review (amy-why-3459 and zengchuang-hw). The implementer does not self-approve it."
},
"module_path_revision": {
"stage": "C2",
"issue": "#451",
"reason": "Packaged-resource access leaves the flat package root. The leaf moves with its bytes unchanged, and the root file is deleted in the same change with no forwarding shell or sys.modules alias.",
"old_module": "inferrsi._repo_pack_data",
"new_module": "inferrsi.resources.repository_packs",
"old_file": "src/inferrsi/_repo_pack_data.py",
"new_file": "src/inferrsi/resources/repository_packs.py",
"old_file_sha256": "751d7bf663318962a2e73cf9d75369e0f8f8c2bda27964c56e44021b9f86c992",
"new_file_sha256": "751d7bf663318962a2e73cf9d75369e0f8f8c2bda27964c56e44021b9f86c992",
"parent_initializer": "src/inferrsi/resources/__init__.py",
"unchanged": "The file bytes, the importlib anchor files(\"inferrsi\") joined with harness/data/repo_packs/<repo>/pack.json, allowed_imports, the two symbols, REPO_TYPES object identity and the two permitted importers outside Knowledge (root catalog and infra.inspection) are unchanged. The leaf still imports no inferrsi module, and its new parent initializer imports nothing, so infra gains no edge into Harness.",
"review": "This manifest revision requires formal architecture review, as the K02 resource_path_revision did. The implementer does not self-approve it, and passing tests are not that review."
}
},
"infra_inspection_rewrite": {
"module": "src/inferrsi/infra/inspection.py",
"current_import": "from ..catalog import repository_pack",
"required_new_import": "from .._repo_pack_data import repository_pack",
"note": "K01 changes only this import line. Original functions, injected parameters, and returns stay the same. current_import records the line at base_commit."
"canonical_import": "from ..resources.repository_packs import repository_pack",
"note": "K01 changed only this import line, from current_import to required_new_import; both record that K01 rewrite. C2 (#451) changes the same line to canonical_import, which is the line in the module today. Original functions, injected parameters, and returns stay the same."
},
"intra_closure_note": "An import of inferrsi._repo_pack_data from inside inferrsi.knowledge (for example inferrsi/knowledge/catalog.py) is intra-closure, not a tenth compatibility exception; it is governed by the leaf's no-inferrsi.*-import rule and by REPO_TYPES object identity, not by this allowlist."
"intra_closure_note": "An import of inferrsi.resources.repository_packs from inside inferrsi.knowledge (for example inferrsi/knowledge/catalog.py) is intra-closure, not a tenth compatibility exception; it is governed by the leaf's no-inferrsi.*-import rule, its import-free parent initializer and REPO_TYPES object identity, not by this allowlist."
}
Loading
Loading