使用 Vertex AI 执行向量相似度搜索

欢迎使用 Firebase Data Connect 的向量相似性搜索 - Firebase 的 语义搜索的实现,集成了 Google Vertex AI

此功能的核心是向量嵌入,即 用于表示文本或媒体语义含义的点数。通过使用输入向量嵌入运行最近邻搜索,您可以找到所有语义相似的内容。Data Connect 使用 PostgreSQL 的 此功能的 pgvector 扩展。

这种强大的语义搜索功能可支持推荐引擎和搜索引擎等应用场景。它也是生成式 AI 流程中检索增强生成的关键组成部分。Vertex AI 文档是您了解 了解详情

您可以依靠 Data Connect 的内置支持来生成矢量 使用 Vertex AI 的 Embeddings API 自动进行嵌入, 或者使用该 API 手动生成它们。

前提条件

  • 为您的项目设置 Data Connect

  • 启用 Vertex AI API

设置

您可以选择本地开发流程(如果您是 Web、Kotlin Android 或 iOS 开发者)或 IDX 流程(适用于 Web 开发者)。您可以使用 本地数据库或 Data Connect 生产项目及其 用于开发用途的 Cloud SQL for PostgreSQL 实例。

以下说明假定您已创建 Data Connect 项目 按照快速入门指南操作

与本地 PostgreSQL 集成

  1. 设置本地 PostgreSQL 实例。
  2. 为您自己授予 Vertex AI user IAM 角色
  3. 在您的环境中设置 Google Cloud 应用默认凭据
  4. 在本地 PostgreSQL 实例中安装 pgvector 扩展程序
  5. 按照 pgvector 代码库中的说明,使用 CREATE EXTENSION vector 启用该扩展程序。

与 IDX 集成

  1. 使用 Data Connect 模板设置您的 IDX 工作区。
  2. 为自己授予 Vertex AI User IAM 角色
  3. 按照 pgvector 代码库中的说明,使用 CREATE EXTENSION vector 启用该扩展程序。

设计架构

如需执行矢量搜索,请在架构中添加一个 Vector 类型的新字段。例如,如果您想使用电影说明进行语义搜索,请添加一个字段来存储与电影说明关联的矢量嵌入。在 此架构添加了 descriptionEmbedding 以存储以下项的向量嵌入: description 字段中的值。

