feat: assert flex-auth ceiling keys are declared, not assumed
flex-auth fixed enrichment so registry facts beat caller-supplied ones (FLEX-DEC-2026-012) and asked each consumer to confirm the ceiling and allowlist keys are actually declared -- the fix wins only where the registry HAS a value, and a manifest omitting max_ttl_hours hands that ceiling back to the caller. Confirmed, and made durable rather than read once. scripts/check_flex_auth_manifest_coverage.py audits both ways a ceiling gets handed back: an actor with no manifest resource at all (warden sign names ssh-cert:actor/<name> whether or not the snapshot was rebuilt -- an honour-system step in SCOPE.md), and a resource missing one of the seven keys. A null is treated as absent, because for enrichment it is. Also asserts the property their exploitability assessment rested on and nothing here held: ops-warden sends no resource.attributes. It was true when they read it, secrets-engine sends them on every request, and it was one refactor from silently stopping being true. Current state: no gap. 4 actors, 4 resources, all seven keys declared. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_013EPuTc18FjU5WFqoSEKH3C Assistant: claude-code Assistant-Model: opus Assistant-Process: 1276224@bnt-lap001 Assistant-Session: 426ec497-e1c4-4dd3-b417-dfce1ca1dbc3
This commit is contained in:
parent
3a01b8f1b5
commit
df48ee96e0
3 changed files with 288 additions and 0 deletions
|
|
@ -81,3 +81,86 @@ def test_compiler_joins_explicit_workload_reference_to_resolved_zone(tmp_path):
|
|||
assert attrs["security_zone"] == "z2-continuity"
|
||||
assert attrs["security_zone_admission"] == "satisfied"
|
||||
assert attrs["security_zone_revision"] == "sha256:zone-revision"
|
||||
|
||||
|
||||
# --- manifest ceiling coverage (FLEX-DEC-2026-012) ----------------------------
|
||||
#
|
||||
# flex-auth fixed enrichment so registry facts beat caller-supplied ones, then
|
||||
# asked every consumer to confirm the ceiling keys are actually declared: the
|
||||
# fix wins only where the registry HAS a value. These assert the two ways a
|
||||
# ceiling gets handed back to the caller.
|
||||
|
||||
import importlib.util # noqa: E402
|
||||
|
||||
import pytest # noqa: E402
|
||||
|
||||
_REPO = ROOT
|
||||
_spec = importlib.util.spec_from_file_location(
|
||||
"check_flex_auth_manifest_coverage",
|
||||
_REPO / "scripts" / "check_flex_auth_manifest_coverage.py",
|
||||
)
|
||||
_coverage = importlib.util.module_from_spec(_spec)
|
||||
_spec.loader.exec_module(_coverage)
|
||||
REQUIRED_CEILING_KEYS = _coverage.REQUIRED_CEILING_KEYS
|
||||
audit = _coverage.audit
|
||||
|
||||
_build_spec = importlib.util.spec_from_file_location("build_flex_auth_registry", SCRIPT)
|
||||
_builder = importlib.util.module_from_spec(_build_spec)
|
||||
_build_spec.loader.exec_module(_builder)
|
||||
build_registry = _builder.build_registry
|
||||
|
||||
|
||||
def _repo_inventory_and_registry():
|
||||
inventory = yaml.safe_load((_REPO / "examples" / "inventory.seed.yaml").read_text())
|
||||
registry = json.loads(
|
||||
(_REPO / "registry" / "flex-auth" / "production_registry_snapshot.json").read_text()
|
||||
)
|
||||
return inventory, registry
|
||||
|
||||
|
||||
def test_shipped_snapshot_declares_every_ceiling_key():
|
||||
"""The confirmation flex-auth asked for, as a test rather than a reading."""
|
||||
report = audit(*_repo_inventory_and_registry())
|
||||
assert report["unregistered_actors"] == []
|
||||
assert report["resources_missing_keys"] == []
|
||||
assert report["covered"] is True
|
||||
|
||||
|
||||
def test_actor_with_no_manifest_resource_is_a_coverage_gap():
|
||||
"""`warden sign` names ssh-cert:actor/<name> whether or not the snapshot was rebuilt."""
|
||||
inventory, registry = _repo_inventory_and_registry()
|
||||
inventory["actors"]["adm-added-after-the-last-build"] = {
|
||||
"type": "adm", "principals": ["adm-full"], "ttl_hours": 48,
|
||||
}
|
||||
report = audit(inventory, registry)
|
||||
assert report["unregistered_actors"] == ["adm-added-after-the-last-build"]
|
||||
assert report["covered"] is False
|
||||
|
||||
|
||||
@pytest.mark.parametrize("key", REQUIRED_CEILING_KEYS)
|
||||
def test_dropping_any_single_ceiling_key_is_a_coverage_gap(key):
|
||||
inventory, registry = _repo_inventory_and_registry()
|
||||
resource = registry["resource_manifests"][0]["resources"][0]
|
||||
resource["attributes"].pop(key)
|
||||
report = audit(inventory, registry)
|
||||
assert report["resources_missing_keys"] == [
|
||||
{"resource": resource["id"], "missing": [key]}
|
||||
]
|
||||
assert report["covered"] is False
|
||||
|
||||
|
||||
@pytest.mark.parametrize("key", REQUIRED_CEILING_KEYS)
|
||||
def test_a_null_ceiling_is_not_a_declaration(key):
|
||||
"""flex-auth overlays a registry value only where one exists."""
|
||||
inventory, registry = _repo_inventory_and_registry()
|
||||
resource = registry["resource_manifests"][0]["resources"][0]
|
||||
resource["attributes"][key] = None
|
||||
report = audit(inventory, registry)
|
||||
assert report["covered"] is False
|
||||
|
||||
|
||||
def test_builder_output_is_covered_by_construction(tmp_path):
|
||||
"""Every resource the builder emits carries the full ceiling set."""
|
||||
inventory = yaml.safe_load((_REPO / "examples" / "inventory.seed.yaml").read_text())
|
||||
report = audit(inventory, build_registry(inventory))
|
||||
assert report["covered"] is True
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue