推理端點對一次可處理的文本量有限,具體取決于模型的輸入容量。分塊(Chunking) 是指將輸入文本拆分成符合這些限制的小塊的過程,在將文檔攝取到 semantic_text 字段時會進行分塊。分塊不僅有助于保持輸入文本在可處理范圍內,還能使內容更加易讀。相比返回一整篇長文檔,在搜索結果中提供最相關的文本片段更有價值。
每個分塊都會包含 文本片段 以及 從中生成的對應嵌入。
默認情況下,文檔會被拆分為 句子(sentence),然后按 最多 250 個單詞 進行分組,并且設置 1 句重疊,使得每個分塊都會與前一個分塊共享一個句子。這種重疊方式可以保持上下文的連續性,防止重要信息因硬性拆分而丟失。
Elasticsearch 使用 ICU4J 庫來檢測單詞和句子的邊界。在確定單詞邊界時,該庫遵循一系列規則,而不僅僅依賴空格字符。對于像 中文或日文 這類不使用空格分隔單詞的書寫語言,系統會利用 字典查找 來識別單詞邊界。
分塊策略
Elasticsearch 提供了 兩種分塊策略:句子策略(sentence) 和 單詞策略(word)。
-
句子策略(sentence):
該策略按 句子邊界 拆分文本,每個分塊包含一個或多個完整的句子,以確保句子級別的語境完整性。- 若某個句子導致分塊超出 max_chunk_size 設定的單詞數上限,該句子會被拆分至多個分塊中。
- sentence_overlap 選項控制前一個分塊中的 多少個句子 應該包含在當前分塊中,可選值為 0 或 1。
-
單詞策略(word):
該策略按 單詞 拆分文本,直至 max_chunk_size 限制。- overlap 選項控制當前分塊應包含前一個分塊中的 多少個單詞。
默認分塊策略 為 句子策略(sentence)。
注意:對于 8.16 版本之前創建的推理端點,默認的分塊策略是 單詞策略(word)。
可以在文章 “Elasticsearch:使用阿里 infererence API 及 semantic text 進行向量搜索” 查看更為詳盡的示例。
安裝
Elasticsarch 及 Kibana
?我們首先需要安裝 Elasticsearch 及 Kibana。我們可以參考如下的文章來進行安裝:
-
如何在 Linux,MacOS 及 Windows 上進行安裝 Elasticsearch
-
Kibana:如何在 Linux,MacOS 及 Windows 上安裝 Elastic 棧中的 Kibana
當我們安裝的時候,選擇 Elastic Stack 8.x 的文章來進行安裝。在本展示中,我們將使用 Elastic Stack 8.17.2 來進行展示。當我們首次運行 Elasticsearch 時,我們可以看到如下的界面:
請記下上面的 elastic 超級用戶的密碼,以備在下面進行使用。
下載代碼
為了展示方便,我們在地址?https://github.com/liu-xiao-guo/elasticsearch-labs/blob/main/notebooks/document-chunking/configuring-chunking-settings-for-inference-endpoints.ipynb下載最新的代碼。
拷貝證書
為了能夠使得我們的代碼能夠正常工作,我們必須拷貝 Elasticsearch 的證書:
cp ~/elastic/elasticsearch-8.17.2/config/certs/http_ca.crt .
$ pwd
/Users/liuxg/python/elasticsearch-labs-liuxg/notebooks/document-chunking
$ cp ~/elastic/elasticsearch-8.17.2/config/certs/http_ca.crt .
創建一個 .env 文件
我們還需要創建一個叫做 .env 的本地文件,并置于項目的根目錄下:
ES_USER="elastic"
ES_PASSWORD="zhHdJmd5oBEVwEfoH2Cr"
ES_ENDPOINT="localhost"
$ pwd
/Users/liuxg/python/elasticsearch-labs-liuxg/notebooks/document-chunking
$ cat .env
ES_USER="elastic"
ES_PASSWORD="zhHdJmd5oBEVwEfoH2Cr"
ES_ENDPOINT="localhost"
你需要根據自己的 Elasticsearch 安裝進行相應的修改。
安裝 Python 依賴項
pip3 install elasticsearch python-dotenv
安裝? ELSER 模型
你可以參考文章 “部署 ELSER - Elastic Learned Sparse EncoderR”。最后,我們可以看到如下的頁面:
代碼展示
我們使用 jupyter 打開我們的筆記本:
jupyter notebook configuring-chunking-settings-for-inference-endpoints.ipynb
建立 Elasticsearch 客戶端連接
from elasticsearch import Elasticsearch
from dotenv import load_dotenv
import osload_dotenv()ES_USER= os.getenv("ES_USER")
ES_PASSWORD = os.getenv("ES_PASSWORD")
ES_ENDPOINT = os.getenv("ES_ENDPOINT")url = f"https://{ES_USER}:{ES_PASSWORD}@{ES_ENDPOINT}:9200"
client = Elasticsearch(url, ca_certs = "./http_ca.crt", verify_certs = True)print(es.info())
創建推理端點對象
讓我們使用 Create Inference API 創建推理端點。
在此示例中,你將為 ELSER 集成創建一個推理端點,該端點將在你的集群中部署 Elastic 的 ELSER 模型。對于任何具有嵌入任務類型的推理端點,分塊設置都是可配置的。完整的可用集成列表可在 Create Inference API 文檔中找到。
要配置分塊設置,請在請求體中包含一個 chunking_settings
映射,其中包含 strategy
值以及所選分塊策略的任何必需值。在本示例中,你將為 sentence
策略配置分塊設置,最大分塊大小為 25 個單詞,每個分塊與前一個分塊重疊 1 個句子。有關可用分塊策略及其可配置值的更多信息,請參閱分塊策略文檔。
import requeststry: client.inference.put(task_type="sparse_embedding",inference_id="my_elser_endpoint",body={"service": "elasticsearch","service_settings": {"num_allocations": 1,"num_threads": 1,"model_id": ".elser_model_2",},"chunking_settings": {"strategy": "sentence","max_chunk_size": 25,"sentence_overlap": 1,},},)
except Exception as e:print(f"Error: {e}")
創建索引
要查看你配置的分塊設置如何生效,需要將文檔攝取到索引的 semantic_text
字段中。讓我們創建一個索引,其中包含一個 semantic_text
字段,并將其鏈接到上一步創建的推理端點。
client.indices.create(index="my_index",mappings={"properties": {"infer_field": {"type": "semantic_text","inference_id": "my_elser_endpoint",}}},
)
攝入一個文檔
現在,讓我們將一個文檔攝取到上一步創建的索引中。
注意:Elasticsearch 在創建推理端點時會啟動 ELSER 模型部署,分配節點可能需要一些時間。在執行以下請求之前,你需要等待部署被分配到節點。
client.index(index="my_index",document={"infer_field": "This is some sample document data. The data is being used to demonstrate the configurable chunking settings feature. The configured chunking settings will determine how this text is broken down into chunks to help increase inference accuracy."},
)
查看分塊
生成的分塊及其對應的推理結果存儲在索引中文檔的 _inference_fields
元字段下的 chunks
鍵中。這些分塊以字符偏移值列表的形式存儲。讓我們查看在上一步攝取文檔時生成的分塊。
為了能夠看得清楚我們的分塊,我們在 Kibana 中使用如下的命令: