CREATE MASKING POLICY

Cria uma nova política de mascaramento no esquema atual/especificado ou substitui uma política de mascaramento existente.

Após criar uma política de mascaramento, aplique a política de mascaramento a uma coluna em uma tabela usando um comando ALTER TABLE … ALTER COLUMN ou uma visualização usando um comando ALTER VIEW.

Consulte também:

Escolha de uma abordagem centralizada, híbrida ou descentralizada, Tópicos avançados de segurança em nível de coluna

DDL da política de mascaramento

Sintaxe

CREATE [ OR REPLACE ] MASKING POLICY [ IF NOT EXISTS ] <name> AS
( <arg_name_to_mask> <arg_type_to_mask> [ , <arg_1> <arg_type_1> ... ] )
RETURNS <arg_type_to_mask> -> <body>
[ COMMENT = '<string_literal>' ]
[ EXEMPT_OTHER_POLICIES = { TRUE | FALSE } ]
Copy

Parâmetros obrigatórios

name

Identificador da política de mascaramento; deve ser único para seu esquema.

O valor do identificador deve começar com um caractere alfabético e não pode conter espaços ou caracteres especiais, a menos que toda a cadeia de caracteres do identificador esteja entre aspas duplas (por exemplo, "My object"). Os identificadores delimitados por aspas duplas também diferenciam letras maiúsculas de minúsculas.

Para obter mais detalhes, consulte Requisitos para identificadores.

AS ( arg_name_to_mask arg_type_to_mask [ , arg_1 arg_type_1 ... ] )

A assinatura da política de mascaramento; especifica as colunas de entrada e os tipos de dados a serem avaliados no tempo de execução da consulta.

Para obter mais detalhes, consulte Referência de tipos de dados SQL.

arg_name_to_mask arg_type_to_mask

A primeira coluna e seu tipo de dados sempre indicam os valores do tipo de dados da coluna a serem mascarados ou tokenizados nas condições da política subsequente.

Note que você não pode especificar uma coluna virtual como primeiro argumento da coluna em uma política de mascaramento condicional.

[ , arg_1 arg_type_1 ... ]

Especifica as colunas condicionais e seus tipos de dados a serem avaliados para determinar se as condições da política devem mascarar ou tokenizar os dados na primeira coluna em cada linha do resultado da consulta.

Se estas colunas e tipos de dados adicionais não forem especificados, o Snowflake avalia a política como uma política normal de mascaramento.

RETURNS arg_type_to_mask

O tipo de dados de retorno deve corresponder ao tipo de dados de entrada da primeira coluna especificada como coluna de entrada.

body

Expressão SQL que transforma os dados na coluna designada por arg_name_to_mask.

A expressão pode incluir Funções de expressão condicional para representar lógica condicional, funções internas ou UDFs para transformar os dados.

Para UDFs e funções externas:

  • O proprietário da política, a função com o privilégio OWNERSHIP na política, deve ter o privilégio USAGE na UDF ou função externa. O privilégio USAGE na UDF ou função externa não é necessário para a função usada para consultar uma coluna que tenha uma política de mascaramento aplicada a ela.

  • Se uma dessas funções estiver sendo usada dentro do corpo de política de mascaramento condicional, o proprietário da política deve ter o privilégio OWNERSHIP na UDF ou função externa. Os usuários que consultam uma coluna com uma política de mascaramento condicional aplicada a ela não precisam ter USAGE na UDF ou função externa.

Para funções de contexto na política body:

Quando a política chama a função CURRENT_DATABASE ou CURRENT_SCHEMA, a função avalia o banco de dados ou o esquema que contém a tabela ou exibição protegida, e não o banco de dados ou o esquema da sessão que você especifica com um comando USE <objeto> ou seleciona com o seletor de contexto em Snowsight.

Parâmetros opcionais

COMMENT = 'string_literal'

Adiciona um comentário ou substitui um comentário existente para a política de mascaramento.

EXEMPT_OTHER_POLICIES = TRUE | FALSE

Uma das seguintes opções, dependendo do uso:

  • Especifica se uma política de acesso a linhas ou a política de mascaramento condicional pode fazer referência a uma coluna que já esteja protegida por esta política de mascaramento.

  • Especifica se uma política de mascaramento atribuída a uma coluna virtual substitui a política de mascaramento que a coluna virtual herda da coluna VALUE. Ao trabalhar com tabelas externas, especifique esta propriedade na política de mascaramento que protege a coluna VALUE.

TRUE

