作者:来自 Elastic Gustavo Llermaly
使用 semantic_text 新功能,并使用 AWS Bedrock 作为推理端点服务。
Elasticsearch 的新 semantic_text 映射类型旨在简化构建 RAG 应用程序的常见挑战。它整合了文本分块、生成嵌入以及检索嵌入的步骤。
在本文中,我们将使用 Amazon Bedrock 作为我们的推理服务,在不离开 Elastic 的情况下创建一个端到端 RAG 应用程序。
步骤
- 创建端点
- 创建映射
- 索引数据
- 提出问题
创建端点
在创建索引之前,我们必须创建用于推理过程的端点。端点将被命名为:
- 嵌入任务
- 完成任务
我们将使用 Bedrock 作为它们的提供者。使用这两个端点,我们可以仅使用 Elastic 工具创建一个完整的 RAG 应用程序!
如果你想了解有关如何配置 Bedrock 的更多信息,我建议你先阅读这篇文章。
嵌入任务
此任务将帮助我们为文档内容和用户将要提出的问题创建向量嵌入(vector embeddings)。
利用这些向量,我们可以找到与问题更相关的块并检索包含答案的文档。
继续在 Kibana DevTools 控制台中运行以创建端点:
PUT _inference/text_embedding/bedrock-embeddings
{
"service": "amazonbedrock",
"service_settings": {
"access_key": "{AWS_ACCESS_KEY}",
"secret_key": "{AWS_SECRET_KEY}",
"region": "{AWS_REGION}",
"provider": "amazontitan",
"model": "amazon.titan-embed-text-v1"
}
}
- provider 必须是 amazontitan、cohere 之一
- model 必须是你在 Bedrock 中可以访问的 model_id
可选附加设置
- dimensions:用于推理的输出维度
- max_input_tokens:输入 token 的最大数量
- similarity:要使用的相似度度量
Completion 任务
找到最佳块(chunk)后,我们必须将它们发送到 LLM 模型,以便它可以为我们生成答案。
运行以下命令添加完成端点:
PUT _inference/completion/bedrock-completion
{
"service": "amazonbedrock",
"service_settings": {
"access_key": "{AWS_ACCESS_KEY}",
"secret_key": "{AWS_SECRET_KEY}",
"region": "{AWS_REGION}",
"model": "anthropic.claude-3-haiku-20240307-v1:0",
"provider": "anthropic",
}
}
- provider 必须是 amazontitan、anthropic、ai21labs、cohere、meta、mistral 之一
- model 必须是你在 Bedrock 中可以访问的一个 model_id 或 ARN
创建映射
新的 semantic_text 映射类型将使事情变得非常简单。它将负责推断嵌入映射和配置,并为你进行段落分块!如果你想了解更多信息,可以阅读这篇精彩的文章。
PUT semantic-text-bedrock
{
"mappings": {
"properties": {
"super_body": {
"type": "semantic_text",
"inference_id": "bedrock-embeddings"
}
}
}
}
是的。就是这样。super_body 已准备好使用向量进行搜索,并处理分块。
索引数据
对于数据索引,我们有许多方法可用,你可以选择你喜欢的方法。
为了简单起见和递归性,我将把我们的这整篇文章复制为富文本并将其存储为文档。
POST semantic-text-bedrock/_doc
{
"super_body": "<The content of this article>"
}
我们有它。是时候测试了。
提问
提问和回答是一个两步过程。首先,我们必须检索与问题相关的文本块,然后我们必须将块发送到 LLM 以生成答案。
我们将探索两种策略来实现这一点,正如承诺的那样,无需任何额外的代码或框架。
策略 1:API 调用
我们可以运行两个 API 调用:一个到 _search 端点以检索块,另一个到 inference 端点以执行 LLM 完成步骤。
检索块
我们将尝试一种 “大海捞针” 查询,以确保 LLM 的答案是从这篇文章中获得的,而不是从 LLM 基础知识中获得的。我们将询问有关这篇文章的递归性的 cat.gif。
我们可以运行简短的语义文本默认查询:
GET semantic-text-bedrock/_search
{
"query": {
"semantic": {
"field": "super_body",
"query": "what's the cat thing about?"
}
}
}
问题是,这个查询不会按相关性对内部命中(块)进行排序,如果我们不想将整个文档作为上下文发送到 LLM,那么我们就需要这样做。它将按文档而不是按块对文档的相关性进行排序。
这个较长的查询将按相关性对内部命中(块)进行排序,因此我们可以抓取有用的内容。
GET semantic-text-bedrock/_search
{
"_source": false,
"retriever": {
"standard": {
"query": {
"nested": {
"path": "super_body.inference.chunks",
"query": {
"knn": {
"field": "super_body.inference.chunks.embeddings",
"query_vector_builder": {
"text_embedding": {
"model_id": "bedrock-embeddings",
"model_text": "what's the cat thing about?"
}
}
}
},
"inner_hits": {
"size": 1,
"name": "semantic-text-bedrock.super_body",
"_source": "*.text"
}
}
}
}
}
}
我们将根级 _source 设置为 false,因为我们只对相关块感兴趣
如你所见,我们正在使用 retrievers 进行此查询,响应如下所示:
现在,我们可以从响应中复制顶部块并将文本组合成一个大字符串。一些框架所做的是向每个块添加元数据。
回答问题
现在我们可以使用我们之前创建的 bedrock 完成端点将此问题与相关块一起发送并获取答案。
POST _inference/completion/bedrock-completion
{
"input": """Answer the question:\n
_what's the cat thing about?_ ,
based on the following context \n
<paste the relevant chunks here>"""
}
我们来看看答案吧!
策略 2:Playground
现在你已经了解了内部工作原理,让我向你展示如何轻松完成此操作,并使用漂亮的用户界面。使用 Elastic Playground。
转到 Playground,配置 Bedrock 连接器,然后选择我们刚刚创建的索引,你就可以开始了。
从这里你可以开始向你的全新索引提出问题。
如果你想了解块文档的另一种方法,我们建议你阅读有关使用嵌套向量字段的摄取管道的信息。
结论
新的 semantic_text 映射类型使创建 RAG 设置变得非常容易,而无需离开 Elastic 生态系统。分块和映射设置等不再是挑战(至少最初不是!),并且有多种替代方法可以向数据提问。
AWS Bedrock 通过提供嵌入和 completion 端点以及作为 Playground 连接器包含在内而完全集成!
如果你有兴趣重现本文的示例,可以在此处找到包含请求的 Postman 集合
准备好自己尝试一下了吗?开始免费试用。
Elasticsearch 集成了 LangChain、Cohere 等工具。加入我们的高级语义搜索网络研讨会,构建你的下一个 GenAI 应用程序!
原文:semantic_text with Amazon Bedrock — Search Labs