PromptBuilder
在 Generator 之前,在管道中使用此组件来渲染提示模板并填充变量值。
| pipeline 中的最常见位置 | 在查询管道中,在 Generator 之前 |
| 必需的初始化变量 | "template": 使用 Jinja2 语法的提示模板字符串 |
| 强制运行变量 | “**kwargs”:用于渲染提示模板的任何字符串。有关更多详细信息,请参阅变量部分。 |
| 输出变量 | “prompt”:表示渲染后的提示模板的字符串 |
| API 参考 | Builders (构建器) |
| GitHub 链接 | https://github.com/deepset-ai/haystack/blob/main/haystack/components/builders/prompt_builder.py |
概述
PromptBuilder 使用提示模板进行初始化,并通过填充通过关键字参数传递的参数来渲染它,kwargs。使用kwargs,您可以传递可变数量的关键字参数,以便提示模板中使用的任何变量都可以指定所需的值。提示模板中出现的所有变量的值都需要通过kwargs.
在初始化时提供给PromptBuilder 的模板需要符合Jinja2 模板语言。
变量
初始化模板中找到的模板变量用作组件的输入类型。如果没有设置required_variables,则默认情况下所有变量都被视为可选。在这种情况下,任何缺失的变量都将替换为空字符串,这可能导致意外行为,尤其是在复杂的管道中。
使用required_variables 和variables 用于指定输入类型和必需变量
-
required_variables- 定义在组件运行时必须提供的模板变量。
- 如果缺少任何必需变量,组件将引发错误并停止执行。
- 您可以
- 传递必需变量名的列表(例如
["query"]),或者 - 使用
"*"将模板中的所有变量标记为必需。
- 传递必需变量名的列表(例如
-
variables- 列出模板中可能出现的所有变量,无论必需还是可选。
- 未提供的可选变量将在渲染的提示中替换为空字符串。
- 这允许在不引发错误的情况下构建部分提示,除非变量被标记为必需。
from haystack.components.builders import PromptBuilder
# All variables optional (default to empty string)
builder = PromptBuilder(
template="Hello {{name}}! {{greeting}}",
required_variables=[] # or omit this parameter entirely
)
# Some variables required
builder = PromptBuilder(
template="Hello {{name}}! {{greeting}}",
required_variables=["name"] # 'greeting' remains optional
)
组件在运行时只等待必需的输入。
Jinja2 时间扩展
PromptBuilder 支持 Jinja2 TimeExtension,它允许您使用日期时间格式。
Time Extension 提供了两个主要功能:
- 一个
now标签,让您可以访问当前时间, - 通过 Python 的 datetime 模块进行日期/时间格式化功能。
要使用 Jinja2 TimeExtension,您需要安装一个依赖项,使用
pip install arrow>=1.3.0
该now 标签
now 标签该now 标签创建一个表示当前时间的 datetime 对象,然后您可以将其存储在变量中
{% now 'utc' as current_time %}
The current UTC time is: {{ current_time }}
您可以指定不同的时区
{% now 'America/New_York' as ny_time %}
The time in New York is: {{ ny_time }}
如果您不指定时区,将使用您系统的本地时区
{% now as local_time %}
Local time: {{ local_time }}
日期格式化
您可以使用 Python 的strftime 语法格式化 datetime 对象
{% now as current_time %}
Formatted date: {{ current_time.strftime('%Y-%m-%d %H:%M:%S') }}
常见的格式代码是:
%Y:4 位年份(例如,2025)%m:月份(01-12)%d:日期(01-31)%H:小时(24 小时制,00-23)%M:分钟(00-59)%S:秒(00-59)
示例
from haystack.components.builders import PromptBuilder
# Define template using Jinja-style formatting
template = """
Current date is: {% now 'UTC' %}
Thank you for providing the date
Yesterday was: {% now 'UTC' - 'days=1' %}
"""
builder = PromptBuilder(template=template)
result = builder.run()["prompt"]
now = f"Current date is: {arrow.now('UTC').strftime('%Y-%m-%d %H:%M:%S')}"
yesterday = f"Yesterday was: {(arrow.now('UTC').shift(days=-1)).strftime('%Y-%m-%d %H:%M:%S')}"
用法
单独使用
以下是使用PromptBuilder 渲染提示模板并填充target_language 和snippet 的示例。PromptBuilder 返回一个包含字符串的提示:将以下上下文翻译成西班牙语。上下文:我不会说西班牙语;翻译.
from haystack.components.builders import PromptBuilder
template = "Translate the following context to {{ target_language }}. Context: {{ snippet }}; Translation:"
builder = PromptBuilder(template=template)
builder.run(target_language="spanish", snippet="I can't speak spanish.")
在 pipeline 中
下面是一个 RAG 管道的示例,我们在其中使用PromptBuilder 来渲染自定义提示模板,并用检索到的文档的内容和查询来填充它。然后将渲染后的提示发送给 Generator。
from haystack import Pipeline, Document
from haystack.utils import Secret
from haystack.components.generators import OpenAIGenerator
from haystack.components.builders.prompt_builder import PromptBuilder
# in a real world use case documents could come from a retriever, web, or any other source
documents = [Document(content="Joe lives in Berlin"), Document(content="Joe is a software engineer")]
prompt_template = """
Given these documents, answer the question.\nDocuments:
{% for doc in documents %}
{{ doc.content }}
{% endfor %}
\nQuestion: {{query}}
\nAnswer:
"""
p = Pipeline()
p.add_component(instance=PromptBuilder(template=prompt_template), name="prompt_builder")
p.add_component(instance=OpenAIGenerator(api_key=Secret.from_env_var("OPENAI_API_KEY")), name="llm")
p.connect("prompt_builder", "llm")
question = "Where does Joe live?"
result = p.run({"prompt_builder": {"documents": documents, "query": question}})
print(result)
运行时更改模板(提示工程)
PromptBuilder 允许您切换现有管道的提示模板。下面的示例基于上一节中的现有管道。我们使用新的提示模板调用现有管道,
documents = [
Document(content="Joe lives in Berlin", meta={"name": "doc1"}),
Document(content="Joe is a software engineer", meta={"name": "doc1"}),
]
new_template = """
You are a helpful assistant.
Given these documents, answer the question.
Documents:
{% for doc in documents %}
Document {{ loop.index }}:
Document name: {{ doc.meta['name'] }}
{{ doc.content }}
{% endfor %}
Question: {{ query }}
Answer:
"""
p.run({
"prompt_builder": {
"documents": documents,
"query": question,
"template": new_template,
},
})
如果您希望在提示工程中使用与默认模板不同的变量,可以通过设置PromptBuilder 的变量初始化参数来实现。
运行时覆盖变量
如果您想覆盖变量的值,可以在运行时使用template_variables,如下所示:
language_template = """
You are a helpful assistant.
Given these documents, answer the question.
Documents:
{% for doc in documents %}
Document {{ loop.index }}:
Document name: {{ doc.meta['name'] }}
{{ doc.content }}
{% endfor %}
Question: {{ query }}
Please provide your answer in {{ answer_language | default('English') }}
Answer:
"""
p.run({
"prompt_builder": {
"documents": documents,
"query": question,
"template": language_template,
"template_variables": {"answer_language": "German"},
},
})
请注意,language_template 引入了answer_language 变量,该变量未绑定到任何管道变量。如果未另行设置,它将使用其默认值“English”。在此示例中,我们将它的值覆盖为“German”。
该template_variables 允许您覆盖管道变量(例如文档)。
其他参考资料
🧑🍳食谱
更新于 4 个月前
