Эффект Cosmos db ARRAY_LENGTH

У меня была проблема, когда действительный запрос ничего не возвращал, пока он должен:

SELECT * 
FROM root 
WHERE 
    (ARRAY_LENGTH(root["orderData"]["_attachments"]) > 0
    AND root["orderData"]["_status"] = "ARCHIVEDVALIDATED") 
OR root["orderData"]["_status"] = "ARCHIVEDREJECTED"

Благодаря сообществу stackoverflow, я узнал, что это было потому, что он принимал слишком много RU, и ничего не возвращалось.

После копания и проверки серверных вещей я узнал, что если я удалю ARRAY_LENGTH(root["orderData"]["_attachments"]) > 0, мой запрос будет идти от 13k RU до 600 RU ..

Я не могу найти способ исправить это, исправление, которое я нашел до сих пор, заключается в удалении ARRAY_LENGTH(root["orderData"]["_attachments"]) > 0из запроса и последующем его фильтрации в памяти (что не очень хорошо ...)

Я что-то упускаю? Как я могу это исправить?

Спасибо!

azure-cosmosdb,

0

Ответов: 2


0

Чтобы выяснить несоответствие в RU между двумя запросами, вы можете проверить показатели запросов для обоих запросов в соответствии с https://docs.microsoft.com/en-us/azure/cosmos-db/sql-api-sql -query-metrics .

Вы также можете попытаться обменять первые два выражения и посмотреть, не имеет ли это никакого значения. В основном попробуйте этот запрос:

SELECT * FROM root WHERE (((root["orderData"]["_status"] = "ARCHIVEDVALIDATED") AND (ARRAY_LENGTH(root["orderData"]["_attachments"]) > 0)) OR (root["orderData"]["_status"] = "ARCHIVEDREJECTED"))

0

600RU все еще очень-очень плохо. Это не решение.

Причиной такой плохой производительности является то, что ваш запрос не может использовать индексы, а полное сканирование никогда не может масштабироваться. Будучи плохим сейчас, оно будет ухудшаться по мере роста вашей коллекции.

Вам нужно убедиться, что ваш запрос может использовать индекс, чтобы анализировать только минимально возможные количества документов. Трудно предложить точное решение, не зная распределения данных по значениям orderdata.statusи orderdata._attachments.length, но вы должны учитывать:

  • Опустите OR . Запросы «того или иного» не могут использовать индекс. CosmosDB использует только один индекс для каждого запроса. Если orderdata.statusзначения достаточно избирательны, вы получите намного лучшую производительность RU / 2, выполнив 2 вызова и объединив результаты в клиенте.
  • Предварительно расчитайте свое состояние на отдельное свойство и поместите на него индекс . Да, это дублирование данных, но несколько лишних байтов ничего вам не стоят, в то время как RU и производительность обойдутся вам в деньгах, а также в работе с пользователями.

Вы также можете комбинировать их, например, имея 2 запроса и сохраняя только количество массивов. Подумайте о своих данных и протестируйте их.

лазурь-cosmosdb,
Похожие вопросы
Яндекс.Метрика