A measurement and the source disagree, and neither has been reconciled. Filed as a finding rather than a bug because which one is wrong is exactly what is unknown — and the answer changes a checklist item either way.
The two claims
The run (#9453, correction CF-3): a browser round recorded observing R1 owd_widening_forbidden answering directly on what it recorded as a stock deploy, and concluded that access-security.owd-save-gate's knownGap mispredicts which layer answers.
The source (packages/plugins/plugin-security/src/object-posture-gate.ts:95, verified on main):
if(!ctx.isArtifactBacked)return;
with the accompanying prose stating R1 "applies only to overlay writes over an artifact-backed object (the OS_METADATA_WRITABLE escape-hatch path — the default deploy already 403s these before this gate runs)".
Both cannot be true of the same fixture. On a default deploy the gate returns before it can answer, and an earlier 403 is what the caller should see.
Why it is filed rather than fixed
The QA wave's ledger-correction round (#9475) rejected CF-3 and left the item unedited, on the grounds that writing a wrong fact into a checklist item is worse than leaving the correct one standing. That is the right call: the item's existing knownGap and clause 4 already record whichever layer answers, so nothing is broken by waiting — but the disagreement is now recorded in a run issue and will be re-derived by the next round unless it is settled here.
What settles it — one re-measure
Re-run the owd-save-gate R1 probe and state explicitly:
- Was
OS_METADATA_WRITABLE set in the environment? - Was the target object artifact-backed (
ctx.isArtifactBacked true) at the moment of the write? - Which layer produced the 403 — the posture gate, or the earlier refusal the prose says the default deploy issues first?
Three outcomes, each with a different owner:
- The observation was on a non-stock fixture (escape hatch on, or an artifact-backed target) → the run record's CF-3 is a fixture-labelling error; correct the run record, leave the item alone.
- The observation was genuinely stock → the gate fires where its own source says it cannot, which is a product defect in
plugin-security and outranks any checklist edit. - Both are right about different objects → the item's
knownGap needs to name the distinguishing condition, which is a ledger edit.
Unassigned and unlabelled for domain:* — routing is the triage seat's call, and the right lane depends on which of the three outcomes lands.
Sources: #9453 (the observation), #9475 (the grounded rejection), QA wave #9296.
A measurement and the source disagree, and neither has been reconciled. Filed as a
findingrather than a bug because which one is wrong is exactly what is unknown — and the answer changes a checklist item either way.The two claims
The run (#9453, correction CF-3): a browser round recorded observing R1
owd_widening_forbiddenanswering directly on what it recorded as a stock deploy, and concluded thataccess-security.owd-save-gate'sknownGapmispredicts which layer answers.The source (
packages/plugins/plugin-security/src/object-posture-gate.ts:95, verified onmain):with the accompanying prose stating R1 "applies only to overlay writes over an artifact-backed object (the
OS_METADATA_WRITABLEescape-hatch path — the default deploy already 403s these before this gate runs)".Both cannot be true of the same fixture. On a default deploy the gate returns before it can answer, and an earlier 403 is what the caller should see.
Why it is filed rather than fixed
The QA wave's ledger-correction round (#9475) rejected CF-3 and left the item unedited, on the grounds that writing a wrong fact into a checklist item is worse than leaving the correct one standing. That is the right call: the item's existing
knownGapand clause 4 already record whichever layer answers, so nothing is broken by waiting — but the disagreement is now recorded in a run issue and will be re-derived by the next round unless it is settled here.What settles it — one re-measure
Re-run the
owd-save-gateR1 probe and state explicitly:OS_METADATA_WRITABLEset in the environment?ctx.isArtifactBackedtrue) at the moment of the write?Three outcomes, each with a different owner:
plugin-securityand outranks any checklist edit.knownGapneeds to name the distinguishing condition, which is a ledger edit.Unassigned and unlabelled for
domain:*— routing is the triage seat's call, and the right lane depends on which of the three outcomes lands.Sources: #9453 (the observation), #9475 (the grounded rejection), QA wave #9296.