As regras de segurança do Cloud Firestore permitem que você controle o acesso a documentos e coleções em seu banco de dados. A sintaxe flexível das regras permite que você crie regras que correspondam a qualquer coisa, desde todas as gravações em todo o banco de dados até operações em um documento específico.
Este guia descreve a sintaxe básica e a estrutura das regras de segurança. Combine esta sintaxe com condições de regras de segurança para criar conjuntos de regras completos.
Declaração de serviço e banco de dados
As regras de segurança do Cloud Firestore sempre começam com a seguinte declaração:
service cloud.firestore {
match /databases/{database}/documents {
// ...
}
}
A declaração do service cloud.firestore
as regras para o Cloud Firestore, evitando conflitos entre as regras de segurança do Cloud Firestore e as regras de outros produtos, como o Cloud Storage.
A declaração match /databases/{database}/documents
especifica que as regras devem corresponder a qualquer banco de dados do Cloud Firestore no projeto. Atualmente, cada projeto possui apenas um único banco de dados chamado (default)
.
Regras básicas de leitura/gravação
As regras básicas consistem em uma declaração de match
especificando um caminho de documento e uma expressão de allow
detalhando quando a leitura dos dados especificados é permitida:
service cloud.firestore {
match /databases/{database}/documents {
// Match any document in the 'cities' collection
match /cities/{city} {
allow read: if <condition>;
allow write: if <condition>;
}
}
}
Todas as declarações de correspondência devem apontar para documentos, não para coleções. Uma instrução match pode apontar para um documento específico, como em match /cities/SF
ou usar curingas para apontar para qualquer documento no caminho especificado, como em match /cities/{city}
.
No exemplo acima, a instrução match usa a sintaxe curinga {city}
. Isso significa que a regra se aplica a qualquer documento na coleção cities
, como /cities/SF
ou /cities/NYC
. Quando as expressões de allow
na instrução de correspondência forem avaliadas, a variável city
resolverá para o nome do documento da cidade, como SF
ou NYC
.
operações granulares
Em algumas situações, é útil dividir a read
e a write
em operações mais granulares. Por exemplo, seu aplicativo pode querer aplicar condições diferentes na criação de documentos e na exclusão de documentos. Ou você pode querer permitir leituras de documentos únicos, mas negar consultas grandes.
Uma regra de read
pode ser dividida em get
e list
, enquanto uma regra de write
pode ser dividida em create
, update
e delete
:
service cloud.firestore {
match /databases/{database}/documents {
// A read rule can be divided into get and list rules
match /cities/{city} {
// Applies to single document read requests
allow get: if <condition>;
// Applies to queries and collection read requests
allow list: if <condition>;
}
// A write rule can be divided into create, update, and delete rules
match /cities/{city} {
// Applies to writes to nonexistent documents
allow create: if <condition>;
// Applies to writes to existing documents
allow update: if <condition>;
// Applies to delete operations
allow delete: if <condition>;
}
}
}
dados hierárquicos
Os dados no Cloud Firestore são organizados em coleções de documentos, e cada documento pode estender a hierarquia por meio de subcoleções. É importante entender como as regras de segurança interagem com os dados hierárquicos.
Considere a situação em que cada documento da coleção cities
contém uma subcoleção de landmarks
. As regras de segurança se aplicam apenas ao caminho correspondente, portanto, os controles de acesso definidos na coleção de cities
não se aplicam à subcoleção de landmarks
. Em vez disso, escreva regras explícitas para controlar o acesso a subcoleções:
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city} {
allow read, write: if <condition>;
// Explicitly define rules for the 'landmarks' subcollection
match /landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
}
Ao aninhar instruções de match
, o caminho da instrução de match
interna é sempre relativo ao caminho da instrução de match
externa. Os seguintes conjuntos de regras são, portanto, equivalentes:
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city} {
match /landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
}
service cloud.firestore {
match /databases/{database}/documents {
match /cities/{city}/landmarks/{landmark} {
allow read, write: if <condition>;
}
}
}
Curingas recursivos
Se você deseja que as regras sejam aplicadas a uma hierarquia arbitrariamente profunda, use a sintaxe curinga recursiva, {name=**}
. Por exemplo:
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the cities collection as well as any document
// in a subcollection.
match /cities/{document=**} {
allow read, write: if <condition>;
}
}
}
Ao usar a sintaxe curinga recursiva, a variável curinga conterá todo o segmento de caminho correspondente, mesmo se o documento estiver localizado em uma subcoleção profundamente aninhada. Por exemplo, as regras listadas acima corresponderiam a um documento localizado em /cities/SF/landmarks/coit_tower
, e o valor da variável do document
seria SF/landmarks/coit_tower
.
Observe, no entanto, que o comportamento dos curingas recursivos depende da versão das regras.
Versão 1
As regras de segurança usam a versão 1 por padrão. Na versão 1, curingas recursivos correspondem a um ou mais itens de caminho. Eles não correspondem a um caminho vazio, então match /cities/{city}/{document=**}
corresponde a documentos em subcoleções, mas não à coleção cities
, enquanto match /cities/{document=**}
corresponde a ambos os documentos na coleções e subcoleções de cities
.
Os curingas recursivos devem vir no final de uma instrução de correspondência.
Versão 2
Na versão 2 das regras de segurança, os curingas recursivos correspondem a zero ou mais itens de caminho. match/cities/{city}/{document=**}
corresponde a documentos em quaisquer subcoleções, bem como documentos na coleção cities
.
Você deve aceitar a versão 2 adicionando rules_version = '2';
no topo de suas regras de segurança:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the cities collection as well as any document
// in a subcollection.
match /cities/{city}/{document=**} {
allow read, write: if <condition>;
}
}
}
Você pode ter no máximo um curinga recursivo por instrução de correspondência, mas na versão 2, você pode colocar esse curinga em qualquer lugar na instrução de correspondência. Por exemplo:
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the songs collection group
match /{path=**}/songs/{song} {
allow read, write: if <condition>;
}
}
}
Se você usar consultas de grupos de coleta , deverá usar a versão 2, consulte protegendo consultas de grupos de coleta .
Instruções de correspondência sobrepostas
É possível que um documento corresponda a mais de uma instrução de match
. No caso em que várias expressões de allow
correspondem a uma solicitação, o acesso é permitido se qualquer uma das condições for true
:
service cloud.firestore {
match /databases/{database}/documents {
// Matches any document in the 'cities' collection.
match /cities/{city} {
allow read, write: if false;
}
// Matches any document in the 'cities' collection or subcollections.
match /cities/{document=**} {
allow read, write: if true;
}
}
}
No exemplo acima, todas as leituras e gravações na coleção cities
serão permitidas porque a segunda regra é sempre true
, embora a primeira regra seja sempre false
.
Limites de regra de segurança
Ao trabalhar com regras de segurança, observe os seguintes limites:
Limite | Detalhes |
---|---|
Número máximo de chamadas exists() , get() e getAfter() por solicitação |
Exceder um dos limites resulta em um erro de permissão negada. Algumas chamadas de acesso a documentos podem ser armazenadas em cache e as chamadas armazenadas em cache não contam para os limites. |
Profundidade máxima da declaração de match aninhada | 10 |
Comprimento máximo do caminho, em segmentos de caminho, permitido em um conjunto de instruções de match aninhadas | 100 |
Número máximo de variáveis de captura de caminho permitidas em um conjunto de instruções de match aninhadas | 20 |
Profundidade máxima da chamada de função | 20 |
Número máximo de argumentos de função | 7 |
Número máximo de associações de variáveis let por função | 10 |
Número máximo de chamadas de função recursivas ou cíclicas | 0 (não permitido) |
Número máximo de expressões avaliadas por solicitação | 1.000 |
Tamanho máximo de um conjunto de regras | Os conjuntos de regras devem obedecer a dois limites de tamanho:
|
Próximos passos
- Escreva condições de regras de segurança personalizadas .
- Leia a referência das regras de segurança .