Permite que uma política diferente faça referência à coluna mascarada ou permite que a política de mascaramento definida em uma coluna virtual substitua a política de mascaramento que a coluna virtual herda da coluna VALUE em uma tabela externa.

FALSE

Não permite que uma política diferente faça referência à coluna mascarada ou permite a política de mascaramento e não permite a política de mascaramento que a coluna virtual herda da coluna VALUE em uma tabela externa.

Observe o seguinte:

  • O valor desta propriedade na política de mascaramento não pode mudar após colocar a política de mascaramento em uma tabela ou exibição. Para atualizar o valor desta configuração de propriedade, execute uma instrução CREATE OR REPLACE MASKING POLICY na política de mascaramento.

  • Quando a propriedade é definida como verdadeira, ela é incluída na saída de chamada da função GET_DDL na política.

Requisitos de controle de acesso

Uma função usada para executar este comando SQL deve ter os seguintes privilégios no mínimo:

Privilégio

Objeto

Notas

CREATE MASKING POLICY

Esquema

Observe que operar em qualquer objeto de um esquema também requer o privilégio USAGE no banco de dados e esquema principais.

Para instruções sobre como criar uma função personalizada com um conjunto específico de privilégios, consulte Criação de funções personalizadas.

Para informações gerais sobre concessões de funções e privilégios para executar ações de SQL em objetos protegíveis, consulte Visão geral do controle de acesso.

Ao especificar a propriedade EXEMPT_OTHER_POLICIES em uma política de mascaramento, a função que possui a política de mascaramento (ou seja, a função com privilégio OWNERSHIP na política) deve estar na hierarquia da função que possui a política de acesso a linhas ou a política de mascaramento condicional.

Por exemplo, as funções personalizadas do administrador de políticas podem formar uma hierarquia de função como a seguir:

masking_admin » rap_admin » SYSADMIN

masking_admin » cond_masking_admin » SYSADMIN

Onde:

masking_admin

Especifica a função personalizada que é proprietária da política de mascaramento que é definida na coluna que será especificada na assinatura de uma política de acesso a linhas ou de uma política de mascaramento condicional.

rap_admin

Especifica a função personalizada que é proprietária da política de acesso a linhas.

cond_masking_admin

Especifica a função personalizada que é proprietária da política de mascaramento condicional.

Para detalhes adicionais sobre a política de mascaramento DDL e privilégios, consulte Gerenciamento da segurança em nível de coluna.

Notas de uso

  • Se você quiser substituir uma política de mascaramento existente e precisar ver a definição atual da política, chame a função GET_DDL ou execute o comando DESCRIBE MASKING POLICY.

  • Para políticas de mascaramento com uma subconsulta no corpo da política de mascaramento, use EXISTS na ramificação WHEN da função CASE. Para um exemplo representativo, consulte o exemplo da tabela de direitos personalizados na seção Política de mascaramento normal (neste tópico).

  • Uma determinada coluna de tabela ou exibição pode ser especificada em uma assinatura de política de mascaramento ou em uma assinatura de política de acesso a linhas. Em outras palavras, a mesma coluna não pode ser especificada tanto em uma assinatura de política de mascaramento quanto em uma assinatura de política de acesso a linhas ao mesmo tempo.

    Para obter mais informações, consulte CREATE ROW ACCESS POLICY.

  • Um provedor de Data Sharing não pode criar uma política de mascaramento em uma conta de leitor.

  • Se utilizar uma UDF em uma política de mascaramento, certifique-se de que o tipo de dados da coluna, a UDF e a política de mascaramento sejam correspondentes. Para obter mais informações, consulte Funções definidas pelo usuário em uma política de mascaramento.

  • Em relação aos metadados:

    Atenção

    Os clientes devem garantir que nenhum dado pessoal (exceto para um objeto do usuário), dados sensíveis, dados controlados por exportação ou outros dados regulamentados sejam inseridos como metadados ao usar o serviço Snowflake. Para obter mais informações, consulte Campos de metadados no Snowflake.

  • Instruções CREATE OR REPLACE <object> são atômicas. Ou seja, quando um objeto é substituído, o objeto antigo é excluído e o novo objeto é criado em uma única transação.

Exemplo: política de mascaramento normal

Você pode usar Funções de expressão condicional, Funções de contexto e UDFs para criar a expressão SQL.

A seguir, você encontra exemplos representativos do corpo de política para mostrar como criar condições de política de mascaramento usando diferentes instruções, funções e tipos de dados de SQL.

Estes exemplos utilizam principalmente a função de contexto CURRENT_ROLE. Se a ativação e a hierarquia de funções for necessária nas condições da política, use IS_ROLE_IN_SESSION.

