Skip to content

Commit 28b6308

Browse files
cursoragentmorluto
andcommitted
Tighten composition admission, MCP hub ownership, and local planning
Split the remaining MCP operations hub by concern, trim unused complete-runtime fixtures from the MCP conftest, and document the owned smoke / attached edges. Require COMPOSITION_ADMISSION on complete-runtime composition modules (AUTHORITY/WIRING/LIFECYCLE/DISCOVERY/REFERENCE/MIXED) with an architecture ratchet, and report setup weights plus heaviest paths from the runtime inventory. Fold infrastructure and high-impact path policy into plan_manifest [local_planning], and label local-test-ownership.json as exact-selector overrides only. Co-authored-by: morluto <morluto@users.noreply.github.com>
1 parent a76cb05 commit 28b6308

48 files changed

Lines changed: 593 additions & 263 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/local-test-ownership.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
{
22
"version": 1,
3+
"role": "Exact pytest selector overrides for non-test paths only. Lane/gate/impact authority lives in tests/plan_manifest.toml (compiled to topology + ci-impact). Do not treat this file as a second planner.",
34
"overrides": {
45
".github/ci-impact.json": [
56
"tests/boundary/process/tooling/test_ci_classification.py",

.github/scripts/plan-local-tests

Lines changed: 23 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ from typing import NamedTuple
1818
ROOT = Path(__file__).resolve().parents[2]
1919
CLASSIFIER = ROOT / ".github" / "scripts" / "classify-ci-paths"
2020
OWNERSHIP = ROOT / ".github" / "local-test-ownership.json"
21+
PLAN_MANIFEST = ROOT / "tests" / "plan_manifest.toml"
2122
TOPOLOGY_MANIFEST = ROOT / "tests" / "topology.toml"
2223

2324
# The planner scripts live without a package context; make the sibling helper
@@ -108,22 +109,28 @@ if not GATE_LANES:
108109

109110
LINT_TYPECHECK_COMMAND = "make lint typecheck"
110111

112+
113+
def _local_planning() -> dict[str, object]:
114+
raw = tomllib.loads(PLAN_MANIFEST.read_text(encoding="utf-8"))
115+
section = raw.get("local_planning", {})
116+
if not isinstance(section, dict):
117+
raise ValueError("tests/plan_manifest.toml local_planning must be a table")
118+
return section
119+
120+
121+
_LOCAL_PLANNING = _local_planning()
122+
111123
# Repository paths whose impact is structural rather than ordinary Python
112124
# behavior. Such changes route to ``make check-static`` (which already includes
113125
# lint-full, typecheck, architecture, and a package build) instead of the
114126
# lighter ``make lint typecheck`` handoff.
115-
INFRASTRUCTURE_PREFIXES = (
116-
".github/",
117-
"Makefile",
118-
"make/",
119-
"pyproject.toml",
120-
"uv.lock",
121-
"tools/",
122-
".pre-commit-config.yaml",
123-
".jscpd.json",
124-
"tests/topology.toml",
125-
"tests/plan_manifest.toml",
127+
INFRASTRUCTURE_PREFIXES = tuple(
128+
str(item) for item in _LOCAL_PLANNING.get("infrastructure_prefixes", ())
126129
)
130+
if not INFRASTRUCTURE_PREFIXES:
131+
raise ValueError(
132+
"tests/plan_manifest.toml local_planning.infrastructure_prefixes required"
133+
)
127134

128135

129136
def is_infrastructure_path(path: str) -> bool:
@@ -165,11 +172,12 @@ def local_command_lanes(lanes: list[str]) -> list[str]:
165172

166173

167174
HIGH_IMPACT_PATHS = {
168-
"src/jacobian/__init__.py",
169-
"tests/conftest.py",
170-
"pyproject.toml",
171-
"uv.lock",
175+
str(item) for item in _LOCAL_PLANNING.get("high_impact_paths", ())
172176
}
177+
if not HIGH_IMPACT_PATHS:
178+
raise ValueError(
179+
"tests/plan_manifest.toml local_planning.high_impact_paths required"
180+
)
173181

174182

175183
class Change(NamedTuple):

docs/reference/testing-strategy.md

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,26 @@ component lanes (prefer `open_domain_services` /
7878
`open_exact_domain_services`). Complete-runtime fixtures are visible only under
7979
owning composition, e2e, and named boundary confests.
8080

81+
Every composition `test_*.py` that uses a complete-runtime fixture must declare
82+
a module-level admission category:
83+
84+
```python
85+
COMPOSITION_ADMISSION = "AUTHORITY" # or WIRING, LIFECYCLE, DISCOVERY, REFERENCE, MIXED
86+
```
87+
88+
| Category | Meaning |
89+
| --- | --- |
90+
| `AUTHORITY` | Checker presence/absence, hydration, verify handoff, fail-closed trust |
91+
| `WIRING` | Portfolio install, catalog contracts, cross-service artifact identity |
92+
| `LIFECYCLE` | Bootstrap, attach, close, recovery, worker quiesce |
93+
| `DISCOVERY` | Whole-portfolio discovery ranking / intent routing |
94+
| `REFERENCE` | Portfolio reference-set / structure-canonicalization contracts |
95+
| `MIXED` | Temporary: ordinary capability matrices still pending domain demotion |
96+
97+
`tools/check_test_architecture.py` fails closed when a complete-runtime
98+
composition module omits the declaration or uses an unknown category. Prefer
99+
shrinking `MIXED` over expanding it.
100+
81101
A test's directory answers what kind of behavior it owns. A marker is retained
82102
only when it changes execution. The CI impact manifest maps changed paths to
83103
every explicitly owned lane, with additive multi-owner rules and a fail-closed
@@ -113,6 +133,15 @@ digest, configuration digests, and canonical plan digest. `make harbor-plan`
113133
uses the pinned Harbor runtime because task digests are part of the plan
114134
contract.
115135

136+
Local planning reads `[local_planning]` from `tests/plan_manifest.toml` for
137+
infrastructure prefixes and high-impact paths. Exact pytest selectors for
138+
non-test paths remain in `.github/local-test-ownership.json` as a thin override
139+
map only—not a second lane/impact planner. Prefer folding stable overrides into
140+
manifest impact rules over growing that JSON.
141+
142+
`make test-runtime-inventory` reports complete-runtime fixture setup weights and
143+
the heaviest paths so demotions can target real cost.
144+
116145
### Local development and CI ownership
117146

118147
The contributor quick path is `make setup PROFILE=core` followed by

tests/boundary/mcp/conftest.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,19 @@
1-
"""MCP transport boundary test configuration."""
1+
"""MCP transport boundary test configuration.
2+
3+
Only ``attached_complete_runtime`` is needed by this lane today
4+
(``test_mcp_inspection_relationship_compaction``). Fresh/authorized complete
5+
fixtures stay out of the MCP conftest so the lane does not hydrate unused
6+
portfolio templates.
7+
"""
28

39
from __future__ import annotations
410

511
from tests.support.complete_runtime_fixtures import (
612
attached_complete_runtime,
7-
authorized_complete_runtime,
8-
authorized_portfolio_template,
913
complete_portfolio_template,
10-
fresh_complete_runtime,
1114
)
1215

1316
__all__ = (
1417
"attached_complete_runtime",
15-
"authorized_complete_runtime",
16-
"authorized_portfolio_template",
1718
"complete_portfolio_template",
18-
"fresh_complete_runtime",
1919
)

0 commit comments

Comments
 (0)