Векторы индексов и запросов в Azure Cosmos DB для NoSQL в Java
ОБЛАСТЬ ПРИМЕНЕНИЯ: NoSQL
Векторный поиск в Azure Cosmos DB для NoSQL в настоящее время является функцией предварительной версии. Перед использованием необходимо зарегистрировать предварительный просмотр. В этой статье рассматриваются следующие задачи:
- Регистрация для предварительной версии векторного поиска в Azure Cosmos DB для NoSQL
- Настройка контейнера Azure Cosmos DB для поиска векторов
- Разработка векторной политики внедрения
- Добавление векторных индексов в политику индексирования контейнеров
- Создание контейнера с векторными индексами и политикой внедрения векторов
- Выполнение векторного поиска по сохраненным данным.
- В этом руководстве описывается процесс создания векторных данных, индексирования данных и последующего запроса данных в контейнере.
Необходимые компоненты
- Существующая учетная запись Azure Cosmos DB для NoSQL.
- Если у вас нет подписки Azure, попробуйте использовать Azure Cosmos DB для NoSQL бесплатно.
- Если у вас есть подписка Azure, создайте новую учетную запись Azure Cosmos DB для NoSQL.
- Последняя версия пакета SDK java для Azure Cosmos DB.
Регистрация для предварительной версии
Для поиска векторов для Azure Cosmos DB для NoSQL требуется предварительная версия функции. Выполните следующие действия, чтобы зарегистрировать:
Перейдите на страницу ресурсов Azure Cosmos DB для NoSQL.
В меню "Параметры" выберите область "Компоненты".
Выберите "Векторный поиск в Azure Cosmos DB для NoSQL".
Ознакомьтесь с описанием функции, чтобы подтвердить, что вы хотите зарегистрировать в предварительной версии.
Нажмите кнопку "Включить", чтобы зарегистрировать в предварительной версии.
Примечание.
Запрос на регистрацию будет автоматически утвержден, однако может потребоваться несколько минут для принятия в силу.
Общие сведения о шагах, связанных с векторным поиском
В следующих шагах предполагается, что вы знаете, как настроить учетную запись NoSQL Cosmos DB и создать базу данных. Функция поиска векторов в настоящее время не поддерживается в существующих контейнерах, поэтому необходимо создать новый контейнер и указать политику внедрения вектора на уровне контейнера и политику индексирования векторов во время создания контейнера.
Давайте рассмотрим пример создания базы данных для интернет-магазина книг, и вы храните название, автор, ISBN и описание каждой книги. Мы также определяем два свойства, которые содержат векторные внедрения. Первым является свойство contentVector, которое содержит вставки текста, созданные из текстового содержимого книги (например, объединение свойств "author" "isbn" и "description" перед созданием внедрения). Второй — "coverImageVector", который создается на основе изображений обложки книги.
- Создайте и сохраните векторные внедрения для полей, в которых требуется выполнить поиск векторов.
- Укажите пути внедрения вектора в политику внедрения вектора.
- Включите все нужные векторные индексы в политику индексирования для контейнера.
В последующих разделах этой статьи мы рассмотрим приведенную ниже структуру для элементов, хранящихся в нашем контейнере:
{
"title": "book-title",
"author": "book-author",
"isbn": "book-isbn",
"description": "book-description",
"contentVector": [2, -1, 4, 3, 5, -2, 5, -7, 3, 1],
"coverImageVector": [0.33, -0.52, 0.45, -0.67, 0.89, -0.34, 0.86, -0.78]
}
Сначала создайте CosmosContainerProperties
объект.
CosmosContainerProperties collectionDefinition = new CosmosContainerProperties(UUID.randomUUID().toString(), "Partition_Key_Def");
Создание векторной политики внедрения для контейнера.
Затем необходимо определить политику вектора контейнера. Эта политика предоставляет сведения, используемые для информирования обработчика запросов Azure Cosmos DB о том, как обрабатывать свойства векторов в системных функциях VectorDistance. Это также сообщает политике индексирования векторов необходимых сведений, следует указать его. Следующие сведения включаются в содержащуюся векторную политику:
- "path": путь свойства, содержащий векторы
- "datatype": тип элементов вектора (по умолчанию Float32)
- "измерения": длина каждого вектора в пути (по умолчанию 1536)
- "distanceFunction": метрика, используемая для вычисления расстояния или сходства (по умолчанию Cosine)
В нашем примере с сведениями о книге векторная политика может выглядеть как пример JSON:
// Creating vector embedding policy
CosmosVectorEmbeddingPolicy cosmosVectorEmbeddingPolicy = new CosmosVectorEmbeddingPolicy();
CosmosVectorEmbedding embedding1 = new CosmosVectorEmbedding();
embedding1.setPath("/coverImageVector");
embedding1.setDataType(CosmosVectorDataType.FLOAT32);
embedding1.setDimensions(8L);
embedding1.setDistanceFunction(CosmosVectorDistanceFunction.COSINE);
CosmosVectorEmbedding embedding2 = new CosmosVectorEmbedding();
embedding2.setPath("/contentVector");
embedding2.setDataType(CosmosVectorDataType.FLOAT32);
embedding2.setDimensions(10L);
embedding2.setDistanceFunction(CosmosVectorDistanceFunction.DOT_PRODUCT);
cosmosVectorEmbeddingPolicy.setCosmosVectorEmbeddings(Arrays.asList(embedding1, embedding2, embedding3));
collectionDefinition.setVectorEmbeddingPolicy(cosmosVectorEmbeddingPolicy);
Создание векторного индекса в политике индексирования
После решения путей внедрения векторов необходимо добавить в политику индексирования векторные индексы. В настоящее время функция поиска векторов для Azure Cosmos DB для NoSQL поддерживается только в новых контейнерах, поэтому необходимо применить политику вектора во время создания контейнера и ее нельзя изменить позже. В этом примере политика индексирования будет выглядеть примерно так:
IndexingPolicy indexingPolicy = new IndexingPolicy();
indexingPolicy.setIndexingMode(IndexingMode.CONSISTENT);
ExcludedPath excludedPath1 = new ExcludedPath("/coverImageVector/*");
ExcludedPath excludedPath2 = new ExcludedPath("/contentVector/*");
indexingPolicy.setExcludedPaths(ImmutableList.of(excludedPath1, excludedPath2));
IncludedPath includedPath1 = new IncludedPath("/*");
indexingPolicy.setIncludedPaths(Collections.singletonList(includedPath1));
// Creating vector indexes
CosmosVectorIndexSpec cosmosVectorIndexSpec1 = new CosmosVectorIndexSpec();
cosmosVectorIndexSpec1.setPath("/coverImageVector");
cosmosVectorIndexSpec1.setType(CosmosVectorIndexType.QUANTIZED_FLAT.toString());
CosmosVectorIndexSpec cosmosVectorIndexSpec2 = new CosmosVectorIndexSpec();
cosmosVectorIndexSpec2.setPath("/contentVector");
cosmosVectorIndexSpec2.setType(CosmosVectorIndexType.DISK_ANN.toString());
indexingPolicy.setVectorIndexes(Arrays.asList(cosmosVectorIndexSpec1, cosmosVectorIndexSpec2, cosmosVectorIndexSpec3));
collectionDefinition.setIndexingPolicy(indexingPolicy);
Наконец, создайте контейнер с политикой индекса контейнера и политикой векторного индекса.
database.createContainer(collectionDefinition).block();
Внимание
Векторный путь, добавленный в раздел "исключенныеPaths" политики индексирования, чтобы обеспечить оптимизированную производительность для вставки. Не добавляя векторный путь к "исключеннымPaths", будет взиматься более высокая плата за единицу запросов и задержку для вставок векторов.
Внимание
В настоящее время поиск векторов в Azure Cosmos DB для NoSQL поддерживается только в новых контейнерах. Необходимо задать как политику вектора контейнера, так и любую политику индексирования векторов во время создания контейнера, так как ее нельзя изменить позже. Обе политики будут изменяться в будущем улучшении функции предварительной версии.
Выполнение запроса поиска сходства векторов
Создав контейнер с требуемой политикой векторов и вставив в контейнер векторные данные, можно выполнить векторный поиск с помощью функции системы "Вектор расстояние " в запросе. Предположим, что вы хотите искать книги о рецептах продуктов питания, глядя на описание, сначала необходимо получить внедрения текста запроса. В этом случае может потребоваться создать внедрения для текста запроса — "рецепт еды". После внедрения поискового запроса его можно использовать в функции VectorDistance в векторном поисковом запросе и получить все элементы, похожие на запрос, как показано здесь:
SELECT TOP 10 c.title, VectorDistance(c.contentVector, [1,2,3,4,5,6,7,8,9,10]) AS SimilarityScore
FROM c
ORDER BY VectorDistance(c.contentVector, [1,2,3,4,5,6,7,8,9,10])
Этот запрос извлекает названия книги, а также оценки сходства в отношении запроса. Ниже приведен пример в Java:
float[] embedding = new float[10];
for (int i = 0; i < 10; i++) {
array[i] = i + 1;
}
ArrayList<SqlParameter> paramList = new ArrayList<SqlParameter>();
paramList.add(new SqlParameter("@embedding", embedding));
SqlQuerySpec querySpec = new SqlQuerySpec("SELECT c.title, VectorDistance(c.contentVector,@embedding) AS SimilarityScore FROM c ORDER BY VectorDistance(c.contentVector,@embedding)", paramList);
CosmosPagedIterable<Family> filteredFamilies = container.queryItems(querySpec, new CosmosQueryRequestOptions(), Family.class);
if (filteredFamilies.iterator().hasNext()) {
Family family = filteredFamilies.iterator().next();
logger.info(String.format("First query result: Family with (/id, partition key) = (%s,%s)",family.getId(),family.getLastName()));
}