Visão geral das condições do IAM

Nesta página, descrevemos o recurso de condições do gerenciamento de identidade e acesso (IAM, na sigla em inglês). Use as condições do IAM para definir e aplicar o controle de acesso condicional e baseado em atributos para recursos do Google Cloud.

Com as condições do IAM, você pode optar por conceder acesso aos principais somente se as condições especificadas forem atendidas. Por exemplo, é possível conceder acesso temporário aos usuários para que eles resolvam um problema de produção, ou conceder acesso somente a funcionários que fazem solicitações no escritório corporativo.

As condições são especificadas nas vinculações de papéis da política de permissão de um recurso. Quando uma condição existir, a solicitação de acesso só será concedida se a expressão condicional for avaliada como true. Cada expressão de condição é um conjunto de instruções lógicas que especificam um ou mais atributos a serem verificados.

Políticas de permissão com condições

As políticas de permissão contêm uma ou mais vinculações de papéis, que têm a estrutura a seguir:

"bindings": [
  {
    "role": ...,
    "members": ...,
    "condition": ...
  },
  ...
]

O objeto condition é opcional, e cada vinculação de papel pode conter zero ou uma condição. Se uma vinculação de papel não tiver um objeto condition, os principais nessa vinculação de papel sempre terão o papel especificado no recurso.

Apenas alguns tipos de recurso aceitam condições em vinculações de papéis. No entanto, é possível conceder acesso condicional a outros tipos de recursos concedendo papéis no nível da organização ou do projeto.

O objeto condition tem a seguinte estrutura:

"condition": {
    "title": ...,
    "description": ...,
    "expression": ...
}

O title da condição é obrigatório, mas o description é opcional. Tanto o título quanto a descrição são campos puramente informativos para ajudá-lo a identificar e descrever a condição.

O campo expression é obrigatório. Ele define uma expressão lógica baseada em atributo usando um subconjunto da Common Expression Language (CEL). A expressão de condição pode conter várias instruções. cada declaração avalia um atributo. As instruções são combinadas usando operadores lógicos, seguindo a especificação da linguagem CEL.

Para saber como adicionar, modificar e remover vinculações de papéis condicionais, veja Como gerenciar vinculações de papéis condicionais.

CEL para condições

Common Expression Language, ou CEL, é a linguagem de expressão usada para especificar uma expressão na condição do IAM. Ela é personalizada para expressar expressões lógicas baseadas em atributos. Para saber mais, veja a especificação da CEL e a respectiva definição de linguagem.

Nas condições do IAM, um subconjunto da CEL é usado para tomar decisões de autorização booleana com base nos dados do atributo. Em geral, uma expressão condicional consiste em uma ou mais instruções unidas por até 12 operadores lógicos (&&, || ou !). Cada instrução expressa uma regra de controle baseada em atributo que se aplica à vinculação de papéis e, por fim, determina se o acesso é permitido.

As Condições do IAM usam os seguintes recursos de CEL:

  • Variáveis: as condições usam variáveis para expressar um determinado atributo, como request.time (do tipo carimbo de data/hora) ou resource.name (do tipo string). Essas variáveis são preenchidas com valor com base no contexto no ambiente de execução.
  • Operadores: cada tipo de dados, como carimbo de data/hora ou string, é compatível com um conjunto de operadores que podem ser usados para criar uma expressão lógica. Geralmente, os operadores são usados para comparar o valor contido em uma variável com um valor literal, como resource.service == "compute.googleapis.com". Neste exemplo, se o valor de entrada de resource.service for compute.googleapis.com, a expressão será avaliada como true.
  • Funções: uma função é um operador "composto" para tipos de dados compatíveis com operações mais complexas. Em expressões condicionais, existem funções predefinidas que podem ser usadas com um determinado tipo de dados. Por exemplo, request.path.startsWith("/finance") usa uma função de correspondência de prefixo de string e avalia como true se o valor de request.path contém um prefixo correspondente, como "/finance".
  • Operadores lógicos: as condições são compatíveis com três operadores lógicos que podem ser usados para criar expressões lógicas complexas a partir de instruções de expressões simples: &&, || e !. Esses operadores lógicos possibilitam o uso de muitas variáveis de entrada em uma expressão condicional. Por exemplo: request.time.getFullYear() < 2020 && resource.service == "compute.googleapis.com" une duas instruções simples e exige que ambas sejam atendidas para produzir um resultado geral de avaliação true.

Saiba mais sobre variáveis, operadores e funções compatíveis na referência do atributo.

Atributos de condição

Os atributos de condição são baseados no recurso solicitado (por exemplo, o tipo ou nome) ou em detalhes sobre a solicitação, por exemplo, carimbo de data/hora ou endereço IP de destino.

Atributos de recurso

É possível usar atributos de recurso para gravar condições que avaliam o recurso na solicitação de acesso. Os atributos que podem ser avaliados incluem os seguintes:

  • O tipo de recurso
  • O nome do recurso
  • O serviço do Google Cloud que está sendo usado
  • As tags anexadas ao recurso

Veja uma lista completa de atributos de recursos na Referência de atributos de recursos.

Saiba como usar atributos de recursos para configurar o acesso baseado em recursos em Como configurar o acesso baseado em recursos.

