Поделиться через


Безопасность на уровне строк в Azure Cosmos DB для PostgreSQL

Это важно

Azure Cosmos DB для PostgreSQL больше не поддерживается для новых проектов. Не используйте эту службу для новых проектов. Вместо этого используйте одну из этих двух служб:

В соответствии с принципами Политик безопасности на уровне строк PostgreSQL ограничивается круг пользователей, которые могут изменять или получать доступ к строкам таблицы. Безопасность на уровне строк особенно полезна в мультитенантном кластере. Это позволяет отдельным клиентам иметь полный доступ к базе данных SQL, скрывая сведения каждого клиента от других клиентов.

Внедрение для приложений с несколькими арендаторами

Мы можем реализовать разделение данных клиента с помощью соглашения об именовании ролей базы данных, связанном с политиками безопасности на уровне строк таблицы. Мы назначим каждому клиенту роль базы данных в нумерованной последовательности: tenant1, tenant2и т. д. Клиенты будут подключаться к Azure Cosmos DB для PostgreSQL с помощью этих отдельных ролей. Политики безопасности на уровне строк могут сравнить имя роли со значениями в столбце распространения tenant_id, чтобы принять решение, следует ли разрешать доступ.

Далее представлено применение подхода к упрощенной таблице событий, распределенной по tenant_id. Сначала создайте ролиtenant1 и tenant2. Затем выполните следующие команды SQL от имени администратора citus:

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;

На данном этапе любой пользователь, имеющий разрешения на выбор для этой таблицы может видеть обе строки. Пользователи из любого клиента могут просматривать и обновлять строку другого клиента. Мы можем устранить утечку данных с помощью политик безопасности таблиц на уровне строк.

Каждая политика состоит из двух предложений: USING (Использование) и WITH CHECK (С проверкой). Когда пользователь пытается считывать или записывать строки, база данных оценивает каждую строку по этим предложениям. PostgreSQL проверяет существующие строки таблицы на соответствие выражению, указанному в предложении USING, и строки, которые будут созданы с помощью инструкции INSERT (Вставка) или UPDATE (Обновление) в предложении 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;

Теперь роли tenant1 и tenant2 получают различные результаты для своих запросов:

Подключено как tenant1:

SELECT * FROM events;
┌───────────┬────┬──────┐
│ tenant_id │ id │ type │
├───────────┼────┼──────┤
│         1 │  1 │ foo  │
└───────────┴────┴──────┘

Подключено как 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"
*/

Следующие шаги