LangChain4j Hibernate 集成实战:在任意 Hibernate 支持数据库中构建向量检索与 RAG

发布时间:2026/9/15 17:20:54
LangChain4j Hibernate 集成实战:在任意 Hibernate 支持数据库中构建向量检索与 RAG LangChain4j Hibernate 集成实战在任意 Hibernate 支持数据库中构建向量检索与 RAG【免费下载链接】langchain4jLangChain4j is an idiomatic, open-source Java library for building LLM-powered applications on the JVM. It offers a unified API over popular LLM providers and vector stores, and makes implementing tool calling (including MCP support), agents and RAG easy. It integrates seamlessly with enterprise Java frameworks like Quarkus and Spring Boot.项目地址: https://gitcode.com/GitHub_Trending/la/langchain4j本文是 LangChain4j Hibernate 向量存储集成langchain4j-hibernate的完整实战指南。该模块将 LangChain4j 的EmbeddingStoreAPI 与 Hibernate ORM 无缝打通使开发者可以直接在 Hibernate 支持的所有数据库PostgreSQL、MySQL、MariaDB、DB2、SQL Server、Oracle、CockroachDB、SAP HANA 等中存取与查询向量嵌入进而用于语义搜索、RAG 等场景。读完本文你将掌握两种存储构建模式动态通用存储与实体存储的全部配置参数、自定义 Hibernate 实体的注解用法、基于 PGVector 的完整 RAG 落地示例以及多数据库向量索引 DDL 与生产级调优建议。集成概览为什么选择 Hibernate 作为向量存储层LangChain4j 的 Hibernate 集成允许开发者将向量嵌入embedding直接存储并查询到 Hibernate 支持的所有数据库无需引入额外的独立向量数据库。对于已经基于 Hibernate 管理数据模型的企业级 Java 应用尤其是 Quarkus、Spring Boot 生态这意味着可以复用现有的SessionFactory、实体映射、事务与连接池设施在同一套数据基础设施中同时完成业务数据与向量数据的持久化。从仓库源码看该模块位于 langchain4j-hibernate其核心 API 只有两类HibernateEmbeddingStore实现 LangChain4j 的EmbeddingStoreTextSegment接口负责向量的增、删、查含相似度检索与元数据过滤。四个注解EmbeddingVector、EmbeddedText、UnmappedMetadata、MetadataAttribute用于在自定义实体上标注向量存储所需的字段。模块依赖方面langchain4j-hibernate/pom.xml 显示其依赖langchain4j-core、hibernate-core与hibernate-vector当前使用 Hibernate ORM 7.4.2.Final并在测试中借助 Testcontainers 覆盖 PostgreSQL/PGVector、DB2、Oracle、MariaDB、SQL Server、CockroachDB 等多种数据库集成测试类位于 langchain4j-hibernate/src/test/java/dev/langchain4j/store/embedding 下的generic与typed两个包。添加依赖在项目中引入langchain4j-hibernate以下为官方文档示例版本dependency groupIddev.langchain4j/groupId artifactIdlangchain4j-hibernate/artifactId version1.20.0-beta30/version /dependency使用 Gradle 则对应implementation dev.langchain4j:langchain4j-hibernate:1.20.0-beta30注意仓库当前源码版本为1.21.0-beta31-SNAPSHOT见 langchain4j-hibernate/pom.xml实际使用时请以你依赖的发行版本为准。该模块还需要你自行引入对应数据库的 JDBC 驱动并可选用连接池如 HikariCP以提升生产环境表现。两种构建模式Generic Store 与 Entity StoreHibernateEmbeddingStore提供了两种构建入口分别对应不同的使用诉求模式构建入口适用场景Generic Store通用存储HibernateEmbeddingStore.dynamicBuilder()/dynamicDatasourceBuilder()只关心EmbeddingStoreAPI不想操心实体类定义与 Hibernate 配置细节Entity Store实体存储HibernateEmbeddingStore.builder()希望复用已有的 Hibernate 实体模型或需要对数据模型做定制两种模式的核心差异在于表结构由谁定义Generic Store 由 store 内部动态生成 Hibernate 元模型与建表逻辑用户只需提供连接参数、表名与向量维度Entity Store 则完全基于你传入的实体类及其上的注解来映射表结构。Generic Store 参数详解Generic Store 的参数通过两种 builder 变体提供dynamicBuilder()以jdbcUrl或host/port/databaseuser/password直接描述数据库连接。dynamicDatasourceBuilder()直接注入一个现成的DataSource对象推荐用于生产环境配合连接池。完整参数如下Plain Java Property说明默认值必填/可选datasource数据库连接的DataSource对象。仅在dynamicDatasourceBuilder()变体中可用。若未提供则必须在dynamicBuilder()变体中单独提供jdbcUrl、user与password。无与jdbcUrl、user、password二选一必填jdbcUrl数据库服务器的 JDBC URL。仅在dynamicBuilder()变体中可用。若未提供DataSource或host、port、database则必填。无三选一必填host数据库服务器主机名。仅在dynamicBuilder()变体中可用。若DataSource与jdbcUrl均未提供则必填。无三选一必填port数据库服务器端口。仅在dynamicBuilder()变体中可用。若DataSource与jdbcUrl均未提供则必填。无三选一必填database要连接的数据库名。仅在dynamicBuilder()变体中可用。若DataSource与jdbcUrl均未提供则必填。无三选一必填databaseKind数据库类型。若提供了DataSource或无法从jdbcUrl推断出类型时则必填。无特定条件下必填user数据库认证用户名。仅在dynamicBuilder()变体中可用。若未提供DataSource则必填。无条件必填password数据库认证密码。仅在dynamicBuilder()变体中可用。若未提供DataSource则必填。无条件必填table存储嵌入的数据库表名。无必填dimension嵌入向量的维度须与所用嵌入模型一致。可用embeddingModel.dimension()动态设置。无必填createIndex是否自动为向量嵌入创建索引。false可选indexType数据库特定的索引类型如ivfflat、hnsw。IVFFlat 将向量划分为若干列表lists查询时只搜索与查询向量最接近的一部分列表相比 HNSW其建索引更快、内存占用更少但在查询性能速度与召回率的权衡上较低。PostgreSQL 上建议使用 IVFFlat 索引。无默认使用数据库偏好类型如 PostgreSQL 上的ivfflat可选indexOptions配置在向量索引上的选项。当createIndextrue且索引类型为ivfflat时PostgreSQL 上必须提供lists 1且取值必须大于零否则表初始化阶段会抛出异常。当createIndexfalse时该参数被忽略无需设置。无条件必填/可选createTable是否自动创建嵌入表。false可选dropTableFirst是否在重建表前先删除旧表适合测试场景。false可选distanceFunction向量搜索所用的距离函数支持范围因数据库而异COSINE、EUCLIDEAN、EUCLIDEAN_SQUARED、MANHATTAN、INNER_PRODUCT、NEGATIVE_INNER_PRODUCT、HAMMING、JACCARD。COSINE可选未设置时默认使用COSINE关于databaseKind的取值源码 DatabaseKind.java 定义了 8 种枚举常量DB2、MARIADB、MSSQL、MYSQL、POSTGRESQL、COCKROACHDB、ORACLE、HANA。当使用jdbcUrl时determineDatabaseKind(String jdbcUrl)会自动识别数据库类型当使用DataSource或实体模式时则可通过determineDatabaseKind(Dialect)从 Hibernate 方言推断推断不出时才需要手动指定。需要特别指出并非所有距离函数在所有数据库上都可用。从 DatabaseKind.java 的实现可以看出例如 MariaDB 只支持COSINE与EUCLIDEAN传入其他值会直接抛出IllegalArgumentExceptionSQL Server 不支持MANHATTAN、HAMMING、JACCARDCockroachDB 不支持MANHATTAN、HAMMING、JACCARDSAP HANA 仅支持COSINE与EUCLIDEAN。因此设置distanceFunction前务必对照所选数据库的向量能力。Entity Store 参数详解Entity Store 使用HibernateEmbeddingStore.builder()构建直接对接已有实体模型Plain Java Property说明默认值必填/可选sessionFactory包含entityClass的SessionFactory对象。无必填databaseKind数据库类型。若无法从 Hibernate ORM 方言推断出类型则必填。无条件必填entityClass用于EmbeddingStore的实体类属于上述SessionFactory。无必填embeddingAttributeName表示向量嵌入的实体属性名。若未设置将扫描实体中带有EmbeddingVector注解的属性。无可选embeddedTextAttributeName表示向量嵌入源文本的实体属性名。若未设置将扫描实体中带有EmbeddedText注解的属性。无可选unmappedMetadataAttributeName表示存储未映射元数据的 JSON 列的实体属性名。若未设置将扫描实体中带有UnmappedMetadata注解的属性。无可选metadataAttributeNames显式映射为文本元数据的实体属性名集合。若未设置将扫描实体中带有MetadataAttribute注解的属性。无可选distanceFunction向量搜索所用距离函数取值与 Generic Store 相同。COSINE可选若未设置扫描EmbeddingVector注解上的distance取值若注解上也未配置则回退到默认COSINE快速开始Docker 启动 PostgreSQL PGVector文档与源码测试均以 PostgreSQL PGVector 作为示范数据库相关集成测试见 PgVectorHibernateEmbeddingStoreIT.java 等。使用 Testcontainers 与pgvector/pgvector镜像可以快速拉起一个带向量扩展的实例。用 Docker 启动测试实例docker run --rm --name langchain4j-postgres-test-container -p 5432:5432 -e POSTGRES_USERmy_user -e POSTGRES_PASSWORDmy_password pgvector/pgvector命令参数说明docker run启动一个新容器。--rm容器停止后自动移除确保不残留数据。--name langchain4j-postgres-test-container为容器命名便于识别。-p 5432:5432将本机 5432 端口映射到容器内 5432 端口。-e POSTGRES_USERmy_user设置 PostgreSQL 用户名为my_user。-e POSTGRES_PASSWORDmy_password设置 PostgreSQL 密码为my_password。pgvector/pgvector指定 Docker 镜像已预配置 PGVector 扩展。示例一仅必填参数的最小配置HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.dynamicBuilder() .databaseKind(DatabaseKind.POSTGRESQL) // Required: The database kind .host(localhost) // Required: Host of the database server .port(5432) // Required: Port of the database server .database(postgres) // Required: Database name .user(my_user) // Required: Database user .password(my_password) // Required: Database password .table(my_embeddings) // Required: Table name to store embeddings .dimension(embeddingModel.dimension()) // Required: Dimension of embeddings .build();这段配置演示了最核心的七个必填项数据库类型、连接地址、表名与向量维度。其中dimension建议始终取自embeddingModel.dimension()确保表结构与嵌入模型严格匹配。示例二配置全部常用参数HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.dynamicBuilder() // Required parameters .databaseKind(DatabaseKind.POSTGRESQL) .host(localhost) .port(5432) .database(postgres) .user(my_user) .password(my_password) .table(my_embeddings) .dimension(embeddingModel.dimension()) // Optional parameters .createIndex(true) // Enable vector index creation .indexType(ivfflat) // Index type IVFFlat .indexOptions(lists 100) // Number of lists for IVFFlat index .createTable(true) // Automatically create the table if it doesnt exist .dropTableFirst(false) // Dont drop the table first (set to true if you want a fresh start) .distanceFunction(DistanceFunction.MANHATTEN) // Use MANHATTAN distance function for vector search .build();提示上述示例中的.distanceFunction(DistanceFunction.MANHATTEN)是官方文档中的写法。需要留意的是仓库源码 DistanceFunction.java 中实际定义的枚举名是MANHATTAN而非MANHATTEN编译时请以源码枚举名为准。该枚举同时提供了COSINE、EUCLIDEAN、EUCLIDEAN_SQUARED、INNER_PRODUCT、NEGATIVE_INNER_PRODUCT、HAMMING、JACCARD等取值。第一个示例适合快速跑通第二个示例展示了全部常用可选参数便于对索引与搜索行为做精细控制。使用完毕后记得调用close()关闭HibernateEmbeddingStore以释放底层 Hibernate 资源。自定义 Hibernate 实体用注解声明向量字段当需要定制数据模型或希望复用已有实体作为EmbeddingStore的数据源时可以使用四个注解标记实体属性EmbeddingVector标记表示嵌入向量的持久化属性。默认按 32 位浮点向量VECTOR_FLOAT32处理可通过JdbcTypeCode(SqlTypes.VECTOR_FLOAT16)等覆盖向量类型支持VECTOR_BINARY、VECTOR_INT8、VECTOR_FLOAT16、VECTOR_FLOAT32、VECTOR_FLOAT64以及稀疏向量类型注解本身带有distance属性用于声明该字段的向量搜索距离函数。EmbeddedText标记生成嵌入向量的源文本属性。UnmappedMetadata标记未映射元数据的容器属性可以是MapString, Object或String以 JSON 列存储全实体最多只能有一个该属性。MetadataAttribute标记需要显式映射为文本元数据的属性负责与TextSegment#metadata的双向同步。一个最小示例Entity public class MyEmbeddingEntity { Id UUID id; EmbeddingVector Array(length 384) // The dimension of the embedding vector based on the embedding model float[] embedding; EmbeddedText String text; UnmappedMetadata MapString, Object metadata; // Can be either a MapString, Object or a String MetadataAttribute String mimeType; // Explicitly mapped. Synchronizes TextSegment#metadata with this attribute MetadataAttribute String fileName; // Explicitly mapped. Synchronizes TextSegment#metadata with this attribute }builder 会自动扫描这些注解并推导属性名因此只需两行核心配置HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.builder() .sessionFactory(sessionFactory) // Required: The SessionFactory containing your entity class .entityClass(MyEmbeddingEntity.class) // Required: The embedding entity class .build();如果不想或无法在实体上添加注解也可以显式声明属性名HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.builder() .sessionFactory(sessionFactory) .entityClass(MyEmbeddingEntity.class) .embeddingAttributeName(embedding) .embeddedTextAttributeName(text) .unmappedMetadataAttributeName(metadata) .metadataAttributeNames(mimeType, fileName) .build();嵌套元数据关联实体的元数据映射与过滤元数据还可以嵌套在OneToOne、ManyToOne或Embedded属性中——只要这些属性同时标注MetadataAttribute或通过.点号分隔符指定显式属性路径。仓库测试中的 BookEntity.java 正是这种模式的真实用例Entity public class Book { Id private Long id; private String title; private String content; MetadataAttribute Embedded private BookDetails details new BookDetails(); MetadataAttribute ManyToOne(fetch FetchType.LAZY) private Author author; EmbeddingVector Array(length 384) private float[] embedding; UnmappedMetadata private MapString, Object metadata; } Entity public class Author { Id MetadataAttribute GeneratedValue private Long id; private String firstname; private String lastname; } Embeddable public class BookDetails { MetadataAttribute private String language; private String abstractText; }对应的属性路径为details.language与author.id可直接作为元数据键参与过滤MetadataFilterBuilder.metadataKey(details.language).isEqualTo(English)MetadataFilterBuilder.metadataKey(author.id).isEqualTo(2L)类型安全的 Hibernate Restriction 搜索除了基于Metadata的过滤HibernateEmbeddingStore还提供search重载方法允许直接使用 Hibernate ORM 类型安全的RestrictionAPI 构建查询条件HibernateEmbeddingStoreBook embeddingStore embeddingStore(); embeddingStore.search( embedding, Path.from(Book.class) .to(Book_.details) .to(BookDetails_.language) .equalTo(English));或HibernateEmbeddingStoreBook embeddingStore embeddingStore(); embeddingStore.search( embedding, Path.from(Book.class) .to(Book_.author) .to(Author_.id) .equalTo(2L));这种写法由编译期生成的元模型类如Book_、BookDetails_、Author_保证路径的类型安全字段名拼写错误会在编译阶段暴露而非运行时。源码 HibernateEmbeddingStore.java 的实现中同时支持 LangChain4j 标准的FilterIsEqualTo、IsGreaterThan、IsIn、And/Or/Not等逻辑组合与 HibernateRestriction两种过滤体系前者的过滤逻辑可在 HibernateEmbeddingStoreContractTest.java 等契约测试中看到覆盖。完整 RAG 示例Hibernate PGVector本节演示如何用 Hibernate 集成构建一套完整的检索增强生成RAG系统。RAG 系统包含两个主要阶段索引阶段离线加载文档、切分块、生成嵌入、存入 pgvector。检索阶段在线对用户查询生成嵌入、检索相似块、将上下文注入 LLM 提示词。前置条件确保已按上文 Docker 方式启动带 PGVector 的 PostgreSQL 实例。阶段一文档摄入Indexingimport dev.langchain4j.data.document.Document; import dev.langchain4j.data.document.DocumentParser; import dev.langchain4j.data.document.DocumentSplitter; import dev.langchain4j.data.document.parser.apache.pdfbox.ApachePdfBoxDocumentParser; import dev.langchain4j.data.document.splitter.DocumentSplitters; import dev.langchain4j.data.embedding.Embedding; import dev.langchain4j.data.segment.TextSegment; import dev.langchain4j.model.embedding.EmbeddingModel; import dev.langchain4j.model.embedding.onnx.allminilml6v2.AllMiniLmL6V2EmbeddingModel; import dev.langchain4j.store.embedding.EmbeddingStore; import dev.langchain4j.store.embedding.EmbeddingStoreIngestor; import static dev.langchain4j.data.document.loader.FileSystemDocumentLoader.loadDocument; // Load document (PDF, TXT, etc.) Document document loadDocument(/path/to/document.pdf, new ApachePdfBoxDocumentParser()); // Split document into smaller chunks // 300 tokens per chunk, 50 tokens overlap for context continuity DocumentSplitter splitter DocumentSplitters.recursive(300, 50); // Create embedding model (384 dimensions for AllMiniLmL6V2) EmbeddingModel embeddingModel new AllMiniLmL6V2EmbeddingModel(); // Create pgvector embedding store HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.dynamicBuilder() .databaseKind(DatabaseKind.POSTGRESQL) .host(localhost) .port(5432) .database(postgres) .user(my_user) .password(my_password) .table(document_embeddings) .dimension(embeddingModel.dimension()) // 384 for AllMiniLmL6V2 .build(); // Ingest: split document, generate embeddings, and store in pgvector EmbeddingStoreIngestor.builder() .documentSplitter(splitter) .embeddingModel(embeddingModel) .embeddingStore(embeddingStore) .build() .ingest(document); System.out.println(Document ingested successfully!);这里的EmbeddingStoreIngestor是 LangChain4j 提供的标准摄入管线自动完成切分 → 向量化 → 写入 store三步你只需要注入 splitter、embeddingModel 与 embeddingStore。示例中使用的AllMiniLmL6V2EmbeddingModel对应仓库中的 langchain4j-embeddings-all-minilm-l6-v2 模块测试中亦使用其量化版langchain4j-embeddings-all-minilm-l6-v2-q见 langchain4j-hibernate/pom.xml输出 384 维向量。阶段二查询检索Retrievalimport dev.langchain4j.data.embedding.Embedding; import dev.langchain4j.data.message.AiMessage; import dev.langchain4j.model.chat.ChatModel; import dev.langchain4j.model.openai.OpenAiChatModel; import dev.langchain4j.store.embedding.EmbeddingMatch; import java.util.List; import java.util.stream.Collectors; // Users question String question What is the refund policy?; // Generate embedding for the question Embedding questionEmbedding embeddingModel.embed(question).content(); // Search for the most similar text segments (top 3 results) EmbeddingSearchResultTextSegment result embeddingStore.search( EmbeddingSearchRequest.builder() .queryEmbedding(questionEmbedding) .maxResults(3) // Retrieve top 3 most similar chunks .build() ); // Build context from retrieved segments String context result.matches().stream() .map(match - match.embedded().text()) .collect(Collectors.joining(\n\n)); // Create prompt with retrieved context String promptWithContext String.format( Answer the question based on the following context. If the context doesnt contain relevant information, say I dont have enough information to answer. Context: %s Question: %s Answer: , context, question); // Send to LLM with context ChatModel chatModel OpenAiChatModel.builder() .apiKey(System.getenv(OPENAI_API_KEY)) .modelName(gpt-4) .build(); String answer chatModel.generate(promptWithContext); System.out.println(Answer: answer);检索阶段的关键点先用与索引阶段同一个EmbeddingModel对查询向量化再调用embeddingStore.search()拿到按相似度排序的前 N 个匹配EmbeddingMatch中可通过score()观察相似度分值将匹配块的文本拼接为上下文最后连同用户问题一起交给大模型生成答案。EmbeddingSearchRequest还支持minScore、filter元数据过滤等参数用于进一步收紧召回结果。生产环境实践建议基于真实使用经验以下是生产部署时的重要考量。1. 连接池生产环境应使用带连接池的DataSource而非零散的单连接参数。这里用 HikariCP 示范其配置类来自第三方库com.zaxxer.hikari需自行引入依赖import com.zaxxer.hikari.HikariConfig; import com.zaxxer.hikari.HikariDataSource; HikariConfig config new HikariConfig(); config.setJdbcUrl(jdbc:postgresql://localhost:5432/postgres); config.setUsername(my_user); config.setPassword(my_password); config.setMaximumPoolSize(10); HikariDataSource dataSource new HikariDataSource(config); EmbeddingStoreTextSegment embeddingStore HibernateEmbeddingStore.dynamicDatasourceBuilder() .databaseKind(DatabaseKind.POSTGRESQL) .datasource(dataSource) .table(document_embeddings) .dimension(384) .build();注意此处dimension直接写死为 384对应示例嵌入模型实际项目中仍推荐用embeddingModel.dimension()动态获取。2. 索引优化对于大数据集超过 10 万条嵌入建议在 PostgreSQL 上开启 IVFFlat 索引以提升查询性能HibernateEmbeddingStore embeddingStore HibernateEmbeddingStore.dynamicBuilder() // ... other config ... .createIndex(true) .indexOptions(lists 100) // Adjust based on dataset size .build();注意在大数据集上创建索引可能耗时较长需要在查询速度与索引构建时间之间做权衡。注意索引维护会拖慢数据摄入批量导入大数据量时可考虑先删索引、导入完成后再重建。3. 分块大小调优根据业务场景实验不同分块大小较小的块200300 tokens精度更高答案更聚焦、更具体。较大的块500800 tokens上下文更丰富但可能降低相关性。4. 错误处理始终优雅地处理数据库连接失败try { embeddingStore.add(embedding, textSegment); } catch (Exception e) { logger.error(Failed to store embedding, e); // Implement retry logic or fallback behavior }5. 自定义实体时的 DDL 管理使用自定义 Hibernate 实体时DDL 需要你自行负责。建议创建import.sql来建索引。例如 PostgreSQLcreate index if not exists my_entity_ivfflat_index on my_entity using ivfflat(embedding vector_cosine_ops) with (lists 1);关于SessionFactory的详细配置可参考 Hibernate ORM 官方用户指南此处不做外部链接展开。向量索引在其他数据库上的语法与选项各不相同需查阅对应数据库提供方的文档。各数据库向量索引 DDL 速查DatabaseKind源码为每种数据库内置了索引 DDL 生成逻辑createIndexDDL方法同时官方文档也给出了手工建索引的参考 SQL两者可互为印证。下面按数据库汇总DB2create vector index my_entity_vector_index on my_entity(embedding) with distance cosine;从 DatabaseKind.java 可见DB2 支持的 distance 值包括cosine、euclidean、euclidean_squared、manhattan、hamming、jaccard与dot对应内积类距离函数。MariaDBcreate vector index if not exists my_entity_vector_index on my_entity(embedding) distancecosine;MariaDB 仅支持cosine与euclidean两种距离度量见 DatabaseKind.java使用其他距离函数会在运行时抛出IllegalArgumentException。MySQLMySQL HeatWave 会自动创建索引无需手工建索引对应源码中 MySQL 的createIndexDDL直接返回null见 DatabaseKind.java。PostgreSQLcreate index if not exists my_entity_ivfflat_index on my_entity using ivfflat(embedding vector_cosine_ops) with (lists 1);PostgreSQL 的vectorOps与距离函数映射关系来自 DatabaseKind.javaCOSINE → vector_cosine_ops、EUCLIDEAN/EUCLIDEAN_SQUARED → vector_l2_ops、MANHATTAN → vector_l1_ops、HAMMING → vector_hamming_ops、JACCARD → vector_jaccard_ops、INNER_PRODUCT/NEGATIVE_INNER_PRODUCT → vector_ip_ops。未指定indexType时默认使用ivfflat并且会在建索引前执行create extension if not exists vector;的初始化 SQL。CockroachDBcreate vector index if not exists my_entity_ivfflat_index on my_entity (embedding vector_cosine_ops);CockroachDB 的 JDBC URL 与 PostgreSQL 相同但建索引语法独立且初始化时会执行set cluster setting feature.vector_index.enabled true;见 DatabaseKind.java只支持vector_cosine_ops、vector_l2_ops、vector_ip_ops。Oraclecreate vector index my_entity_vector_index on my_entity(embedding) organization neighbor partitions with distance cosine;Oracle 支持的 distance 值最全cosine、euclidean、euclidean_squared、manhattan、hamming、jaccard、dot见 DatabaseKind.java。SQL Servercreate vector index my_entity_vector_index on my_entity(embedding) with (metriccosine);SQL Server 的 metric 支持cosine、euclidean、dot三种取值JDBC URL 模板中还内置了sendTimeAsDatetimefalse与trustServerCertificatetrue等连接参数见 DatabaseKind.java。SAP HANAcreate hnsw vector index my_entity_vector_index on my_entity(embedding) with similarity function cosine_similarity;SAP HANA 使用 HNSW 索引支持cosine_similarity与l2distance两种相似度函数见 DatabaseKind.java。源码原理深挖索引 DDL 与距离函数的自动生成理解HibernateEmbeddingStore底层行为有助于在生产中做出正确配置决策。从源码 DatabaseKind.java 可以看出每种数据库类型封装了四类信息JDBC URL 模板如 PostgreSQL 的jdbc:postgresql://{host}:{port}/{database}、SQL Server 的jdbc:sqlserver://{host}:{port};databaseName{database};...dynamicBuilder()会据此拼接完整连接串。索引 DDL 生成函数createIndexDDL(distanceFunction, indexType, table, embeddingColumn, indexOptions)按距离函数把索引操作符/度量映射为各数据库的建索引语句——这就是createIndextrue时自动建索引的实现基础。初始化 SQL如 PostgreSQL 的create extension if not exists vector;、CockroachDB 的集群设置开关在建表建索引前自动执行。数据库识别逻辑isJdbcUrl()用于从 JDBC URL 推断类型determineDatabaseKind(Dialect)用于从 Hibernate 方言推断类型。而距离函数枚举 DistanceFunction.java 统一定义了 8 种语义COSINE、EUCLIDEAN、EUCLIDEAN_SQUARED、MANHATTAN、INNER_PRODUCT、NEGATIVE_INNER_PRODUCT、HAMMING、JACCARD再由各数据库的 DDL 生成逻辑做语义 → 方言的翻译不支持某距离函数的数据库会在构建索引或初始化时直接抛出IllegalArgumentException因此建议在项目早期就锁定所用数据库与距离函数组合。注解层方面EmbeddingVector.java、EmbeddedText.java、UnmappedMetadata.java 分别通过JdbcTypeCode将字段映射为 Hibernate 的VECTOR、LONG32VARCHAR长文本与JSON列类型这也是一个实体即可同时承载向量、文本与元数据的技术基础。仓库中 PgVectorHibernateEmbeddingStoreBookEntityIT.java 等集成测试对嵌套元数据、JSONB 过滤、float16 向量、元数据重置等场景均有覆盖可作为理解行为边界的参考。【免费下载链接】langchain4jLangChain4j is an idiomatic, open-source Java library for building LLM-powered applications on the JVM. It offers a unified API over popular LLM providers and vector stores, and makes implementing tool calling (including MCP support), agents and RAG easy. It integrates seamlessly with enterprise Java frameworks like Quarkus and Spring Boot.项目地址: https://gitcode.com/GitHub_Trending/la/langchain4j创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

关于本文作者

来自尧图内容编辑团队

尧图内容编辑团队 内容团队

尧图内容编辑团队

本文由尧图网络内容编辑团队执笔。团队由资深项目经理、前端工程师与设计师组成,所有内容均来自亲手交付的真实项目,先讲清问题、再给出可落地的解法。尧图深耕北京网站建设十年,服务过京华建材集团、智造科技等各行业客户,把一线经验沉淀为可复用的行业观察。

  • 十年建站经验,覆盖建材、制造、服务、文创等
  • 项目经理把关选题与事实准确性
  • 工程师与设计师联合撰写专业细节
  • 统一编辑规范,保证文风与排版一致
  • 每月复盘转化数据,迭代选题方向

延伸阅读

相关资讯与近期热门内容

深度阅读推荐

建站决策前值得细读的三篇

网站改版的5个关键决策
2024-08-12

网站改版的5个关键决策

什么时候该改版、改到什么程度、如何避免流量掉光,京华建材集团改版复盘给出答案。

获取专属建站方案

看完文章,把您的行业与预算告诉我们,免费获取一份量身定制的官网建设方案与报价。

立即免费咨询