Как индексировать и запрашивать сложные пространственные типы в CosmosDB? - PullRequest
1 голос
/ 19 июня 2020

У меня есть база данных / коллекция CosmosDB с ключом раздела на /id и включенной пространственной индексацией с использованием конфигурации Geography. Когда я запрашиваю объекты со свойством LineString в заданном LineString или Polygon, запрос извлекает все документы в коллекции перед возвратом тех, которые находятся в пределах LineString / Polygon (получено больше чем вывод). Потребляемые единицы RU растут по мере увеличения количества элементов в коллекции, что сигнализирует мне, что он в основном выполняет сканирование, а индекс не работает.

В документации CosmosDB указано следующее:

Azure Cosmos DB поддерживает индексацию точек, строк линий, многоугольников и мультиполигонов

Однако в документации нет примеров, которые не используют Point type, и я не могу выполнить запрос с использованием перестановок исключительно типов, отличных от Point, и попасть в индекс.

Чтобы проверить работу пространственного индексирования, у меня есть дополнительное свойство Start для элемента со значением сначала Point в LineString, и я могу запросить, находится ли это в пределах Polygon при постоянном потреблении RU.

Вот индекс:

{
    "indexingMode": "consistent",
    "automatic": true,
    "includedPaths": [
        {
            "path": "/*"
        }
    ],
    "excludedPaths": [
        {
            "path": "/\"_etag\"/?"
        }
    ],
    "spatialIndexes": [
        {
            "path": "/*",
            "types": [
                "Point",
                "LineString",
                "Polygon",
                "MultiPolygon"
            ]
        }
    ]
}

Вот игла. Стог сена - это около 1000 объектов со случайными LineStrings.

{
    "id": "test",
    "Start": {
        "type": "Point",
        "coordinates": [ 1, 3 ]
    },
    "Points": {
        "type": "LineString",
        "coordinates": [ [ 1, 3 ], [ 1, 4 ], [ 1, 5 ] ]
    }
}

Вот поиск в Polygon:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Points, {
    "type":"Polygon",
    "coordinates": [[[0, 10], [0, 0], [2, 0], [2, 10], [0, 10]]]
})
---
Request Charge:           127.4 RUs
Retrieved document count: 992
Retrieved document size:  1219980 bytes
Output document count:    1
Output document size:     441 bytes
Index hit document count: 0
Index lookup time:        3.77 ms

Вот поиск в LineString:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Points, {
    "type":"LineString",
    "coordinates": [[1, 3], [1, 4], [1, 5]]
})
---
Request Charge:           122.53 RUs
Retrieved document count: 992
Retrieved document size:  1219980 bytes
Output document count:    1
Output document size:     441 bytes
Index hit document count: 0
Index lookup time:        3.0100000000000002 ms

Вот поиск Start в том же Polygon, что и выше, показывающий, что пространственное индексирование включено и работает:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Start, {
    "type":"Polygon",
    "coordinates": [[[0, 10], [0, 0], [2, 0], [2, 10], [0, 10]]]
---
Request Charge:           8.1 RUs
Retrieved document count: 1
Retrieved document size:  343 bytes
Output document count:    1
Output document size:     392 bytes
Index hit document count: 1
Index lookup time:        2.79 ms

1 Ответ

0 голосов
/ 22 июня 2020

Я создаю контейнер и добавляю ваш образец документа, но результат отличается от вашего.

Первый sql результат:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Points, {
    "type":"Polygon",
    "coordinates": [[[0, 10], [0, 0], [2, 0], [2, 10], [0, 10]]]
})
---
Request Charge:            10.53 RUs
Retrieved document count:  1
Retrieved document size:   349 bytes
Output document count:     1
Output document size:      398 bytes
Index hit document count:  1
Index lookup time:         1.6800000000000002 ms

Второй sql результат:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Points, {
    "type":"LineString",
    "coordinates": [[1, 3], [1, 4], [1, 5]]
})
---
Request Charge:            7.24 RUs
Retrieved document count:  1
Retrieved document size:   349 bytes
Output document count:     1
Output document size:      398 bytes
Index hit document count:  1
Index lookup time:         1.1399000000000001 ms

Третий sql результат:

SELECT *
FROM items i
WHERE ST_WITHIN(i.Start, {
    "type":"Polygon",
    "coordinates": [[[0, 10], [0, 0], [2, 0], [2, 10], [0, 10]]]
})
---
Request Charge:            10.53 RUs
Retrieved document count:  1
Retrieved document size:   349 bytes
Output document count:     1
Output document size:      398 bytes
Index hit document count:  1
Index lookup time:         1.6500000000000001 ms

Согласно моему тесту, каждый sql попадает в индекс.

Кстати, мой индекс такой же, как вы и геопространственная конфигурация - Geography. Вы можете попробовать еще раз, и если результат будет аналогичен вашему приведенному выше, сообщите мне более подробную информацию, например sdk или детали вашего документа (я тестирую это на портале Azure).

...