supabase: guarded, auto-expiring temporary support access to restricted tenants#3115
Open
skord wants to merge 1 commit into
Open
supabase: guarded, auto-expiring temporary support access to restricted tenants#3115skord wants to merge 1 commit into
skord wants to merge 1 commit into
Conversation
…ed tenants Restricted tenants are deliberately not attached to estuary_support/, so support cannot reach them by default. This adds an internal.support_access tracking table plus SECURITY DEFINER functions to grant, revoke, and expire temporary support access to a single tenant. Operators receive EXECUTE on the functions (granted out of band by the departmental-roles tooling) and never write public.role_grants directly, so they cannot escalate their own access. The grant function only attaches estuary_support/ to a named, existing tenant and logs who granted it, why, and when it expires. Expiry is enforced by pg_cron on the Supabase database, registered out of band since pg_cron is absent from the sqlx test cluster. The sweeper only removes grants that have a support_access tracking row, so the permanent estuary_support/ grants normal tenants receive are never affected. Adds pgTAP coverage in supabase/tests/support_access.test.sql. Implements ADR estuary/security#746.
ad2b4c6 to
f8f4e2e
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Adds a guarded, auto-expiring mechanism for temporary support access to restricted
tenants that are deliberately excluded from the standing
estuary_support/role.Why
Today, giving a restricted tenant temporary support access means an operator with
broad database access hand-writes a
role_grantsrow and is trusted to remove it.There is no expiry, no record of who granted it or why, and it requires write
access to the system-wide authorization table, which is also the ability to grant
anyone admin on anything. See ADR estuary/security#746.
What's in this PR
internal.support_accesstracking table: the source of truth for temporarygrants, separate from
role_grants.internal.grant_support_access(tenant, reason, duration),internal.revoke_support_access(tenant), andinternal.expire_support_access(),all
SECURITY DEFINER.revoke all ... from publicon the three functions.supabase/tests/support_access.test.sql.Why it's safe
EXECUTEon the functions and never writerole_grantsdirectly,so they cannot escalate their own access. The grant function only attaches
estuary_support/to a named, existing tenant, and recordssession_user,reason, and expiry.
estuary_support/grants normal tenants receive are never touched.Out of band (not in this migration)
EXECUTEon these functions is granted to operator roles by the departmentaldatabase-roles tooling (a separate private repo), not here.
Expiry is enforced by
pg_cronon the Supabase database. It is registered once,out of band, because
pg_cronis absent from the sqlx test cluster:Testing
supabase db resetapplies all migrations cleanly.mise run ci:sql-tappasses, including the new tests: grant attaches and logs;blank reason and unknown tenant are rejected; expire sweeps only expired, tracked
grants and preserves permanent ones; revoke detaches and marks the row revoked.
Related