From 212951209aab74a5d148573a9db8950e20b1fc85 Mon Sep 17 00:00:00 2001 From: Andrey Date: Thu, 16 Jul 2026 23:19:01 +0300 Subject: [PATCH] :wrench: fix(deploy): grant custocrm_schema membership to runtime roles C04 RLS relies on the permissive custocrm_schema_access policy (USING/WITH CHECK true, created by tenancy.0003 on every tenant table) to let login roles perform cross-tenant writes such as a login-failed audit record with organization_id IS NULL. That policy is attached to custocrm_schema, but init-runtime-roles.sh never made custocrm_runtime_app / custocrm_runtime_platform members of custocrm_schema, so the policy did not cover the login roles and the write failed with 'violates row-level security policy' even under WITH CHECK true. Reproduced on a clean DB; the missing membership was the sole cause. Add the two GRANT statements. Document the bug and the post-cutover CSRF-cookie fix (62bac47) in INVENTORY-0009 and RUNBOOK-0002. --- deploy/postgres/init-runtime-roles.sh | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/deploy/postgres/init-runtime-roles.sh b/deploy/postgres/init-runtime-roles.sh index 2882772..fe27287 100644 --- a/deploy/postgres/init-runtime-roles.sh +++ b/deploy/postgres/init-runtime-roles.sh @@ -40,6 +40,15 @@ WHERE NOT EXISTS (SELECT 1 FROM pg_roles WHERE rolname = :'migration_user') SELECT format('GRANT custocrm_runtime_app TO %I', :'app_user') \gexec SELECT format('GRANT custocrm_runtime_platform TO %I', :'platform_user') \gexec SELECT format('GRANT custocrm_schema TO %I', :'migration_user') \gexec +-- C04 RLS: runtime_app/platform must also be members of custocrm_schema so the +-- permissive custocrm_schema_access policy (USING/WITH CHECK true, created by +-- tenancy.0003 on every tenant table) applies to them. Without this membership +-- the schema_access policy does not cover the login roles, leaving only the +-- tenant_isolation / audit-insert policies, which do not OR to true for +-- cross-tenant writes (e.g. login-failed audit with organization_id IS NULL) +-- and block the write with "violates row-level security policy". +SELECT format('GRANT custocrm_schema TO custocrm_runtime_app') \gexec +SELECT format('GRANT custocrm_schema TO custocrm_runtime_platform') \gexec SELECT format('GRANT CONNECT ON DATABASE %I TO %I', current_database(), :'app_user') \gexec SELECT format('GRANT CONNECT ON DATABASE %I TO %I', current_database(), :'platform_user') \gexec SELECT format('GRANT CONNECT, CREATE, TEMPORARY ON DATABASE %I TO %I', current_database(), :'migration_user') \gexec