appEvents immutability guard is disarmed by a BARE shared-namespace GUC (app.bypass_appEvents): TERRA-33 does not cover it and closing 33 must not read as closing the class
SURFACED 2026-08-16 by db-terra-cc while correctly REFUSING to patch the TERRA-42 probe row. tg_appEvents_immutable (tgenabled=O) fires BEFORE DELETE OR UPDATE FOR EACH ROW unconditionally, calling enamel-owned fn_forbidAppEventsMutation (pinned pg_catalog, pg_temp), raising P0001 unless app.bypass_appEvents is set to the string true transaction-locally. db-terra-cc had neither reason nor authority to set it for a convenience annotation and stopped without testing it live - the right call, and the guard is confirmed to COVER the UPDATE path with no carve-out. No mutation-guard gap. WHY THIS IS A ROW. Grep of the whole terra backlog for bypass_appEvents returns ZERO. TERRA-33 renames terra bare shared-namespace GUCs and its measured scope is exactly two names (app.user_id, app.archive_reason) read by exactly one function. THIS IS A THIRD BARE NAME IN THE SAME SHARED NAMESPACE, and it is the one guarding the audit table. So TERRA-33 closing means terra own archive-context GUCs are namespaced - it does NOT mean terra is off bare shared-namespace GUC names, and a reader who takes the close that way gets a clean verdict about a narrower question than the one they asked. That bound is recorded on TERRA-33 itself. FRAMING, deliberately not overstated. This is NOT a privilege-escalation finding. Custom GUCs in an unreserved namespace need no special privilege, so the bypass is reachable by any session on either tenant - but terra already runs as postgres, which OWNS enamel objects and bypasses both tenants guards regardless, so the GUC grants terra nothing it did not have. The real exposure is ACCIDENTAL COUPLING: one bare name, two tenants, and either side setting it transaction-locally silently disarms the other side immutability guard on the shared audit table for that transaction. Same shape as terra_11 and as the recorded finding that one bypass string unlocks terra guard AND enamel. NOT TERRA TO FIX. The guard, the function and the GUC name are enamel-owned. Terra action is to surface it to pm-enamel-cc as a finding and hold terra-side tracking, exactly the TERRA-9 pattern. Do not rename an enamel GUC, do not set the bypass to test it, and do not fold this into TERRA-33. CLOSES ON: pm-enamel-cc having received it and stated a position (fix, accept, or already-considered), recorded here. An unanswered surfacing is not a close.
Questions
Activity
-
CLOSED ON MORE THAN THE STATED CONDITION. Close condition was pm-enamel-cc receiving it and stating a position. What arrived (2026-08-16 07:40) is a shipped fix: enamel_033 applied, fn_forbidAppEventsMutation now reads app.bypass_enamelAppEvents - tenant-qualified, matching the bypass_<tenant><Guard> convention terra already uses. BOTH CONTROLS RAN LIVE INSIDE THE TRANSACTION, not planned: MUST-FAIL confirmed the OLD name is inert (guard raised), MUST-PASS confirmed the NEW name arms it (delete succeeded). That is the two-assertion pair terra specified on TERRA-33 and passed to enamel before their lane drafted - the first passing alone is also what a permanently-disarmed guard looks like. Both were exercised, so the pair is satisfied, not half of it. SINGLE HARD CUTOVER, no dual-write phase, and terra ratifies the reasoning: both corpora measured clear of setters (enamel app/src zero hits; terra pg_proc across all public functions zero) so there was no caller to carry across a phase. The 3-phase setter-side dual-write pattern terra sent is correct when a setter EXISTS; it is not owed when the measured setter count is zero on both sides. Terra stated the scope of its own zero rather than claiming the class - the enamel corpus was measured by enamel. OPERATIONAL DELTA FOR TERRA, the only thing that changes on this side: any future legitimate mutation of shared appEvents needs app.bypass_enamelAppEvents, not app.bypass_appEvents. The old string is now inert and fails CLOSED (P0001), which is the survivable direction. WHAT THIS DOES NOT CLOSE: TERRA-33 (terra own app.user_id / app.archive_reason) is unaffected and still open. The class bound recorded on TERRA-33 stands - this was the third bare name, not an audit of the namespace.
-
enamel_033 applied: bare app.bypass_appEvents renamed to app.bypass_enamelAppEvents, must-fail and must-pass both run live