Assistants API 深入探究试用版
如 Assistants 概述中所述,使用 Assistants API 构建应用程序涉及多个概念。
本指南将更深入地介绍这些概念中的每一个。
如果您想立即开始编码,请查看 Assistants API 快速入门。
创建助手
首先,创建 Assistant 只需要指定model
使用。但您可以进一步自定义 Assistant 的行为:
- 使用
instructions
参数来指导 Assistant 的个性并定义其目标。说明类似于 Chat Completions API 中的系统消息。 - 使用
tools
参数,以便 Assistant 访问最多 128 个工具。您可以授予它对 OpenAI 托管工具的访问权限,例如code_interpreter
和file_search
调用第三方工具,或通过function
叫。 - 使用
tool_resources
参数为工具提供code_interpreter
和file_search
访问文件。文件使用File
upload 端点,并且必须具有purpose
设置为assistants
与此 API 一起使用。
例如,要创建一个 Assistant,该 Assistant 可以基于.csv
文件,请先上传一个文件。
1
2
3
4
file = client.files.create(
file=open("revenue-forecast.csv", "rb"),
purpose='assistants'
)
然后,使用code_interpreter
工具,并将文件作为资源提供给工具。
1
2
3
4
5
6
7
8
9
10
11
assistant = client.beta.assistants.create(
name="Data visualizer",
description="You are great at creating beautiful data visualizations. You analyze data present in .csv files, understand trends, and come up with data visualizations relevant to those trends. You also share a brief text summary of the trends observed.",
model="gpt-4o",
tools=[{"type": "code_interpreter"}],
tool_resources={
"code_interpreter": {
"file_ids": [file.id]
}
}
)
您最多可以将 20 个文件附加到code_interpreter
和 10,000 个文件更改为file_search
(使用vector_store
对象)。
每个文件的大小最大为 512 MB,最多有 5,000,000 个令牌。默认情况下,项目中上传的所有文件的大小不能超过 100 GB,但您可以联系我们的支持团队来提高此限制。
管理线程和消息
Threads (线程) 和 Messages (消息) 表示 Assistant 与用户之间的对话会话。每个线程的消息数限制为 100,000 条。一旦 Messages 的大小超过模型的上下文窗口,Thread 将尝试巧妙地截断消息,然后完全删除它认为最不重要的消息。
您可以创建一个具有初始 Messages 列表的 Thread,如下所示:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
thread = client.beta.threads.create(
messages=[
{
"role": "user",
"content": "Create 3 data visualizations based on the trends in this file.",
"attachments": [
{
"file_id": file.id,
"tools": [{"type": "code_interpreter"}]
}
]
}
]
)
消息可以包含文本、图像或文件附件。消息attachments
是将文件添加到线程的tool_resources
.您还可以选择将文件添加到thread.tool_resources
径直。
创建图像输入内容
消息内容可以包含外部图像 URL 或通过文件 API 上传的文件 ID。只有支持 Vision 的型号才能接受图像输入。支持的图像内容类型包括 png、jpg、gif 和 webp。创建图像文件时,将purpose="vision"
,以便您以后下载并显示输入内容。目前,每个项目有 100GB 的限制。请联系我们以请求提高限制。
除非指定,否则工具无法访问图像内容。要将图像文件传递给 Code Interpreter,请在消息中添加文件 IDattachments
list 以允许工具读取和分析输入。目前无法在 Code Interpreter 中下载图像 URL。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
file = client.files.create(
file=open("myimage.png", "rb"),
purpose="vision"
)
thread = client.beta.threads.create(
messages=[
{
"role": "user",
"content": [
{
"type": "text",
"text": "What is the difference between these images?"
},
{
"type": "image_url",
"image_url": {"url": "https://example.com/image.png"}
},
{
"type": "image_file",
"image_file": {"file_id": file.id}
},
],
}
]
)
低保真或高保真图像理解
通过控制detail
参数,该参数有三个选项,low
,high
或auto
中,您可以控制模型处理图像和生成其文本理解的方式。
low
将启用 “Low Res” 模式。该模型将收到 512 像素 x 512 像素的低分辨率图像版本,并以 85 个令牌的预算表示图像。这允许 API 返回更快的响应,并为不需要高细节的使用案例消耗更少的输入令牌。high
将启用“高分辨率”模式,该模式首先允许模型查看低分辨率图像,然后根据输入图像大小创建输入图像的详细裁剪。使用定价计算器查看各种图像大小的令牌计数。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
thread = client.beta.threads.create(
messages=[
{
"role": "user",
"content": [
{
"type": "text",
"text": "What is this an image of?"
},
{
"type": "image_url",
"image_url": {
"url": "https://example.com/image.png",
"detail": "high"
}
},
],
}
]
)
上下文窗口管理
Assistants API 会自动管理截断,以确保其保持在模型的最大上下文长度内。您可以通过指定希望运行使用的最大令牌数和/或希望包含在运行中的最近消息的最大数量来自定义此行为。
Max Completion 和 Max Prompt Tokens
要控制单次 Run 中的令牌使用,请将max_prompt_tokens
和max_completion_tokens
在创建 Run.这些限制适用于整个运行生命周期中所有完成中使用的令牌总数。
例如,使用max_prompt_tokens
设置为 500 且max_completion_tokens
设置为 1000 表示第一次完成会将线程截断为 500 个令牌,并将输出限制为 1000 个令牌。如果在第一次完成中仅使用 200 个提示令牌和 300 个完成令牌,则第二次完成将具有 300 个提示令牌和 700 个完成令牌的可用限制。
如果完成达到max_completion_tokens
limit,则 Run 将终止,状态为incomplete
,详细信息将在incomplete_details
字段。
截断策略
您还可以指定截断策略来控制如何将线程渲染到模型的上下文窗口中。
使用类型为auto
将使用 OpenAI 的默认截断策略。使用类型为last_messages
将允许您指定要包含在上下文窗口中的最新消息的数量。
消息注释
由 Google 助理创建的消息可能包含annotations
在content
对象的数组。注释提供有关应如何注释 Message 中的文本的信息。
有两种类型的 Annotation:
file_citation
:文件引文由file_search
工具,并定义对 Assistant 上传和用于生成响应的特定文件的引用。file_path
:文件路径注释由code_interpreter
工具,并包含对该工具生成的文件的引用。
当 Message 对象中存在注释时,您将在文本中看到难以辨认的模型生成的子字符串,您应该将其替换为注释。这些字符串可能如下所示【13†source】
或sandbox:/mnt/data/file.csv
.下面是一个示例 python 代码片段,它将这些字符串替换为注释中存在的信息。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
# Retrieve the message object
message = client.beta.threads.messages.retrieve(
thread_id="...",
message_id="..."
)
# Extract the message content
message_content = message.content[0].text
annotations = message_content.annotations
citations = []
# Iterate over the annotations and add footnotes
for index, annotation in enumerate(annotations):
# Replace the text with a footnote
message_content.value = message_content.value.replace(annotation.text, f' [{index}]')
# Gather citations based on annotation attributes
if (file_citation := getattr(annotation, 'file_citation', None)):
cited_file = client.files.retrieve(file_citation.file_id)
citations.append(f'[{index}] {file_citation.quote} from {cited_file.filename}')
elif (file_path := getattr(annotation, 'file_path', None)):
cited_file = client.files.retrieve(file_path.file_id)
citations.append(f'[{index}] Click <here> to download {cited_file.filename}')
# Note: File download functionality not implemented above for brevity
# Add footnotes to the end of the message before displaying to user
message_content.value += '\n' + '\n'.join(citations)
运行和运行步骤
当您在 Thread 中拥有用户所需的所有上下文时,您可以使用您选择的 Assistant 运行 Thread。
1
2
3
4
run = client.beta.threads.runs.create(
thread_id=thread.id,
assistant_id=assistant.id
)
默认情况下,Run 将使用model
和tools
配置,但您可以在创建 Run 时覆盖其中的大部分配置,以增加灵活性:
1
2
3
4
5
6
7
run = client.beta.threads.runs.create(
thread_id=thread.id,
assistant_id=assistant.id,
model="gpt-4o",
instructions="New instructions that override the Assistant instructions",
tools=[{"type": "code_interpreter"}, {"type": "file_search"}]
)
注意:tool_resources
在创建运行期间,无法覆盖与 Assistant 关联的 Assistant。您必须使用 modify Assistant 终端节点来执行此作。
运行生命周期
Run 对象可以具有多个状态。
地位 | 定义 |
---|---|
queued | 首次创建运行时或完成required_action ,它们将移至 queued 状态。他们几乎应该立即迁移到in_progress . |
in_progress | in_progress时,Assistant 使用模型和工具执行步骤。您可以通过检查 Run Steps 来查看 Run 的进度。 |
completed | Run 成功完成!您现在可以查看 Assistant 添加到 Thread 的所有消息,以及 Run 执行的所有步骤。您还可以通过向 Thread 添加更多用户 Messages 并创建另一个 Run 来继续对话。 |
requires_action | 使用函数调用工具时,Run 将移动到required_action state 之后,模型确定要调用的函数的名称和参数。然后,您必须运行这些函数并在运行继续之前提交输出。如果在expires_at 时间戳通过(创建后大约 10 分钟),运行将变为 Expired 状态。 |
expired | 当调用输出的函数之前未提交时,会发生这种情况expires_at 并且运行过期。此外,如果运行执行时间过长,并且超出了expires_at ,我们的系统将使运行过期。 |
cancelling | 您可以尝试取消in_progress 使用 Cancel Run 终端节点运行。尝试取消后,Run (运行) 的状态将变为cancelled .尝试取消,但不能保证取消。 |
cancelled | 已成功取消运行。 |
failed | 您可以通过查看last_error 对象。失败的时间戳将记录在failed_at . |
incomplete | 运行结束时间max_prompt_tokens 或max_completion_tokens 达到。您可以通过查看incomplete_details 对象。 |
轮询更新
如果您未使用流式处理,为了使运行状态保持最新,您必须定期检索 Run 对象。每次检索对象时,您都可以检查运行状态,以确定应用程序下一步应执行的作。
您可以选择使用我们的 Node 和 Python SDK 中的 Polling Helpers 来帮助您完成此作。这些帮助程序将自动为你轮询 Run 对象,并在 Run 对象处于最终状态时返回该对象。
线程锁
当 Run 为in_progress
而不是处于终端状态,则 Thread 被锁定。这意味着:
- 无法将新消息添加到线程中。
- 无法在 Thread 上创建新的 Run。
运行步骤
Run step statuss 与 Run statuss 具有相同的含义。
Run Step 对象中的大部分有趣细节都位于step_details
田。可以有两种类型的步骤详细信息:
message_creation
:当 Assistant 在线程上创建消息时,将创建此运行步骤。tool_calls
:此运行步骤是在 Assistant 调用工具时创建的。有关此内容的详细信息,请参阅工具指南的相关部分。
数据访问指南
目前,通过 API 创建的 Assistants、Threads、Messages 和 Vector Store 的范围限定为创建它们的 Project。因此,任何拥有该项目 API 密钥访问权限的人都可以在项目中读取或写入 Assistants、Threads、Messages 和 Runs。
我们强烈建议使用以下数据访问控制:
- 实施授权。在对 Assistants、Threads、Messages 和 Vector Store 执行读取或写入作之前,请确保最终用户已获得授权。例如,将最终用户有权访问的对象 ID 存储在数据库中,并在使用 API 获取对象 ID 之前对其进行检查。
- 限制 API 密钥访问。仔细考虑您的组织中哪些人应该拥有 API 密钥并成为项目的一部分。定期审核此列表。API 密钥支持各种作,包括读取和修改敏感信息,例如消息和文件。
- 创建单独的帐户。请考虑为不同的应用程序创建单独的项目,以便跨多个应用程序隔离数据。