Gerenciar índices
O Firestore garante o alto desempenho das consultas ao exigir um índice de todas elas. Os índices necessários para as consultas mais básicas são criados automaticamente para você. À medida que você usa e testa o aplicativo, o Cloud Firestore gera mensagens de erro para ajudar na criação de outros índices necessários. Esta página descreve como gerenciar índices de campo único, compostos e [vetor][vetor].
Criar um índice inexistente usando uma mensagem de erro
Se você tentar executar uma consulta composta com uma cláusula de intervalo que não esteja mapeada a um índice atual, um erro será retornado. A mensagem desse erro inclui um link direto para você criar o índice ausente no Firebase console.
Abra o link gerado para o Firebase console, revise as informações preenchidas automaticamente e clique em Criar.
Caso um índice vetorial seja necessário, a mensagem de erro vai incluir um comando da Google Cloud CLI para criar o índice vetorial ausente. Execute o comando para criar o índice ausente.
Papéis e permissões
Antes de criar um índice no Firestore, confirme se um dos papéis a seguir foi atribuído:
roles/datastore.owner
roles/datastore.indexAdmin
roles/editor
roles/owner
Se você tiver definido papéis personalizados, atribua todas as permissões a seguir para criar índices:
datastore.indexes.create
datastore.indexes.delete
datastore.indexes.get
datastore.indexes.list
datastore.indexes.update
Usar o Console do Google Cloud Platform
No Console do Google Cloud Platform, é possível gerenciar isenções de indexação de campo único e índices compostos.
Criar um índice composto
Para criar manualmente um novo índice composto a partir do Console do GCP, faça isto:
No Console do Google Cloud, acesse a página Bancos de Dados.
Selecione o banco de dados necessário na lista de bancos de dados.
No menu de navegação, clique em Índices e na guia Composto.
Clique em Criar índice.
Insira um ID de coleção. Adicione os nomes dos campos que você quer indexar e um modo de índice para cada campo. Clique em Salvar índice.
Seu novo índice será exibido na lista de índices compostos, e o Firestore começará a criar seu índice. Quando o processo de criação terminar, você verá uma marca de seleção verde próxima ao índice.
Excluir um índice composto
Para excluir um índice composto, realize estas ações:
No Console do Google Cloud, acesse a página Bancos de Dados.
Selecione o banco de dados necessário na lista de bancos de dados.
No menu de navegação, clique em Índices e na guia Composto.
Na lista de índices compostos, clique no botão Mais
referente ao índice que você quer excluir. Clique em Excluir.Confirme que quer excluir o índice clicando em Excluir índice no alerta.
Adicionar uma isenção de índice de campo único
As isenções de índice de campo único permitem modificar configurações automáticas de índice para campos específicos em uma coleção. É possível adicionar uma isenção de campo único no console:
No Console do Google Cloud, acesse a página Bancos de Dados.
Selecione o banco de dados necessário na lista de bancos de dados.
No menu de navegação, clique em Índices e na guia Campo único.
Clique em Adicionar isenção.
Insira um ID da coleção e um caminho de campo.
Selecione novas configurações de indexação para o campo. Ative ou desative os índices de campo único crescente, decrescente e de "matriz contém" atualizados automaticamente.
Clique em Salvar isenção.
Adicionar uma isenção no nível da coletânea
Para definir uma isenção de índice de campo único que se aplica a todos os campos em um ID de coleção:
- Clique em Adicionar isenção.
Insira um ID da coleção para o grupo de coleções e defina Caminho do campo como
*
.Selecione as isenções de indexação que você quer aplicar a todos os campos no grupo de coleções.
Clique em Salvar isenção.
Excluir uma isenção de índice de campo único
Para excluir uma isenção de índice de campo único, faça isto:
No Console do Google Cloud, acesse a página Bancos de Dados.
Selecione o banco de dados necessário na lista de bancos de dados.
No menu de navegação, clique em Índices e na guia Campo único.
Na lista de isenções de índice de campo único, clique no botão
Mais para isenção do que gostaria de excluir. Clique em Excluir.Confirme que você quer excluir a isenção clicando em Excluir no alerta.
Ao excluir uma isenção de campo único, o campo ou subcampo especificado usará as configurações de indexação herdadas. Os campos do documento são revertidos para as configurações automáticas de índice do seu banco de dados. Os subcampos de um mapa herdam qualquer isenção em campos pai antes de herdarem configurações automáticas de índice.
Na Firebase CLI
Também é possível implantar índices com a CLI do Firebase.
Para começar, execute o comando firebase init firestore
no diretório do projeto.
Durante a configuração, a Firebase CLI gera um arquivo JSON com os índices
padrão no formato correto. Edite o arquivo para adicionar mais índices e faça a implantação
usando o comando firebase deploy
.
Para implantar apenas índices e regras do Firestore, adicione a
flag --only firestore
.
Se você fizer edições nos índices usando o Console do Firebase, atualize o arquivo de índices local. Consulte a referência de definição do índice JSON.
Usar o Terraform
Como criar índices no banco de dados
Os bancos de dados do Firestore podem incluir índices de campo único e compostos. É possível editar o arquivo de configuração do Terraform para criar um índice para o banco de dados.
Os índices de campo único e compostos usam tipos de recursos do Terraform distintos
(google_firestore_index
e google_firestore_field
).
Índice de campo único
O exemplo de arquivo de configuração do Terraform a seguir cria um índice de campo único no campo name
na coleção chatrooms
:
firestore.tf
resource "random_id" "variable"{ byte_length = 8 } resource "google_firestore_field" "single-index" { project = "project-id" database = "database-id" collection = "chatrooms_${random_id.variable.hex}" field = "name" index_config { indexes { order = "ASCENDING" query_scope = "COLLECTION_GROUP" } indexes { array_config = "CONTAINS" } } ttl_config {} }
- Substitua project-id pela ID do seu projeto. Os ID do projeto precisam ser exclusivos.
- Substitua database-id pelo ID do banco de dados.
Índice composto
O exemplo de arquivo de configuração do Terraform a seguir cria um índice composto para uma combinação dos campos name
e description
na coleção chatrooms
:
firestore.tf
resource "google_firestore_index" "composite-index" { project = "project-id" database = "database-id" collection = "chatrooms" fields { field_path = "name" order = "ASCENDING" } fields { field_path = "description" order = "DESCENDING" } }
- Substitua project-id pela ID do seu projeto. Os ID do projeto precisam ser exclusivos.
- Substitua database-id pelo ID do banco de dados.
Índice vetorial
O exemplo de arquivo de configuração do Terraform a seguir cria um índice vetorial no campo embedding
na coleção chatrooms
:
firestore.tf
resource "google_firestore_index" "vector-index" { project = "project-id" database = "database-id" collection = "chatrooms" fields { field_path = "__name__" order = "ASCENDING" } fields { field_path = "embedding" vector_config { dimension = 128 flat {} } } }
- Substitua project-id pela ID do seu projeto. Os ID do projeto precisam ser exclusivos.
- Substitua database-id pelo ID do banco de dados.
Índices do modo Datastore
Também é possível criar índices do modo de repositório de dados usando o Terraform.
datastore.tf
resource "google_firestore_index" "datastore-mode-index" { project = "project-id" database = "database-id" collection = "chatrooms" fields { field_path = "name" order = "ASCENDING" } fields { field_path = "description" order = "DESCENDING" } query_scope = "COLLECTION_GROUP" api_scope = "DATASTORE_MODE_API" }
Migrar de google_datastore_index
O recurso google_datastore_index
foi descontinuado e não estará disponível na versão 6.0.0 e mais recentes do terraform-provider-google.
Se você usava o recurso google_datastore_index
, pode migrar para google_firestore_index
.
Para migrar, faça o seguinte:
- Crie um recurso
google_firestore_index
equivalente. - Importe o índice do modo Datastore para o novo recurso.
- Remova as referências ao recurso
google_datastore_index
antigo. - Remova o recurso
google_datastore_index
antigo do estado do Terraform. - Execução de
terraform apply
para aplicar as mudanças.
Confira instruções mais detalhadas:
- Escreva um
google_firestore_index
substituto com base no recursogoogle_datastore_index
atual. Confira as mudanças necessárias abaixo. - Determine o caminho do recurso do Firestore do seu índice:
export INDEX_RESOURCE_PATH=$(echo '"projects/${google_datastore_index.datastore-index-resource-name.project}/databases/(default)/collectionGroups/${google_datastore_index.datastore-index-resource-name.kind}/indexes/${google_datastore_index.datastore-index-resource-name.index_id}"' | terraform console | tr -d '"')
Substitua datastore-index-resource-name pelo nome do recurso do Terraform.
- Importe o índice do modo Datastore para o recurso
google_firestore_index
criado acima:terraform import google_firestore_index.firestore-index-resource-name $INDEX_RESOURCE_PATH
Substitua firestore-index-resource-name pelo nome do recurso do Terraform.
Para mais informações sobre a importação de recursos de índice do Firestore, consulte a documentação de referência do google_firestore_index.
- Exclua o recurso
google_datastore_index
do arquivo de configuração do Terraform. - Remova o recurso
google_datastore_index
atual do estado do Terraform:terraform state rm google_datastore_index.datastore-index-resource-name
Para mais informações sobre a remoção de recursos, consulte a página do Terraform sobre Remoção de recursos.
- Execute
terraform plan
. Verifique a saída para confirmar que você não está criando nem destruindo recursos.Inspecione a saída para garantir que a importação foi concluída. Se a saída mostrar que algum campo está mudando, verifique se essas mudanças são intencionais. Se a saída incluir uma linha semelhante a esta:
google_firestore_index.firestore-index-resource-name must be replaced
Em seguida, inspecione o arquivo de configuração do Terraform para saber se há algum erro.
- Quando estiver satisfeito com a saída do plano do Terraform, execute:
terraform apply
- Substitua
google_datastore_index
porgoogle_firestore_index
. - Substitua o nome do argumento
kind
porcollection
, mas mantenha o valor do argumento. - Substitua o nome do argumento
ancestor
porquery_scope
. Substitua o valor do argumentoALL_ANCESTORS
porCOLLECTION_RECURSIVE
e qualquer outro valor porCOLLECTION_GROUP
. Se não houver um argumentoancestor
, adicione um argumentoquery_scope
com o valorCOLLECTION_GROUP
. - Adicione o argumento
api_scope
com o valorDATASTORE_MODE_API
. - Para cada instância de
properties
, substitua por uma instância correspondente defields
. Substitua cada instância dename
porfield_path
e cada instância dedirection
pororder
. A configuração de um índice leva alguns minutos. O tempo de criação mínimo de um índice é de alguns minutos, mesmo para um banco de dados vazio.
O tempo de preenchimento depende da quantidade de dados no índice novo. Quanto mais valores de campo corresponderem à definição do índice, mais demorado será o preenchimento.
Traduzir o índice
Para traduzir um recurso google_datastore_index para o recurso google_firestore_index equivalente, copie-o e faça as seguintes alterações:
Por exemplo, considere este recurso google_datastore_index
:
datastore.tf
resource "google_datastore_index" "legacy" { kind = "foo" properties { name = "property_a" direction = "ASCENDING" } properties { name = "property_b" direction = "ASCENDING" } }
O recurso google_firestore_index
equivalente seria:
resource "google_firestore_index" "new" { // note: defaults to the provider project project = project // note: defaults to the (default) database database = "(default)" collection = "foo" api_scope = "DATASTORE_MODE_API" // since there was no "ancestor" property set above, use COLLECTION_GROUP here query_scope = "COLLECTION_GROUP" fields { field_path = "property_a" order = "ASCENDING" } fields { field_path = "property_b" order = "ASCENDING" } }
Tempo de criação do índice
Para criar um índice, o Firestore precisa configurar o índice e, em seguida, preencher o índice com os dados existentes. O tempo de criação do índice é a soma do tempo de configuração e do tempo de preenchimento:
As versões de índice são operações de longa duração.
Depois de iniciar um build de índice, o Firestore atribui
um nome exclusivo à operação. Os nomes das operações são prefixados com projects/[PROJECT_ID]/databases/(default)/operations/
, por exemplo:
projects/project-id/databases/(default)/operations/ASA1MTAwNDQxNAgadGx1YWZlZAcSeWx0aGdpbi1zYm9qLW5pbWRhEgopEg
No entanto, é possível deixar de fora o prefixo ao especificar um nome de operação para
o comando describe
.
Como listar todas as operações de longa duração
Para listar operações de longa duração, use o comando gcloud firestore operations list. Esse comando lista as operações contínuas e as concluídas recentemente. As operações são listadas por alguns dias após a conclusão:
gcloud firestore operations list
Verificar o status da operação
Em vez de listar todas as operações de longa duração, é possível listar os detalhes de uma única operação:
gcloud firestore operations describe operation-name
Como estimar o tempo de conclusão
Conforme sua operação é executada, consulte o valor do campo state
para o status geral da operação.
Uma solicitação para o status de uma operação de longa duração também retorna as métricas
workEstimated
e workCompleted
. Essas métricas são retornadas para o número
de documentos. workEstimated
mostra o número total estimado de documentos que uma
operação processará. workCompleted
mostra o número de documentos processados até o momento. Após a conclusão da operação,
workCompleted
reflete o número total de documentos que foram
realmente processados, o que pode ser diferente do valor de workEstimated
.
Divida workCompleted
por workEstimated
para ter uma estimativa aproximada do andamento. A
estimativa pode ser imprecisa porque depende da coleção de estatísticas em
atraso.
Por exemplo, veja o status do progresso de uma criação de índice:
{ "operations": [ { "name": "projects/project-id/operations/AyAyMDBiM2U5NTgwZDAtZGIyYi0zYjc0LTIzYWEtZjg1ZGdWFmZWQHEjF0c2Flc3UtcmV4ZWRuaS1uaW1kYRUKSBI", "metadata": { "@type": "type.googleapis.com/google.firestore.admin.v1.IndexOperationMetadata", "common": { "operationType": "CREATE_INDEX", "startTime": "2020-06-23T16:52:25.697539Z", "state": "PROCESSING" }, "progressDocuments": { "workCompleted": "219327", "workEstimated": "2198182" } }, }, ...
Quando uma operação for concluída, a descrição da operação conterá "done":
true
. Veja o valor do campo state
para
o resultado da operação. Se o campo done
não for definido na resposta,
seu valor será false
. Não dependa da existência do valor done
para operações em andamento.
Erros na criação do índice
Talvez você encontre erros na criação ao gerenciar índices compostos e isenções de índices de campo único. A indexação pode falhar se o Firestore encontrar um problema com os dados usados nessa operação. Isso costuma significar que você atingiu um limite de índice. Por exemplo, a operação pode ter atingido o número máximo de entradas de índice por documento.
Se a criação do índice falhar, você verá a mensagem de erro no console. Verifique se você atingiu algum limite de índice. Depois, tente novamente a operação de indexação.