Máscara completa:

A função analyst pode ver o valor em texto simples. Usuários sem a função analyst veem uma máscara completa.

CREATE OR REPLACE MASKING POLICY email_mask AS (val string) returns string ->
  CASE
    WHEN current_role() IN ('ANALYST') THEN VAL
    ELSE '*********'
  END;
Copy

Permitir que uma conta de produção consulte valores sem máscara e todas as outras contas (como de desenvolvimento, teste) vejam valores com máscara.

case
  when current_account() in ('<prod_account_identifier>') then val
  else '*********'
end;
Copy

Retornar NULL para usuários não autorizados:

case
  when current_role() IN ('ANALYST') then val
  else NULL
end;
Copy

Retornar um valor estático mascarado para usuários não autorizados:

CASE
  WHEN current_role() IN ('ANALYST') THEN val
  ELSE '********'
END;
Copy

Retornar um valor de hash usando SHA2 , SHA2_HEX para usuários não autorizados. O uso de uma função de hash em uma política de mascaramento pode resultar em colisões; portanto, tenha cuidado com esta abordagem. Para obter mais informações, consulte Tópicos avançados de segurança em nível de coluna.

CASE
  WHEN current_role() IN ('ANALYST') THEN val
  ELSE sha2(val) -- return hash of the column value
END;
Copy

Aplicar uma máscara parcial ou máscara completa:

CASE
  WHEN current_role() IN ('ANALYST') THEN val
  WHEN current_role() IN ('SUPPORT') THEN regexp_replace(val,'.+\@','*****@') -- leave email domain unmasked
  ELSE '********'
END;
Copy

Usando carimbos de data/hora.

case
  WHEN current_role() in ('SUPPORT') THEN val
  else date_from_parts(0001, 01, 01)::timestamp_ntz -- returns 0001-01-01 00:00:00.000
end;
Copy

Importante

Atualmente, o Snowflake não oferece suporte a diferentes tipos de dados de entrada e saída em uma política de mascaramento, como a definição da política de mascaramento para apontar para um carimbo de data/hora e retornar uma cadeia de caracteres (por exemplo, ***MASKED***); os tipos de dados de entrada e saída devem ser correspondentes.

Uma alternativa é converter o valor real do carimbo de data/hora em um valor de carimbo de data/hora inventado. Para obter mais informações, consulte DATE_FROM_PARTS e CAST , ::.

Usando uma UDF:

CASE
  WHEN current_role() IN ('ANALYST') THEN val
  ELSE mask_udf(val) -- custom masking function
END;
Copy

Em dados das variantes:

CASE
   WHEN current_role() IN ('ANALYST') THEN val
   ELSE OBJECT_INSERT(val, 'USER_IPADDRESS', '****', true)
END;
Copy

Usando uma tabela de direitos personalizados. Observe o uso de EXISTS na cláusula WHEN. Use sempre EXISTS ao incluir uma subconsulta no corpo de política de mascaramento. Para obter mais informações sobre as subconsultas que o Snowflake suporta, consulte Como trabalhar com subconsultas.

CASE
  WHEN EXISTS
    (SELECT role FROM <db>.<schema>.entitlement WHERE mask_method='unmask' AND role = current_role()) THEN val
  ELSE '********'
END;
Copy

Usando DECRYPT em dados previamente criptografados com ENCRYPT ou ENCRYPT_RAW, com uma frase secreta nos dados criptografados:

case
  when current_role() in ('ANALYST') then DECRYPT(val, $passphrase)
  else val -- shows encrypted value
end;
Copy

Usando uma <JavaScript UDF em JSON (VARIANT):

Neste exemplo, uma UDF JavaScript esconde os dados de localização em uma cadeia de caracteres JSON. É importante definir o tipo de dados como VARIANT na UDF e a política de mascaramento. Se o tipo de dados na coluna da tabela, UDF e a assinatura da política de mascaramento não forem correspondentes, o Snowflake retorna uma mensagem de erro porque não consegue resolver o SQL.

-- Flatten the JSON data

create or replace table <table_name> (v variant) as
select value::variant
from @<table_name>,
  table(flatten(input => parse_json($1):stationLocation));

-- JavaScript UDF to mask latitude, longitude, and location data

