Partilhar via


Políticas de indexação no Azure Cosmos DB

APLICA-SE A: NoSQL

No Azure Cosmos DB, cada contentor tem uma política de indexação que determina como os itens do contentor devem ser indexados. A política de indexação predefinida para os contentores recém-criados indexa todas as propriedades de cada item e aplica índices de intervalo a qualquer cadeia ou número. Tal permite que obtenha um bom desempenho de consulta sem precisar de pensar na indexação e na gestão do índice antecipadamente.

Em algumas situações, talvez você queira substituir esse comportamento automático para melhor atender às suas necessidades. Você pode personalizar a política de indexação de um contêiner definindo seu modo de indexação e incluir ou excluir caminhos de propriedade.

Nota

O método de atualização de políticas de indexação descrito neste artigo só se aplica à API do Azure Cosmos DB para NoSQL. Saiba mais sobre a indexação na API do Azure Cosmos DB para MongoDB

Modo de indexação

O Azure Cosmos DB dá suporte a dois modos de indexação:

  • Consistente: o índice é atualizado de forma síncrona à medida que você cria, atualiza ou exclui itens. Isso significa que a consistência de suas consultas lidas será a consistência configurada para a conta.
  • Nenhum: a indexação está desativada no contêiner. Esse modo é comumente usado quando um contêiner é usado como um armazenamento de chave-valor puro, sem a necessidade de índices secundários. Ele também pode ser usado para melhorar o desempenho de operações em massa. Após a conclusão das operações em massa, o modo de índice pode ser definido como Consistente e, em seguida, monitorado usando o IndexTransformationProgress até a conclusão.

Nota

O Azure Cosmos DB também dá suporte a um modo de indexação Lazy. A indexação em diferido executa atualizações ao índice com um nível de prioridade muito menor quando o motor não está a realizar qualquer outro trabalho. Tal poderá levar a resultados de consulta inconsistentes ou incompletos. Se você planeja consultar um contêiner do Azure Cosmos DB, não deve selecionar indexação lenta. Novos contêineres não podem selecionar indexação lenta. Você pode solicitar uma isenção entrando em contato ( cosmosdbindexing@microsoft.com exceto se estiver usando uma conta do Azure Cosmos DB no modo sem servidor que não oferece suporte à indexação lenta).

Por padrão, a política de indexação é definida como automatic. Isso é conseguido definindo a automatic propriedade na política de indexação como true. Definir essa propriedade como true permite que o Azure Cosmos DB indexe automaticamente os itens à medida que são escritos.

Tamanho do índice

No Azure Cosmos DB, o armazenamento total consumido é a combinação do tamanho dos dados e do tamanho do índice. A seguir estão algumas características do tamanho do índice:

  • O tamanho do índice depende da política de indexação. Se todas as propriedades estiverem indexadas, o tamanho do índice poderá ser maior do que o tamanho dos dados.
  • Quando os dados são excluídos, os índices são compactados quase continuamente. No entanto, para pequenas exclusões de dados, você pode não observar imediatamente uma diminuição no tamanho do índice.
  • O tamanho do índice pode crescer temporariamente quando as partições físicas se dividem. O espaço de índice é liberado depois que a divisão da partição é concluída.

Incluir e excluir os caminhos das propriedades