type Movie @table {
 id: ID! @col(name: "movie_id") @default(id: ID! @col(name: "movie_id") @default(expr: "uuidV4()")
 title: String!
 description: String
 descriptionEmbedding: Vector! @col(size:768)
 // ...
}

生成和检索嵌入

Data Connect 提供对矢量嵌入的集成支持, _embed 服务器值。这会指示 Data Connect 生成 向量嵌入,方法是在内部调用 Vertex AI 的 Embedding API。_embed 服务器值可用于变更和查询。

变更

通过 Data Connect 生成并存储嵌入

在您的矢量搜索应用中,您可能需要请求将嵌入 系统会在您将记录添加到数据库后立即生成以下是createMovie 变更会将影片记录添加到 Movie 表,并传递影片 具有指定嵌入 model 的说明。

mutation createMovie($movieData: Movie_Data! @pick(fields: ["title", "genre", "description"])) {
  movie_insert(data: {
    ...movieData,
    descriptionEmbedding_embed: {model: "textembedding-gecko@003", text: $movieData.description}
  })
}

在某些情况下,您可能需要更新电影说明和嵌入内容。

mutation updateDescription($id: String!, $description: String!) {
  movie_update(id: $id, data: {
    description: $description,
    descriptionEmbedding_embed: {model: "textembedding-gecko@003", text: $description}
  })
}

如需从客户端调用后一种变更,请执行以下操作:

import { updateMovieDescriptionWithEmbed } from 'lib/dataconnect-sdk/';

await updateMovieDescriptionWithEmbed({ id: movieId, description: description});

// Use the response

查询

使用如下所示的查询提取向量嵌入。请注意,查询返回的 descriptionEmbedding 是一个浮点数数组,通常不可读。因此,Data Connect 生成的 SDK 不支持直接返回它。

您可以使用返回的向量嵌入进行相似度搜索,如下一部分所述。

query getMovieDescription($id: String!) @auth(is: PUBLIC) {
 movie(id: $id)
   id
   description
   descriptionEmbedding
}

执行相似度搜索

现在,我们可以执行相似搜索了。

对于每个 Vector 字段,Data Connect 会生成一个 GraphQL 函数 实现了相似性搜索。生成的函数的名称为 ${pluralType}_${vectorFieldName}_similarity。它支持一些参数 如以下示例和参考列表中所示。

您可以定义用于调用相似性搜索的 GraphQL 函数。如 如上所述,_embed 服务器值会将 Data Connect 定向到 使用 Vertex AI 的 Embedding API 生成矢量嵌入,在本示例中, 为用于与电影进行比较的搜索字符串创建嵌入 描述嵌入。

在本示例中,相似度搜索最多会返回 5 部电影。 description 在语义上与输入查询最接近。对结果集进行排序 按距离的升序排列(最接近最远)。

query searchMovieDescriptionUsingL2Similarity ($query: String!) @auth(level: PUBLIC) {
    movies_descriptionEmbedding_similarity(
      compare_embed: {model: "textembedding-gecko@003", text: $query},
      method: L2,
      within: 2,
      where: {content: {ne: "No info available for this movie."}}, limit: 5)
      {
        id
        title
        description
      }
  }

调用相似度查询

如需从客户端代码调用相似度搜索,请执行以下操作:

import { searchMovieDescriptionUsingL2similarity} from 'lib/dataconnect-sdk';

const response = await searchMovieDescriptionUsingL2similarity({ query });

// Use the response

使用自定义嵌入

借助 Data Connect,您还可以直接将嵌入作为 Vector 进行处理,而无需使用 _embed 服务器值来生成嵌入。

存储自定义嵌入

使用 Vertex Embeddings API,指定匹配的模型并请求 正确维度的嵌入结果。

然后,将返回的浮点数数组转换为 Vector 以传递给更新。 存储操作

mutation updateDescription($id: String!, $description: String!, $descriptionEmbedding: Vector!) {
  movie_update(id: $id, data: {
    // title, genre...
    description: $description,
    descriptionEmbedding: $descriptionEmbedding
  })
}

使用自定义嵌入执行相似度搜索

执行相同的操作以检索搜索字词的嵌入,并将其转换为 Vectors

然后,调用 _similarity 查询来执行每次搜索。

query searchMovieDescriptionUsingL2Similarity($compare: Vector!, $within: Float, $excludesContent: String, $limit: Int) @auth(level: PUBLIC) {
    movies_descriptionEmbedding_similarity(
      compare: $compare,
      method: L2,
      within: $within,
      where: {content: {ne: $excludesContent}}, limit: $limit)
      {
        id
        title
        description
      }
  }

部署到生产环境

部署架构和连接器

典型 Data Connect 迭代的最后一步是部署您的 将资源部署到生产环境中。

使用 firebase deploy 命令将包含 Vector 类型的架构部署到 CloudSQL 时,Firebase CLI 会执行必要的步骤,以便在 CloudSQL 实例上启用基于 Vertex AI 的嵌入生成。

firebase deploy --only dataconnect

如果您想在 CloudSQL 实例中手动启用嵌入支持,或者遇到 CLI 错误,请按照这些说明操作。

矢量搜索语法

架构扩展

Data ConnectVector 数据类型映射到 PostgreSQL 的 vector 类型 (由 pgvector 扩展程序定义)。 pgvector 的 vector 类型存储为单精度浮点数的数组。 。

Data Connect 中,Vector 类型表示为 JSON 数字数组。输入会强制转换为 float32 值数组。如果强制转换失败,则会引发错误。

使用 @col 指令的 size 参数设置 矢量。

type Question @table {
    text: String!
    category: String!
    textEmbedding: Vector! @col(size: 768)
}

Vector 类型支持 sizeVector 运算(例如相似搜索)需要所有 Vector 具有相同的维数。

directive @col(
  # … existing args
  """
  Defines a fixed column size for certain scalar types.

  - For Vector, size is required.
  - For all other types, size is currently unsupported and hence supplying it will result in a schema error.
  """
  size: Int
) on FIELD_DEFINITION

适用于查询和更改的 _embed 服务器值

_embed

此服务器值会引导 Data Connect 服务生成 并使用 Vertex AI 的 Embedding API 存储嵌入。 此服务器值可用于查询和更改。

用于相似性搜索的参数

method: COSINE|INNER_PRODUCT|L2

用于搜索附近邻居的距离函数。目前支持的算法是 pgvector 搜索算法的子集。

within: float

对最近邻搜索范围的限制 错误。

where: FDC filter condition

请参阅架构、查询和变更指南

limit: int

要返回的结果数。