CREATE OR REPLACE FUNCTION full_location_masking(v variant)
  RETURNS variant
  LANGUAGE JAVASCRIPT
  AS
  $$
    if ("latitude" in V) {
      V["latitude"] = "**latitudeMask**";
    }
    if ("longitude" in V) {
      V["longitude"] = "**longitudeMask**";
    }
    if ("location" in V) {
      V["location"] = "**locationMask**";
    }

    return V;
  $$;

  -- Grant UDF usage to ACCOUNTADMIN

  grant ownership on function FULL_LOCATION_MASKING(variant) to role accountadmin;

  -- Create a masking policy using JavaScript UDF

  create or replace masking policy json_location_mask as (val variant) returns variant ->
    CASE
      WHEN current_role() IN ('ANALYST') THEN val
      else full_location_masking(val)
      -- else object_insert(val, 'latitude', '**locationMask**', true) -- limited to one value at a time
    END;
Copy

Usando o tipo de dados GEOGRAPHY:

Neste exemplo, uma política de mascaramento usa a função TO_GEOGRAPHY para converter todos os dados GEOGRAPHY em uma coluna para um ponto fixo, a longitude e a latitude para Snowflake em San Mateo, Califórnia, para usuários cuja CURRENT_ROLE não seja ANALYST.

create masking policy mask_geo_point as (val geography) returns geography ->
  case
    when current_role() IN ('ANALYST') then val
    else to_geography('POINT(-122.35 37.55)')
  end;
Copy

Definir a política de mascaramento em uma coluna com o tipo de dados GEOGRAPHY e defina o valor GEOGRAPHY_OUTPUT_FORMAT para a sessão como GeoJSON:

alter table mydb.myschema.geography modify column b set masking policy mask_geo_point;
alter session set geography_output_format = 'GeoJSON';
use role public;
select * from mydb.myschema.geography;
Copy

O Snowflake retorna o seguinte:

---+--------------------+
 A |         B          |
---+--------------------+
 1 | {                  |
   |   "coordinates": [ |
   |     -122.35,       |
   |     37.55          |
   |   ],               |
   |   "type": "Point"  |
   | }                  |
 2 | {                  |
   |   "coordinates": [ |
   |     -122.35,       |
   |     37.55          |
   |   ],               |
   |   "type": "Point"  |
   | }                  |
---+--------------------+
Copy

Os valores do resultado da consulta na coluna B dependem do valor do parâmetro GEOGRAPHY_OUTPUT_FORMAT para a sessão. Por exemplo, se o valor do parâmetro for definido como WKT, o Snowflake retorna o seguinte:

alter session set geography_output_format = 'WKT';
select * from mydb.myschema.geography;

---+----------------------+
 A |         B            |
---+----------------------+
 1 | POINT(-122.35 37.55) |
 2 | POINT(-122.35 37.55) |
---+----------------------+
Copy

Para exemplos que utilizam outras funções de contexto e hierarquia de funções, consulte Tópicos avançados de segurança em nível de coluna.

Exemplo: política de mascaramento condicional

O exemplo seguinte retorna dados não mascarados para usuários cuja CURRENT_ROLE é a função personalizada de admin ou cujo valor na coluna de visibilidade é Public. Todas as outras condições resultam em um valor fixo mascarado.

-- Conditional Masking

create masking policy email_visibility as
(email varchar, visibility string) returns varchar ->
  case
    when current_role() = 'ADMIN' then email
    when visibility = 'Public' then email
    else '***MASKED***'
  end;
Copy

O exemplo seguinte retorna dados não tokenizados para usuários cuja CURRENT_ROLE é a função personalizada de admin ou cujo valor em uma outra coluna é Public. Todas as outras condições resultam em um valor tokenizado.

-- Conditional Tokenization

create masking policy de_email_visibility as
 (email varchar, visibility string) returns varchar ->
   case
     when current_role() = 'ADMIN' and visibility = 'Public' then de_email(email)
     else email -- sees tokenized data
   end;
Copy

Exemplo: permitir uma coluna mascarada em uma política de acesso a linhas ou uma política de mascaramento condicional

Substitua uma política de mascaramento que permita visualizar o endereço de e-mail, visualizar apenas o domínio do endereço de e-mail ou um valor fixo mascarado:

create or replace masking policy governance.policies.email_mask
as (val string) returns string ->
case
  when current_role() in ('ANALYST') then val
  when current_role() in ('SUPPORT') then regexp_replace(val,'.+\@','*****@')
  else '********'
end
comment = 'specify in row access policy'
exempt_other_policies = true
;
Copy

Esta política pode agora ser definida em uma coluna e uma política de acesso a linhas ou uma política de mascaramento condicional pode fazer referência à coluna protegida por esta política de mascaramento, conforme necessário.