Uma política de indexação personalizada pode especificar caminhos de propriedade que são explicitamente incluídos ou excluídos da indexação. Ao otimizar o número de caminhos indexados, você pode reduzir substancialmente a latência e a carga de RU das operações de gravação. Esses caminhos são definidos seguindo o método descrito na seção de visão geral da indexação com as seguintes adições:

  • Um caminho que leva a um valor escalar (cadeia de caracteres ou número) termina com /?
  • elementos de uma matriz são abordados juntos através da /[] notação (em vez de /0, /1 etc.)
  • O curinga /* pode ser usado para corresponder a quaisquer elementos abaixo do nó

Tomando novamente o mesmo exemplo:

    {
        "locations": [
            { "country": "Germany", "city": "Berlin" },
            { "country": "France", "city": "Paris" }
        ],
        "headquarters": { "country": "Belgium", "employees": 250 },
        "exports": [
            { "city": "Moscow" },
            { "city": "Athens" }
        ]
    }
  • o headquarterscaminho do employees é /headquarters/employees/?

  • o locationscaminho ' country é /locations/[]/country/?

  • o caminho para qualquer coisa abaixo headquarters é /headquarters/*

Por exemplo, poderíamos incluir o /headquarters/employees/? caminho. Esse caminho garantiria que indexássemos a propriedade, employees mas não indexássemos JSON aninhado extra dentro dessa propriedade.

Estratégia de inclusão/exclusão

Qualquer política de indexação deve incluir o caminho /* raiz como um caminho incluído ou excluído.

  • Inclua o caminho raiz para excluir seletivamente caminhos que não precisam ser indexados. Essa abordagem é recomendada, pois permite que o Azure Cosmos DB indexe proativamente qualquer nova propriedade que possa ser adicionada ao seu modelo.

  • Exclua o caminho raiz para incluir seletivamente caminhos que precisam ser indexados. O caminho da propriedade da chave de partição não é indexado por padrão com a estratégia de exclusão e deve ser explicitamente incluído, se necessário.

  • Para caminhos com caracteres regulares que incluem: caracteres alfanuméricos e _ (sublinhado), não é necessário escapar da cadeia de caracteres de caminho entre aspas duplas (por exemplo, "/path/?"). Para caminhos com outros caracteres especiais, você precisa escapar da cadeia de caracteres de caminho em torno de aspas duplas (por exemplo, "/"path-abc"/?"). Se você espera caracteres especiais em seu caminho, você pode escapar de todos os caminhos por segurança. Funcionalmente, não faz diferença se você escapar de todos os caminhos ou apenas daqueles que têm caracteres especiais.

  • A propriedade _etag system é excluída da indexação por padrão, a menos que o etag seja adicionado ao caminho incluído para indexação.

  • Se o modo de indexação estiver definido como consistente, as propriedades id do sistema serão _ts automaticamente indexadas.

  • Se um caminho explicitamente indexado não existir em um item, um valor será adicionado ao índice para indicar que o caminho está indefinido.

Todos os caminhos explicitamente incluídos têm valores adicionados ao índice para cada item no contêiner, mesmo que o caminho esteja indefinido para um determinado item.

Consulte esta seção para obter exemplos de políticas de indexação para incluir e excluir caminhos.

Incluir/excluir precedência

Se os caminhos incluídos e excluídos tiverem um conflito, o caminho mais preciso terá precedência.

Eis um exemplo:

Caminho incluído: /food/ingredients/nutrition/*

Caminho excluído: /food/ingredients/*

Nesse caso, o caminho incluído tem precedência sobre o caminho excluído porque é mais preciso. Com base nesses caminhos, quaisquer dados no food/ingredients caminho ou aninhados dentro seriam excluídos do índice. A exceção seriam os dados dentro do caminho incluído: /food/ingredients/nutrition/*, que seriam indexados.

Aqui estão algumas regras para precedência de caminhos incluídos e excluídos no Azure Cosmos DB:

  • Caminhos mais profundos são mais precisos do que caminhos mais estreitos. por exemplo: /a/b/? é mais preciso do que /a/?.

  • O /? é mais preciso do que /*. Por exemplo /a/? , é mais preciso do que /a/* isso /a/? tem precedência.

  • O caminho /* deve ser um caminho incluído ou um caminho excluído.

Índices de texto completo

Nota

Você deve habilitar o recurso de visualização da API NoSQL de Pesquisa Híbrida de Texto Completo para especificar um índice de texto completo.

Os índices de texto completo permitem a pesquisa e a pontuação de texto completo de forma eficiente usando o índice. A definição de um caminho de texto completo em uma política de indexação pode ser feita facilmente incluindo uma fullTextIndexes seção da política de indexação que contém todos os caminhos de texto a serem indexados. Por exemplo:

{
    "indexingMode": "consistent",
    "automatic": true,
    "includedPaths": [
        {
            "path": "/*"
        }
    ],
    "excludedPaths": [
        {
            "path": "/\"_etag\"/?"
        },
    ],
    "fullTextIndexes": [
        {
            "path": "/text"
        }
    ]
}

Importante

Uma política de indexação de texto completo deve estar no caminho definido na política de texto completo do contêiner. Saiba mais sobre as políticas de vetor de contêiner.

Índices vetoriais

Nota

Você deve habilitar o recurso de Pesquisa Vetorial NoSQL do Azure Cosmos DB para especificar um índice vetorial.

Os índices vetoriais aumentam a eficiência ao realizar pesquisas vetoriais usando a função do VectorDistance sistema. As pesquisas de vetores têm menor latência, maior taxa de transferência e menor consumo de RU ao aplicar um índice vetorial. Você pode especificar os seguintes tipos de políticas de índice de vetor:

Tipo Description Dimensões máximas
flat Armazena vetores no mesmo índice que outras propriedades indexadas. 505
quantizedFlat Quantifica (comprime) vetores antes de armazenar no índice. Isso pode melhorar a latência e a taxa de transferência ao custo de uma pequena quantidade de precisão. 4096
diskANN Cria um índice baseado no DiskANN para uma pesquisa aproximada rápida e eficiente. 4096

Importante

Atualmente, as políticas vetoriais e os índices vetoriais são imutáveis após a criação. Para fazer alterações, crie uma nova coleção.

Alguns pontos a observar:

  • Os flat tipos de índice e quantizedFlat aplicam o índice do Azure Cosmos DB para armazenar e ler cada vetor ao executar uma pesquisa vetorial. As pesquisas vetoriais com um flat índice são pesquisas de força bruta e produzem 100% de precisão ou recordação. Ou seja, é garantido encontrar os vetores mais semelhantes no conjunto de dados. No entanto, há uma limitação de 505 dimensões para vetores em um índice plano.

    • O quantizedFlat índice armazena vetores quantizados (compactados) no índice. Pesquisas vetoriais com quantizedFlat índice também são pesquisas de força bruta, no entanto, sua precisão pode ser um pouco inferior a 100%, uma vez que os vetores são quantificados antes de adicionar ao índice. No entanto, as pesquisas vetoriais com quantized flat devem ter menor latência, maior taxa de transferência e menor custo de RU do que as pesquisas vetoriais em um flat índice. Esta é uma boa opção para cenários em que você está usando filtros de consulta para restringir a pesquisa vetorial a um conjunto relativamente pequeno de vetores, e alta precisão é necessária.

    • O diskANN índice é um índice separado definido especificamente para vetores que aplicam o DiskANN, um conjunto de algoritmos de indexação vetorial de alto desempenho desenvolvidos pela Microsoft Research. Os índices DiskANN podem oferecer algumas das consultas de menor latência, maior taxa de transferência e menor custo de RU, mantendo alta precisão. No entanto, como o DiskANN é um índice de vizinhos mais próximos aproximados (ANN), a precisão pode ser menor do que quantizedFlat ou flat.

Os diskANN índices e quantizedFlat podem usar parâmetros opcionais de compilação de índice que podem ser usados para ajustar a troca de precisão versus latência que se aplica a cada índice vetorial Vizinhos Aproximados Mais Próximos.

  • quantizationByteSize: Define o tamanho (em bytes) para a quantização do produto. Min=1, Default=dynamic (o sistema decide), Max=512. Definir isso maior pode resultar em pesquisas vetoriais de maior precisão às custas de maior custo de RU e maior latência. Isso se aplica a ambos os quantizedFlat tipos e índice DiskANN .
    • indexingSearchListSize: Define quantos vetores pesquisar durante a construção da construção do índice. Mín=10, Padrão=100, Máx=500. Definir isso maior pode resultar em pesquisas vetoriais de maior precisão às custas de tempos de compilação de índice mais longos e latências de ingestão de vetores mais altas. Isto aplica-se apenas aos DiskANN índices.

Aqui está um exemplo de uma política de indexação com um índice vetorial:

{
    "indexingMode": "consistent",
    "automatic": true,
    "includedPaths": [
        {
            "path": "/*"
        }
    ],
    "excludedPaths": [
        {
            "path": "/_etag/?",
        },
        {
            "path": "/vector/*"
        }
    ],
    "vectorIndexes": [
        {
            "path": "/vector",
            "type": "diskANN"
        }
    ]
}

Importante

Uma política de indexação de vetores deve estar no caminho definido na política de vetores do contêiner. Saiba mais sobre as políticas de vetor de contêiner.

Importante

O caminho do vetor adicionado à seção "excludedPaths" da política de indexação para garantir um desempenho otimizado para inserção. Não adicionar o caminho do vetor a "excludedPaths" resultará em maior carga de RU e latência para inserções vetoriais.

Índices espaciais

Ao definir um caminho espacial na política de indexação, você deve definir qual índice type deve ser aplicado a esse caminho. Os tipos possíveis de índices espaciais incluem:

  • Ponto

  • Polígono

  • Multipolígono

  • LineString

O Azure Cosmos DB, por padrão, não criará nenhum índice espacial. Se você gostaria de usar funções internas do SQL espacial, você deve criar um índice espacial nas propriedades necessárias. Consulte esta seção para obter exemplos de políticas de indexação para adicionar índices espaciais.

Índices de tupla

Os índices de tupla são úteis ao executar a filtragem em vários campos dentro de um elemento de matriz. Os índices de tupla são definidos na seção includedPaths da política de indexação usando o especificador de tupla "[]".

Nota

Ao contrário dos caminhos incluídos ou excluídos, não é possível criar um caminho com o curinga /*. Todo caminho de tupla precisa terminar com "/?". Se uma tupla em um caminho de tupla não existir em um item, um valor será adicionado ao índice para indicar que a tupla está indefinida.

Os caminhos de tupla de matriz serão definidos na seção includedPaths e usarão a seguinte notação.

<path prefix>/[]/{<tuple 1>, <tuple 2> … <tuple n>}/?

Tenha em atenção que:

  • A primeira parte, o caminho Prefixo, é o caminho que é comum entre as tuplas. É o caminho da raiz para a matriz. No nosso exemplo é "/events".
  • Em seguida, está o especificador curinga de matriz "[]". Todos os caminhos de tupla de matriz devem ter um especificador curinga de matriz antes do especificador de tupla "{}".
  • Em seguida, é especificar as tuplas usando o especificador de tupla "{}".
  • As tuplas serão separadas por vírgula.
  • Tuple precisa usar a mesma especificação de caminho que outros caminhos de índice, com algumas exceções:
  • As tuplas não devem começar com o "/" à esquerda.
  • Tuplas não devem ter curingas de matriz.
  • Tuplas não devem acabar "?" ou "*"
  • “?” é o último segmento de um caminho de tupla e deve ser especificado imediatamente após o segmento especificador de tupla.

Por exemplo,

/events/[]/{name, category}/?

Estes são alguns exemplos de caminhos de tupla de matriz válidos :

    “includedPaths”:[  
        {“path”: “/events/[]/{name/first, name/last}/?”}, 
        {“path”: “/events/[]/{name/first, category}/?”}, 
        {“path”: “/events/[]/{name/first, category/subcategory}/?”}, 
        {“path”: “/events/[]/{name/[1]/first, category}/?”}, 
        {“path”: “/events/[]/{[1], [3]}/?”}, 
        {“path”: “/city/[1]/events/[]/{name, category}/?”} 
    ]

Estes são alguns exemplos de caminhos de tupla de matriz inválidos

  • /events/[]/{name/[]/first, category}/?
    • Uma das tuplas tem curinga array
  • /events/[]/{name, category}/*
    • O último segmento no caminho da tupla da matriz deve ser "?" e não *
  • /events/[]/{{name, first},category}/?
    • O especificador de tupla está aninhado
  • /events/{name, category}/?
    • O curinga de matriz está faltando antes do especificador de tupla
  • /events/[]/{/name,/category}/?
    • Tuplas começam com liderança /
  • /events/[]/{name/?,category/?}/?
    • As tuplas terminam com um ?
  • /city/[]/events/[]/{name, category}/?
    • O prefixo do caminho como 2 curingas de matriz

Índices compostos

As consultas que têm uma ORDER BY cláusula com duas ou mais propriedades exigem um índice composto. Você também pode definir um índice composto para melhorar o desempenho de muitas consultas de igualdade e intervalo. Por padrão, nenhum índice composto é definido, portanto, você deve adicionar índices compostos conforme necessário.

Ao contrário dos caminhos incluídos ou excluídos, não é possível criar um caminho com o curinga /* . Cada caminho composto tem um implícito /? no final do caminho que você não precisa especificar. Os caminhos compostos levam a um valor escalar que é o único valor incluído no índice composto. Se um caminho em um índice composto não existir em um item ou levar a um valor não escalar, um valor será adicionado ao índice para indicar que o caminho está indefinido.

Ao definir um índice composto, você especifica:

  • Dois ou mais caminhos de propriedade. A sequência na qual os caminhos de propriedade são definidos é importante.

  • A ordem (ascendente ou descendente).

Nota

Quando você adiciona um índice composto, a consulta utilizará índices de intervalo existentes até que a nova adição de índice composto seja concluída. Portanto, quando você adiciona um índice composto, você pode não observar imediatamente melhorias de desempenho. É possível acompanhar o progresso da transformação do índice usando um dos SDKs.

Consultas ORDER BY em várias propriedades:

As considerações a seguir são usadas ao usar índices compostos para consultas com uma ORDER BY cláusula com duas ou mais propriedades.

  • Se os caminhos de índice composto não corresponderem à sequência das propriedades na ORDER BY cláusula, o índice composto não poderá suportar a consulta.

  • A ordem dos caminhos de índice composto (ascendente ou descendente) também deve corresponder à order ORDER BY da cláusula.

  • O índice composto também suporta uma ORDER BY cláusula com a ordem oposta em todos os caminhos.

Considere o exemplo a seguir, onde um índice composto é definido no nome das propriedades, idade e _ts:

Índices Composto Consulta de exemplo ORDER BY Suportado pelo Índice Composto?
(name ASC, age ASC) SELECT * FROM c ORDER BY c.name ASC, c.age asc Yes
(name ASC, age ASC) SELECT * FROM c ORDER BY c.age ASC, c.name asc No
(name ASC, age ASC) SELECT * FROM c ORDER BY c.name DESC, c.age DESC Yes
(name ASC, age ASC) SELECT * FROM c ORDER BY c.name ASC, c.age DESC No
(name ASC, age ASC, timestamp ASC) SELECT * FROM c ORDER BY c.name ASC, c.age ASC, timestamp ASC Yes
(name ASC, age ASC, timestamp ASC) SELECT * FROM c ORDER BY c.name ASC, c.age ASC No

Você deve personalizar sua política de indexação para poder atender a todas as consultas necessárias ORDER BY .

Consultas com filtros em várias propriedades

Se uma consulta tiver filtros em duas ou mais propriedades, pode ser útil criar um índice composto para essas propriedades.

Por exemplo, considere a seguinte consulta que tem um filtro de igualdade e intervalo:

SELECT *
FROM c
WHERE c.name = "John" AND c.age > 18

Essa consulta é mais eficiente, levando menos tempo e consumindo menos RUs, se for capaz de aplicar um índice composto no (name ASC, age ASC).

As consultas com vários filtros de intervalo também podem ser otimizadas com um índice composto. No entanto, cada índice composto individual só pode otimizar um único filtro de intervalo. Os filtros de intervalo incluem >, <, <=, >=e !=. O filtro de intervalo deve ser definido em último lugar no índice composto.

Considere a seguinte consulta com um filtro de igualdade e dois filtros de intervalo:

SELECT *
FROM c
WHERE c.name = "John" AND c.age > 18 AND c._ts > 1612212188

Esta consulta é mais eficiente com um índice composto em (name ASC, age ASC) e (name ASC, _ts ASC). No entanto, a consulta não utilizaria um índice composto porque (age ASC, name ASC) as propriedades com filtros de igualdade devem ser definidas primeiro no índice composto. Dois índices compostos separados são necessários em vez de um único índice (name ASC, age ASC, _ts ASC) composto, uma vez que cada índice composto só pode otimizar um único filtro de intervalo.

As considerações a seguir são usadas ao criar índices compostos para consultas com filtros em várias propriedades

  • As expressões de filtro podem usar vários índices compostos.
  • As propriedades no filtro da consulta devem corresponder às do índice composto. Se uma propriedade estiver no índice composto, mas não estiver incluída na consulta como um filtro, a consulta não utilizará o índice composto.
  • Se uma consulta tiver outras propriedades no filtro que não estão definidas em um índice composto, uma combinação de índices compostos e de intervalo será usada para avaliar a consulta. Isso requer menos RUs do que o uso exclusivo de índices de intervalo.
  • Se uma propriedade tiver um filtro de intervalo (>, <, <=, >=, ou !=), essa propriedade deverá ser definida por último no índice composto. Se uma consulta tiver mais de um filtro de intervalo, ela poderá se beneficiar de vários índices compostos.
  • Ao criar um índice composto para otimizar consultas com vários filtros, o ORDER índice composto não tem impacto nos resultados. Esta propriedade é opcional.

Considere os seguintes exemplos em que um índice composto é definido no nome das propriedades, idade e carimbo de data/hora:

Índices Composto Consulta de exemplo Suportado pelo Índice Composto?
(name ASC, age ASC) SELECT * FROM c WHERE c.name = "John" AND c.age = 18 Yes
(name ASC, age ASC) SELECT * FROM c WHERE c.name = "John" AND c.age > 18 Yes
(name ASC, age ASC) SELECT COUNT(1) FROM c WHERE c.name = "John" AND c.age > 18 Yes
(name DESC, age ASC) SELECT * FROM c WHERE c.name = "John" AND c.age > 18 Yes
(name ASC, age ASC) SELECT * FROM c WHERE c.name != "John" AND c.age > 18 No
(name ASC, age ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" AND c.age = 18 AND c.timestamp > 123049923 Yes
(name ASC, age ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" AND c.age < 18 AND c.timestamp = 123049923 No
(name ASC, age ASC) and (name ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" AND c.age < 18 AND c.timestamp > 123049923 Yes

Consultas com filtro e ORDER BY

Se uma consulta filtra uma ou mais propriedades e tem propriedades diferentes na cláusula ORDER BY, pode ser útil adicionar as propriedades no filtro à ORDER BY cláusula.

Por exemplo, adicionando as propriedades no filtro à ORDER BY cláusula, a seguinte consulta pode ser reescrita para aplicar um índice composto:

Consulta usando o índice de intervalo:

SELECT *
FROM c 
WHERE c.name = "John" 
ORDER BY c.timestamp

Consulta usando índice composto:

SELECT * 
FROM c 
WHERE c.name = "John"
ORDER BY c.name, c.timestamp

As mesmas otimizações de consulta podem ser generalizadas para quaisquer ORDER BY consultas com filtros, tendo em mente que índices compostos individuais só podem suportar, no máximo, um filtro de intervalo.

Consulta usando o índice de intervalo:

SELECT * 
FROM c 
WHERE c.name = "John" AND c.age = 18 AND c.timestamp > 1611947901 
ORDER BY c.timestamp

Consulta usando índice composto:

SELECT * 
FROM c 
WHERE c.name = "John" AND c.age = 18 AND c.timestamp > 1611947901 
ORDER BY c.name, c.age, c.timestamp

Além disso, você pode usar índices compostos para otimizar consultas com funções do sistema e ORDER BY:

Consulta usando o índice de intervalo:

SELECT * 
FROM c 
WHERE c.firstName = "John" AND Contains(c.lastName, "Smith", true) 
ORDER BY c.lastName

Consulta usando índice composto:

SELECT * 
FROM c 
WHERE c.firstName = "John" AND Contains(c.lastName, "Smith", true) 
ORDER BY c.firstName, c.lastName

As seguintes considerações se aplicam ao criar índices compostos para otimizar uma consulta com um filtro e ORDER BY uma cláusula:

  • Se você não definir um índice composto em uma consulta com um filtro em uma propriedade e uma cláusula separada ORDER BY usando uma propriedade diferente, a consulta ainda terá êxito. No entanto, o custo RU da consulta pode ser reduzido com um índice composto, particularmente se a ORDER BY propriedade na cláusula tiver uma cardinalidade alta.
  • Se a consulta filtrar propriedades, essas propriedades devem ser incluídas primeiro na ORDER BY cláusula.
  • Se a consulta filtra em várias propriedades, os filtros de igualdade devem ser as primeiras propriedades na ORDER BY cláusula.
  • Se a consulta filtra em várias propriedades, você pode ter no máximo um filtro de intervalo ou função do sistema utilizada por índice composto. A propriedade usada no filtro de intervalo ou na função do sistema deve ser definida em último lugar no índice composto.
  • Todas as considerações para criar índices compostos para ORDER BY consultas com várias propriedades e consultas com filtros em várias propriedades ainda se aplicam.
Índices Composto Consulta de exemplo ORDER BY Suportado pelo Índice Composto?
(name ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" ORDER BY c.name ASC, c.timestamp ASC Yes
(name ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" AND c.timestamp > 1589840355 ORDER BY c.name ASC, c.timestamp ASC Yes
(timestamp ASC, name ASC) SELECT * FROM c WHERE c.timestamp > 1589840355 AND c.name = "John" ORDER BY c.timestamp ASC, c.name ASC No
(name ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" ORDER BY c.timestamp ASC, c.name ASC No
(name ASC, timestamp ASC) SELECT * FROM c WHERE c.name = "John" ORDER BY c.timestamp ASC No
(age ASC, name ASC, timestamp ASC) SELECT * FROM c WHERE c.age = 18 and c.name = "John" ORDER BY c.age ASC, c.name ASC,c.timestamp ASC Yes
(age ASC, name ASC, timestamp ASC) SELECT * FROM c WHERE c.age = 18 and c.name = "John" ORDER BY c.timestamp ASC No

Consultas com um filtro e um agregado

Se uma consulta filtra uma ou mais propriedades e tem uma função de sistema de agregação, pode ser útil criar um índice composto para as propriedades na função de sistema de filtro e agregação. Esta otimização aplica-se às funções do sistema SUM e AVG .

As considerações a seguir se aplicam ao criar índices compostos para otimizar uma consulta com uma função de filtro e agregação do sistema.

  • Os índices compostos são opcionais ao executar consultas com agregações. No entanto, o custo de RU da consulta muitas vezes pode ser reduzido com um índice composto.
  • Se a consulta filtra em várias propriedades, os filtros de igualdade devem ser as primeiras propriedades no índice composto.
  • Você pode ter no máximo um filtro de intervalo por índice composto e ele deve estar na propriedade na função de sistema agregado.
  • A propriedade na função de sistema agregado deve ser definida em último lugar no índice composto.
  • O order (ASC ou DESC) não importa.
Índices Composto Consulta de exemplo Suportado pelo Índice Composto?
(name ASC, timestamp ASC) SELECT AVG(c.timestamp) FROM c WHERE c.name = "John" Yes
(timestamp ASC, name ASC) SELECT AVG(c.timestamp) FROM c WHERE c.name = "John" No
(name ASC, timestamp ASC) SELECT AVG(c.timestamp) FROM c WHERE c.name > "John" No
(name ASC, age ASC, timestamp ASC) SELECT AVG(c.timestamp) FROM c WHERE c.name = "John" AND c.age = 25 Yes
(age ASC, timestamp ASC) SELECT AVG(c.timestamp) FROM c WHERE c.name = "John" AND c.age > 25 No

Índices compostos com um curinga de matriz

Abaixo está um exemplo de um índice composto que contém um curinga de matriz.

{  
    "automatic":true,
    "indexingMode":"Consistent",
    "includedPaths":[  
        {  
            "path":"/*"
        }
    ],
    "excludedPaths":[],
    "compositeIndexes":[  
        [  
            {"path":"/familyname", "order":"ascending"},
            {"path":"/children/[]/age", "order":"descending"}
        ]
    ]
}

Um exemplo de consulta que pode se beneficiar desse índice composto é:

SELECT r.id
FROM root r
JOIN ch IN r.children
WHERE r.familyname = 'Anderson' AND ch.age > 20

Modificando a política de indexação

A política de indexação de um contêiner pode ser atualizada a qualquer momento usando o portal do Azure ou um dos SDKs com suporte. Uma atualização da política de indexação aciona uma transformação do índice antigo para o novo, que é realizada online e in-loco (para que nenhum espaço de armazenamento extra seja consumido durante a operação). A política de indexação antiga é transformada de forma eficiente na nova política sem afetar a disponibilidade de gravação, a disponibilidade de leitura ou a taxa de transferência provisionada no contêiner. A transformação de índice é uma operação assíncrona, e o tempo necessário para ser concluída depende da taxa de transferência provisionada, do número de itens e de seu tamanho. Se várias atualizações de política de indexação precisarem ser feitas, é recomendável fazer todas as alterações como uma única operação para que a transformação do índice seja concluída o mais rápido possível.

Importante

A transformação de índice é uma operação que consome unidades de solicitação.

Nota

Você pode acompanhar o progresso da transformação do índice no portal do Azure ou usando um dos SDKs.

Não há impacto na disponibilidade de gravação durante quaisquer transformações de índice. A transformação do índice usa suas RUs provisionadas, mas com uma prioridade menor do que suas operações ou consultas CRUD.

Não há impacto na disponibilidade de leitura ao adicionar novos caminhos indexados. As consultas só utilizarão novos caminhos indexados quando uma transformação de índice for concluída. Em outras palavras, ao adicionar um novo caminho indexado, as consultas que se beneficiam desse caminho indexado têm o mesmo desempenho antes e durante a transformação do índice. Após a conclusão da transformação do índice, o mecanismo de consulta começará a usar os novos caminhos indexados.

Ao remover caminhos indexados, você deve agrupar todas as alterações em uma transformação de política de indexação. Se você remover vários índices e fizer isso em uma única alteração de política de indexação, o mecanismo de consulta fornecerá resultados consistentes e completos em toda a transformação do índice. No entanto, se você remover índices por meio de várias alterações de política de indexação, o mecanismo de consulta não fornecerá resultados consistentes ou completos até que todas as transformações de índice sejam concluídas. A maioria dos desenvolvedores não descarta índices e, em seguida, imediatamente tenta executar consultas que utilizam esses índices, portanto, na prática, essa situação é improvável.

Quando você solta um caminho indexado, o mecanismo de consulta interromperá imediatamente o uso e fará uma verificação completa.

Nota

Sempre que possível, você deve sempre tentar agrupar várias remoções de índice em uma única modificação de política de indexação.

Importante

A remoção de um índice entra em vigor imediatamente, enquanto a adição de um novo índice leva algum tempo, pois requer uma transformação de indexação. Ao substituir um índice por outro (por exemplo, substituindo um único índice de propriedade por um índice composto), certifique-se de adicionar o novo índice primeiro e, em seguida, aguarde a conclusão da transformação do índice antes de remover o índice anterior da política de indexação. Caso contrário, isso afetará negativamente sua capacidade de consultar o índice anterior e poderá interromper quaisquer cargas de trabalho ativas que façam referência ao índice anterior.

Políticas de indexação e TTL

O uso do recurso TTL (Time-to-Live) requer indexação. Isto significa que:

  • não é possível ativar o TTL em um contêiner onde o modo de indexação está definido como none,
  • não é possível definir o modo de indexação como Nenhum em um contêiner onde o TTL está ativado.

Para cenários em que nenhum caminho de propriedade precisa ser indexado, mas o TTL é necessário, você pode usar uma política de indexação com um modo de indexação definido como consistent, sem caminhos incluídos e /* como o único caminho excluído.