docs(adr0041): resolve the baseline trust-domain question and narrow two false D3 claims (BACKLOG #1679) - #1184
Conversation
…two false D3 claims (BACKLOG #1679) Act 5 of BACKLOG #1679. Acts 1 to 4 shipped in PR 1159, which deliberately left the baseline's trust domain open and recorded it as an owner decision. It is not one: the record leaves no defensible second option, so this replaces the open paragraph with the resolution. Ground 1, and it is sufficient alone: any in-process anchor is circular. _loaded_module_files walks messagefoundry.__path__, so integrity.py is inside the set it attests. It attests itself and nothing else attests it. attest_engine has exactly one caller, run_startup_attestation in its own module; that has exactly one caller, the ASGI lifespan in api/app.py. An adversary with venv-write rewrites integrity.py in one write, the same primitive that re-seals RECORD, so any anchor the engine reads at startup is read by code that actor already owns. That is a logical collapse rather than a cost, and it holds even if the anchor were free. Ground 2: the project already ruled the structurally identical question at trust boundary 5, where the answer is a deployer-owned filesystem ACL and not a cryptographic control. The residual is stated plainly: the control detects an inconsistent in-place edit and cannot detect a consistent one. The out-of-domain anchoring that does exist is named: origin at install time, detection by the off-box audit tee. What still earns the control its keep is named too: the shadowed-package shape needs no venv write at all, so AC-13 raises the bar against an actor strictly weaker than the stated adversary. The premise the resolution rests on - that the install root can be made non-writable in the intended shape - is recorded as an assumption, not answered. Six declined alternatives are tabled with their reasons. Two D3 claims were false in the shipped code and are dropped rather than left standing. "Enforced production default" for the non-editable wheel: nothing enforces it, so it now reads "recommended". "At startup (and on demand)": there is no on-demand surface, no attest CLI subcommand and no API route, so the phrase is dropped throughout. New behaviour, AC-14: under fail_closed_on_drift the declared-editable branch returned with no log, no audit row and no alert, so a first deployment that opted into hard enforcement on an editable install would have started with its tripwire disarmed and zero signal. It now logs a WARNING naming the reason. This is a MISCONFIGURATION control and it closes no hole: an actor with venv-write plants direct_url.json or rewrites the check in the same single write. AC-12 is untouched - still no refusal, no row, no alert - and the warning is keyed on the opt-in, so the default alert-only posture stays silent on a dev checkout. The CONFIGURATION.md fail_closed_on_drift row now points at the D3 resolution instead of selling hard enforcement with no boundary. The fact is stated once, in the ADR, and linked from the module docstring and the config reference.
|
Three subjects found while doing this and deliberately NOT built here. Named in words, with no number cited, because none is allocated. 1. 2. 3. An install-root ACL preflight, mirroring what One question I could not settle, and it is the owner's: can the install root be made non-writable in the intended deployment shape? The resolution in this PR rests on that ACL. It exists nowhere in these sources. The ADR now records it as the premise rather than answering it. One place the tree disagreed with the brief: the brief pinned |
Lander reviewThis removes two false claims from a shipped ADR, which is the highest-value thing a docs PR can do here. I re-derived both from the branch rather than reading them. Claim 1: "enforced production default" was falseNothing refuses to start on an editable install under either posture, and a declared-editable install is exempt regardless. So "enforced" was wrong and "recommended" is right. This is the SDS-3.7 shape exactly — a shipped security document asserting an enforcement that does not exist, which a reader would have planned around. Claim 2: "and on demand" was false, and the near-miss is the interesting partThe call chain is closed at one path: Everything else the grep returns is the No CLI subcommand, and this time with a control that fires: My first pass at this used a regex that returned 0 for a subcommand that does exist, which would have made the zero above meaningless. Recording that because a search proving nothing is the failure mode this repository keeps paying for. And the route that looks like the exception is not one. That is the store's SQLite check, not engine attestation. Two controls with adjacent names, and the ADR is right to say so rather than let a reader merge them. Filing a real on-demand surface is separate work, as the note says. The trust-domain resolution is correctly argued"Any in-process anchor is circular" is sufficient on its own: The new control is scoped honestlyThe added warning fires when an operator sets AC-12 is preserved and the tests assert it — still no refusal, no audit row, no alert on an editable install, so a dev checkout is not bricked. Both arms are covered: the fail-closed opt-in warns, the default posture stays silent. Stated no larger than it isI verified the two narrowed claims, the call chain, the absence of a CLI surface with a working control, and what the integrity-check route actually does. I did not re-derive the ADR 0017 relationship or the second ground for the trust-domain decision; the first ground is sufficient on its own and is the one I checked. Verdict: merge. |
BACKLOG #1679, act 5. Acts 1 to 4 shipped in PR 1159 and are not rebuilt here.
PR 1159 deliberately left one question open and recorded it as an owner decision under ADR 0041 AC-12/AC-13: should a
RECORDbaseline that sits inside the adversary's own install be trusted at all, and if not what out-of-domain anchor replaces it. It is not an owner decision. The record leaves no defensible second option, so this replaces the open paragraph with the resolution and narrows two claims that are false in the shipped code.What changed
RECORDstays the baseline. No runtime out-of-domain anchor is adopted.docs/CONFIGURATION.mdlinks to the resolution instead of selling hard enforcement with no boundary. The fact is stated once, in the ADR.Nothing was mirrored into
docs/SECURITY.md— it carries no startup-attestation claim to narrow, and a copy there would create a second home for a load-bearing fact.Ground 1 — any in-process anchor is circular
_loaded_module_filessources frommessagefoundry.__path__, sointegrity.pyis inside the set it attests. It attests itself and nothing else attests it.Verified in the tree, not carried from the brief:
attest_engine— exactly one caller,run_startup_attestation, in its own module.run_startup_attestation— exactly one caller, the ASGI lifespan inmessagefoundry/api/app.py.add_parser(calls inmessagefoundry/__main__.py, zero of them namedattest.An adversary with venv-write rewrites
integrity.pyin one write — the same primitive that re-sealsRECORD. So any anchor the engine consumes at startup is consumed by code that actor already owns. That kills an operator-supplied pin, this ADR's own deferred signed manifest used as a runtime check, and Sigstore-as-runtime-anchor, in one sentence. It is a logical collapse rather than a cost, so it holds even if the anchor were free.Ground 2 — the precedent
The project already ruled the structurally identical question, admin-authored Python executed in-process, at trust boundary 5. The answer recorded there is a deployer-owned filesystem ACL rather than a cryptographic control. Cited by number only; that document is withheld from public checkouts and none of its text is reproduced here.
What the resolution states
RECORDpasses clean. Accepted.messagefoundry/directory resolved ahead of site-packages. AC-13 therefore raises the bar against an actor strictly weaker than the stated adversary. That is a real gain, not a consolation.record_pin, aneditable_install_allowedkey, a publisher-signed boot manifest, a repo-recorded digest, folding theRECORDdigest into astartup_integrityrow and diffing against the prior one, and a per-boot heartbeat row.The two false claims
"Enforced production default" for the non-editable hash-locked wheel. Nothing enforces it.
[integrity].enableddefaults true,fail_closed_on_driftdefaults false, a declared-editable install is exempt under either, and no code path anywhere refuses to start on one. Verified:grep -rn "editable" --include=*.py messagefoundry/returns 35 hits inintegrity.py, 6 in__main__.py(web console provenance, unrelated), 5 insettings.py(the[integrity]docstrings), and nothing that refuses. Narrowed to "recommended"."At startup (and on demand)". There is no on-demand surface. No
attest/integrityCLI subcommand (control above) and no API route —POST /status/integrity-checkis the store's SQLitePRAGMA quick_check, a different control. The phrase is dropped from the ADR (two places),docs/CONFIGURATION.mdand theintegrity.pymodule docstring. Filing either surface is separate work and is not done here.AC-14 — one WARNING line, described honestly
Under
fail_closed_on_drift=true, thedeclared_editablebranch ofrun_startup_attestationreturned with no log, no audit row, no alert, and never refused. A first deployment that opted into hard enforcement on an editable install would start with its tripwire disarmed and nothing in the boot log to read.It now logs a WARNING naming the reason, and the reason token is what carries the cause into the boot-log posture readout.
This is a MISCONFIGURATION control and it closes no hole. An adversary with venv-write plants one
direct_url.jsonor rewrites this check in the same single write. What the line does is tell an operator that the opt-in they set is not in effect.AC-12 is untouched: still no refusal, no audit row, no alert, so a dev checkout is never bricked. The warning is keyed on the opt-in, not on editability, so the default alert-only posture stays silent — warning on every dev run is how a warning stops being read.
The failing test, and its exact output before the fix
Test written first, run first, red first:
The
1 passedin that run is the paired arm,test_declared_editable_under_the_default_posture_stays_silent, which asserts the default posture emits nothing. It passes before and after, which is what makes it a guard against over-correction: a fix that warned on every editable install would turn it red.After the fix:
Checks run
From this worktree's own
.venv(stdlibvenv, installed with--constraint constraints.lock,messagefoundry.__file__verified to resolve inside this worktree).ruff check .ruff format --check .mypy messagefoundrypytest tests/test_startup_attestation.pypytest tests/test_settings.py tests/test_security_posture_defaults.pypytestdoc gates (test_doc_guards_lane,test_doc_ref_handle,test_docs_cite_no_refused_config_keys,test_docs_security_pathways,test_operator_docs_no_warning_sign,test_ledger_check,test_docs_runbooks)Skipped: the full
pytestsuite. It does not finish inside one turn. The slices above cover every file this change touches.CI legs a human must read after I exit
Every hosted-runner leg, since none of them run locally — in particular
windows-service-smoke(NSSM), the gated SQL Server and PostgreSQL suites (tests/test_startup_attestation.pyfeeds_assert_startup_attestation_tamper_evidenceinto both), and the full-suite legs on all three runners.Notes
docs/BACKLOG.mdis untouched. It is a public stub in this repository with zero numbered items.