Zabezpečení na úrovni řádků ve službě Azure Cosmos DB for PostgreSQL
PLATÍ PRO: Azure Cosmos DB for PostgreSQL (využívá rozšíření databáze Citus pro PostgreSQL)
Zásady zabezpečení na úrovni řádků PostgreSQL omezují, kteří uživatelé můžou upravovat řádky tabulky nebo k těmto řádkům přistupovat. Zabezpečení na úrovni řádků může být zvlášť užitečné v clusteru s více tenanty. Umožňuje, aby jednotliví tenanti měli úplný přístup SQL k databázi a zároveň skrývali informace o každém tenantovi před ostatními tenanty.
Implementace pro aplikace s více tenanty
Oddělení dat tenanta můžeme implementovat pomocí zásad vytváření názvů pro databázové role, které jsou propojeny se zásadami zabezpečení na úrovni řádků tabulky. Každému tenantovi přiřadíme roli databáze v očíslované posloupnosti: tenant1
, tenant2
atd. Tenanti se připojí ke službě Azure Cosmos DB for PostgreSQL pomocí těchto samostatných rolí. Zásady zabezpečení na úrovni řádků můžou porovnat název role s hodnotami v distribučním tenant_id
sloupci a rozhodnout, jestli chcete povolit přístup.
Tady je postup, jak tento přístup použít u zjednodušené tabulky událostí distribuované nástrojem tenant_id
. Nejprve vytvořte roletenant1
a tenant2
. Pak jako citus
uživatel správce spusťte následující příkazy SQL:
CREATE TABLE events(
tenant_id int,
id int,
type text
);
SELECT create_distributed_table('events','tenant_id');
INSERT INTO events VALUES (1,1,'foo'), (2,2,'bar');
-- assumes that roles tenant1 and tenant2 exist
GRANT select, update, insert, delete
ON events TO tenant1, tenant2;
Každý, kdo má pro tuto tabulku oprávnění k výběru, uvidí oba řádky. Uživatelé z obou tenantů můžou zobrazit a aktualizovat řádek druhého tenanta. Únik dat můžeme vyřešit pomocí zásad zabezpečení tabulek na úrovni řádků.
Každá zásada se skládá ze dvou klauzulí: USING a WITH CHECK. Když se uživatel pokusí přečíst nebo zapsat řádky, databáze vyhodnotí každý řádek na základě těchto klauzulí. PostgreSQL zkontroluje existující řádky tabulky proti výrazu zadanému v klauzuli USING a řádky, které by se vytvořily pomocí příkazu INSERT nebo UPDATE proti klauzuli WITH CHECK.
-- first a policy for the system admin "citus" user
CREATE POLICY admin_all ON events
TO citus -- apply to this role
USING (true) -- read any existing row
WITH CHECK (true); -- insert or update any row
-- next a policy which allows role "tenant<n>" to
-- access rows where tenant_id = <n>
CREATE POLICY user_mod ON events
USING (current_user = 'tenant' || tenant_id::text);
-- lack of CHECK means same condition as USING
-- enforce the policies
ALTER TABLE events ENABLE ROW LEVEL SECURITY;
Nyní role tenant1
a tenant2
získání různých výsledků pro své dotazy:
Připojeno jako tenant1:
SELECT * FROM events;
┌───────────┬────┬──────┐
│ tenant_id │ id │ type │
├───────────┼────┼──────┤
│ 1 │ 1 │ foo │
└───────────┴────┴──────┘
Připojeno jako tenant2:
SELECT * FROM events;
┌───────────┬────┬──────┐
│ tenant_id │ id │ type │
├───────────┼────┼──────┤
│ 2 │ 2 │ bar │
└───────────┴────┴──────┘
INSERT INTO events VALUES (3,3,'surprise');
/*
ERROR: new row violates row-level security policy for table "events_102055"
*/
Další kroky
- Naučte se vytvářet role v clusteru.
- Projděte si koncepty zabezpečení ve službě Azure Cosmos DB for PostgreSQL.