Problem: A multi-tenant HR platform sharing one Postgres database had experienced 3 cross-tenant data leaks in 12 months due to missing WHERE tenant_id clauses. Application-layer filtering was a convention, not an enforcement mechanism.
Solution: Moved tenant isolation to Postgres Row-Level Security. Policies check current_setting('app.tenant_id') at the database layer. Django sets the session variable at connection time. A Testcontainers-based migration harness spins a real Postgres instance per migration, runs the migration, then attempts a cross-tenant read. Any migration failing the invariant fails CI.
Technology: Postgres RLS · Django · Testcontainers · Python
Optimisation pattern: application-filtering-to-postgres-rls
Outcomes:
Zero cross-tenant leaks in 18 months (vs. 3 in prior 12 months). Migration test suite adds ~40 s to CI. 100% of new tables have RLS policies at creation.