这是最简、可直接运行的 Java 版 Milvus 入门教程,适配 Milvus 2.4+,包含:连接、建集合、建索引、插入数据、向量检索全套流程。
一、环境准备
-
先启动 Milvus 服务(推荐 Docker 单机版)
bashwget https://github.com/milvus-io/milvus/releases/download/v2.4.10/milvus-standalone-docker-compose.yml -O docker-compose.yml docker-compose up -d -
Java 环境:JDK 21
-
Maven 引入依赖
二、Maven 依赖
直接复制到 pom.xml:
xml
<dependencies>
<!-- Milvus Java SDK -->
<dependency>
<groupId>io.milvus</groupId>
<artifactId>milvus-sdk-java</artifactId>
<version>2.4.10</version>
</dependency>
<!-- 工具类 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>2.0.32</version>
</dependency>
</dependencies>
三、完整可运行代码
核心流程
- 连接 Milvus
- 创建集合(表)
- 创建索引(必须建索引才能检索)
- 插入向量数据
- 加载集合到内存
- 向量相似检索
java
import io.milvus.client.MilvusClient;
import io.milvus.client.MilvusServiceClient;
import io.milvus.common.clientenum.ConsistencyLevelEnum;
import io.milvus.grpc.DataType;
import io.milvus.grpc.SearchResults;
import io.milvus.param.ConnectParam;
import io.milvus.param.IndexType;
import io.milvus.param.MetricType;
import io.milvus.param.collection.*;
import io.milvus.param.dml.InsertParam;
import io.milvus.param.dml.SearchParam;
import io.milvus.param.index.CreateIndexParam;
import io.milvus.response.SearchResultsWrapper;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Random;
public class MilvusJavaQuickStart {
// 配置
private static final String HOST = "localhost";
private static final int PORT = 19530;
private static final String COLLECTION_NAME = "java_demo_collection";
private static final int VECTOR_DIM = 128; // 向量维度
public static void main(String[] args) {
// 1. 连接 Milvus
MilvusClient client = new MilvusServiceClient(
ConnectParam.newBuilder()
.withHost(HOST)
.withPort(PORT)
.build()
);
System.out.println("✅ Milvus 连接成功");
try {
// 2. 创建集合
createCollection(client);
// 3. 创建索引
createIndex(client);
// 4. 插入数据
insertData(client);
// 5. 加载集合到内存(检索前必须执行)
loadCollection(client);
// 6. 向量检索
searchVector(client);
System.out.println("\n🎉 全部执行完成!");
} catch (Exception e) {
e.printStackTrace();
} finally {
client.close();
}
}
// 创建集合(表)
private static void createCollection(MilvusClient client) {
// 先判断是否存在,存在则删除
HasCollectionParam hasCollectionParam = HasCollectionParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.build();
if (client.hasCollection(hasCollectionParam).getData()) {
DropCollectionParam dropParam = DropCollectionParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.build();
client.dropCollection(dropParam);
}
// 定义字段:ID + 向量 + 文本
List<FieldType> fields = new ArrayList<>();
// 主键ID
fields.add(FieldType.newBuilder()
.withName("id")
.withDataType(DataType.Int64)
.withPrimaryKey(true)
.withAutoID(true) // 自动生成ID
.build());
// 向量字段
fields.add(FieldType.newBuilder()
.withName("embedding")
.withDataType(DataType.FloatVector)
.withDimension(VECTOR_DIM)
.build());
// 文本元数据
fields.add(FieldType.newBuilder()
.withName("text")
.withDataType(DataType.VarChar)
.withMaxLength(64)
.build());
// 创建集合
CreateCollectionParam createParam = CreateCollectionParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.withFieldTypes(fields)
.withConsistencyLevel(ConsistencyLevelEnum.STRONG)
.build();
client.createCollection(createParam);
System.out.println("✅ 集合创建成功");
}
// 创建索引(必须建索引才能检索)
private static void createIndex(MilvusClient client) {
CreateIndexParam indexParam = CreateIndexParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.withFieldName("embedding")
.withIndexType(IndexType.HNSW) // 索引类型:HNSW(高性能)
.withMetricType(MetricType.L2) // 距离算法:欧氏距离
.withExtraParam("{\"M\":16,\"efConstruction\":200}")
.build();
client.createIndex(indexParam);
System.out.println("✅ 索引创建成功");
}
// 插入测试数据
private static void insertData(MilvusClient client) {
List<InsertParam.Field> fields = new ArrayList<>();
// 生成 10 条随机向量 + 文本
List<List<Float>> vectors = new ArrayList<>();
List<String> texts = new ArrayList<>();
Random random = new Random();
for (int i = 0; i < 10; i++) {
// 生成 128 维随机向量
List<Float> vec = new ArrayList<>();
for (int j = 0; j < VECTOR_DIM; j++) {
vec.add(random.nextFloat());
}
vectors.add(vec);
texts.add("Java测试文本_" + i);
}
fields.add(new InsertParam.Field("embedding", vectors));
fields.add(new InsertParam.Field("text", texts));
// 插入
InsertParam insertParam = InsertParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.withFields(fields)
.build();
client.insert(insertParam);
System.out.println("✅ 数据插入成功:10 条");
}
// 加载集合(检索前必须执行)
private static void loadCollection(MilvusClient client) {
LoadCollectionParam loadParam = LoadCollectionParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.build();
client.loadCollection(loadParam);
// 等待加载完成
try { Thread.sleep(1000); } catch (InterruptedException e) {}
System.out.println("✅ 集合已加载到内存");
}
// 向量相似检索
private static void searchVector(MilvusClient client) throws Exception {
// 生成随机查询向量
List<Float> queryVector = new ArrayList<>();
Random random = new Random();
for (int i = 0; i < VECTOR_DIM; i++) {
queryVector.add(random.nextFloat());
}
// 检索参数
SearchParam searchParam = SearchParam.newBuilder()
.withCollectionName(COLLECTION_NAME)
.withMetricType(MetricType.L2)
.withTopK(3) // 返回最相似的 3 条
.withVectors(Arrays.asList(queryVector))
.withVectorFieldName("embedding")
.withOutFields(Arrays.asList("text")) // 返回文本字段
.withParams("{\"ef\":50}")
.build();
// 执行检索
SearchResults response = client.search(searchParam);
SearchResultsWrapper wrapper = new SearchResultsWrapper(response.getResults());
System.out.println("\n🔍 检索结果(Top3):");
List<SearchResultsWrapper.IDScore> scores = wrapper.getIDScore(0);
for (SearchResultsWrapper.IDScore score : scores) {
System.out.println("ID:" + score.getLongID()
+ " | 相似度距离:" + String.format("%.4f", score.getScore())
+ " | 文本:" + score.getFieldValue("text"));
}
}
}
四、运行说明
- 确保 Milvus 服务正常运行
- 直接运行
main方法 - 控制台输出:连接成功 → 建集合 → 建索引 → 插入数据 → 检索结果
五、核心概念速查
| 概念 | 说明 |
|---|---|
| 集合(Collection) | 相当于数据库的表 |
| 字段(Field) | 表的列,支持向量/数字/字符串 |
| 索引(Index) | 向量必须建索引才能快速检索 |
| HNSW | 最常用索引类型,查询速度快、耗内存 |
| L2 | 欧氏距离,最通用的向量相似度算法 |
| 加载集合 | 检索前必须加载到内存 |
六、常用扩展
- 真实向量:把随机向量替换成文本嵌入模型(如 Sentence-BERT)输出的向量
- 过滤检索 :增加
withExpr("text like '%Java%'")实现条件检索 - 删除数据 :使用
DeleteParam按 ID/条件删除 - 可视化工具 :Attu(
docker run -p 8000:3000 zilliz/attu)
总结
- 这套代码是 Java 操作 Milvus 最简标准模板,可直接用于项目
- 必须流程:建集合 → 建索引 → 插入 → 加载 → 检索