前言
嗨,大家好,我是雪荷,最近在公司開發 AI 知識庫,同時學到了一些 AI 開發相關的技術,這期先與大家分享一下如何用 ES 當做向量數據庫。
安裝ES
第一步我們先安裝 Elasticsearch,這里建議 Elasticsearch 一定要在 8.13.x 以上,這里我選用的版本為 8.14.3。
下載 Docker Desktop
我使用 Docker 部署的 ES,所以需要先安裝 Docker Desktop,大家根據自己的系統下載。
Mac 安裝 Docker Desktop:Docker—蘋果Mac安裝Docker的兩種方式-CSDN博客
Windows 安裝 Docker Desktop:https://zhuanlan.zhihu.com/p/441965046
啟動 ES
打開命令行直接一條命令梭哈,ES 自從 8.0 版本就默認開啟安全認證了,這里我設置了關閉。
docker run -d \--name elasticsearch \-p 9200:9200 -p 9300:9300 \-e "discovery.type=single-node" \-e "xpack.security.enabled=false" \-e "xpack.security.http.ssl.enabled=false" \elasticsearch:8.14.3
訪問 http://localhost:9200,出現以下界面代表 ES 啟動成功。
部署本地大模型
前往 ollama 官網下載大模型本地部署工具,依舊根據自己系統進行選擇。
下載完畢通過命令行下載大模型,大家可以根據電腦配置和需求下載不同的模型和模型參數,qwen、deepseek 都是可以的,我這里就是 8b 的 deepseek-r1
ollama run deepseek-r1:8b
然后還要部署一個文本嵌入模型,主要將文本轉為向量化,這個模型僅 pull 就好,因為不是文本生成模型 run 不了。
ollama pull mxbai-embed-large:latest
搭建 Spring Boot 項目
搭建 Spring Boot 就不用我教了吧,相信各位佐助都會,建議 Spring Boot 版本要在 3.3.x 以上,我的為 3.5.3。
引入依賴
添加配置類
ES 配置類,主要配置 ES 連接地址、端口和向量數據的相關參數。
@Configuration
public class EsRagConfig {@Beanpublic RestClient restClient() {return RestClient.builder(new HttpHost("localhost", 9200, "http")) // 配置 ES 地址和端口.build();}@Beanpublic VectorStore vectorStore(RestClient restClient, EmbeddingModel embeddingModel) {ElasticsearchVectorStoreOptions options = new ElasticsearchVectorStoreOptions();options.setIndexName("custom-index"); // 設置索引名稱options.setSimilarity(SimilarityFunction.cosine);options.setDimensions(1024); // 設置向量維度return ElasticsearchVectorStore.builder(restClient, embeddingModel).options(options).initializeSchema(true) // 沒有索引時自動創建索引.batchingStrategy(new TokenCountBatchingStrategy()).build();}}
Ollama 配置類
將本地大模型注冊為 Spring Bean,以后通過 ChatClient 來調用,這樣更加自由、定制化。
@Configuration
public class OllamaConfig {@Resourceprivate ChatModel ollamaChatModel;@Resourceprivate LoggerAdvisor loggerAdvisor;@Beanpublic ChatClient chatClient() {return ChatClient.builder(ollamaChatModel).defaultAdvisors(loggerAdvisor).build();}}
排除自動配置類
在 Spring Boot類上排除 Elasticsearch 向量存儲的自動配置類,不然會打架。
配置文件和知識庫文件
主要指定 ollama 地址和本地模型,以及端口號和請求前綴
spring:ai:ollama:base-url: http://localhost:11434chat:model: deepseek-r1:8b
server:address: 0.0.0.0port: 8888servlet:context-path: /api
添加 Markdown 讀取工具和 Markdown 文件
在 resources 目錄放一個要存到向量數據庫的文件。
Markdown 文件內容如下:
新建一個 RagController
@RestController
@RequestMapping("/rag")
public class RagController implements CommandLineRunner {@Resourceprivate ChatClient chatClient;@Resourceprivate ElasticsearchVectorStore vectorStore;@Resourceprivate MyMarkdownReader myMarkdownReader;@Overridepublic void run(String... args) throws Exception {List<Document> documents = myMarkdownReader.loadMarkdown();vectorStore.add(documents);System.out.println("文檔寫入 ES 成功");}@GetMapping("/completion")public String completion(@RequestParam String question) {return chatClient.prompt().user(question).advisors(new QuestionAnswerAdvisor(vectorStore)).call().content();}}
到這基本就 OK 了,隨后啟動項目,查看文件已經寫入成功沒,再通過 ES 調接口,查看是不是真的存儲成功,可以看到真的成了。
調用結果如下:
總結
本文只是實現的一個小 demo,適合小文本場景,對于大文本場景通常需要 ETL (提取
轉換和加載)、token 切分,Rag 相似度匹配,條件過濾,而對于有圖片的文件還需要實現 OCR。如果覺得文章不錯的話,就給我點個贊吧,嘿嘿😋。Spring 官方還提供了各種文件的 reader,可以根據需求和場景選擇合適的 reader,例如 tika 能實現 html、doc、ppt 和 pdf 多種文件的讀取,但是對于 pdf 文件個人不太建議使用 tika 庫,要想學習更多知識就請關注我吧??。
個人項目
厚米匹配
網址:厚米匹配系統
前端倉庫:https://github.com/dnwwdwd/homieMatching-fronted
后端倉庫:https://github.com/dnwwdwd/homieMatching
靈犀 BI
網址:魚智能 BI
前端倉庫:https://github.com/dnwwdwd/Lingxi-BI-fronted
后端倉庫:https://github.com/dnwwdwd/Lingxi-BI