Exemplos de expressões

Permitir acesso a instâncias de VMs do Compute Engine, mas nenhum outro tipo de recurso:

resource.type == "compute.googleapis.com/Instance"

Permitir acesso a recursos do Cloud Storage, mas não a outros recursos do serviço:

resource.service == "storage.googleapis.com"

Permita o acesso apenas a objetos do Cloud Storage dentro de um bucket específico:

resource.type == "storage.googleapis.com/Object" &&
resource.name.startsWith("projects/_/buckets/exampleco-site-assets/")

Permita o acesso aos recursos do Google Cloud que têm a tag env: prod:

resource.matchTag('123456789012/env', 'prod')

Atributos de solicitação

Use atributos de solicitação para gravar condições que avaliem detalhes sobre a solicitação, como os seguintes:

  • O nível de acesso
  • A data e a hora
  • O endereço IP e a porta de destino (para o tunelamento de TCP do IAP)
  • O host/caminho do URL esperado (para o IAP)

Exemplo de expressão de nível de acesso (somente para IAP)

No exemplo a seguir, a organização define um nível de acesso, CorpNet, que limita o acesso ao intervalo de endereços IP em que o tráfego entra e sai de uma rede corporativa. O acesso só é permitido se a solicitação atender aoCorpNet nível de acesso:

"accessPolicies/199923665455/accessLevels/CorpNet" in
request.auth.access_levels

A organização define os níveis de acesso com base nos atributos da solicitação, como o endereço IP de origem, os atributos do dispositivo, a hora do dia e muito mais. Para mais detalhes, consulte a documentação do Access Context Manager.

Exemplo de expressão do atributo de API

Permitir que um usuário conceda e revogue apenas o papel de administrador da conta de faturamento (roles/billing.admin):

api.getAttribute('iam.googleapis.com/modifiedGrantsByRole', [])
                 .hasOnly(['roles/billing.admin'])

Para saber mais sobre o uso de atributos de API para limitar a concessão de papéis, consulte Como definir limites ao conceder papéis.

Exemplo de expressões de data/hora

Permitir acesso temporariamente até uma data/hora de validade especificada:

request.time < timestamp("2021-01-01T00:00:00Z")

Permitir acesso apenas durante o horário de trabalho especificado, com base no fuso horário de Berlim, na Alemanha:

request.time.getHours("Europe/Berlin") >= 9 &&
request.time.getHours("Europe/Berlin") <= 17 &&
// Days of the week range from 0 to 6, where 0 == Sunday and 6 == Saturday.
request.time.getDayOfWeek("Europe/Berlin") >= 1 &&
request.time.getDayOfWeek("Europe/Berlin") <= 5

Permitir acesso apenas para um mês e um ano específicos, com base no fuso horário de Berlim, na Alemanha:

request.time.getFullYear("Europe/Berlin") == 2020
request.time.getMonth("Europe/Berlin") < 6

Para especificar um carimbo de data/hora, use o formato RFC 3339. Para especificar um fuso horário, use os identificadores do banco de dados de fuso horário da IANA.

Saiba mais sobre expressões de data e hora na especificação da CEL.

Saiba como usar expressões de data/hora para configurar o acesso temporário em Como configurar o acesso temporário.

Exemplo de expressões de IP/porta de destino (para o tunelamento de TCP do IAP)

Permitir acesso a um endereço IP interno de destino ou número de porta:

destination.ip == "14.0.0.1"
destination.ip != "127.0.0.1"
destination.port == 22
destination.port > 21 && destination.port <= 23

Exemplo de expressões de regra de encaminhamento

Permitir o acesso de um principal se a solicitação não estiver criando uma regra de encaminhamento ou se ela estiver criando uma regra de encaminhamento para um balanceador de carga interno do Google Cloud:

!compute.isForwardingRuleCreationOperation() || (
  compute.isForwardingRuleCreationOperation() &&
  compute.matchLoadBalancingSchemes([
    'INTERNAL', 'INTERNAL_MANAGED', 'INTERNAL_SELF_MANAGED'
  ])
)

Exemplos de expressões de host/caminho do URL (para o IAP)

Permite acesso apenas a determinados subdomínios ou caminhos de URL na solicitação:

request.host == "hr.example.com"
request.host.endsWith(".example.com")
request.path == "/admin/payroll.js"
request.path.startsWith("/admin")

Para mais detalhes sobre esquemas de balanceamento de carga, consulte Como usar condições do IAM em balanceadores de carga do Google Cloud.

Exemplo de expressão com diferentes tipos de atributos

Permitir acesso quando a solicitação é feita durante um horário específico, correspondendo a um prefixo de nome de recurso, com o nível de acesso pretendido e para um tipo de recurso específico:

request.time > timestamp("2018-08-03T16:00:00-07:00") &&
request.time < timestamp("2018-08-03T16:05:00-07:00") &&
((resource.name.startsWith("projects/project-123/zones/us-east1-b/instances/dev") ||
 (resource.name.startsWith("projects/project-123/zones/us-east1-b/instances/prod") &&
  "accessPolicies/34569256/accessLevels/CorpNet" in request.auth.access_levels)) ||
 resource.type != "compute.googleapis.com/Instance")

A seguir