Skip to main content

为规则设置 Webhook 通知

当您在自动化作上添加 Webhook URL 时,只要您定义的规则与任何新运行匹配,我们就会向您的 Webhook 终端节点发出 POST 请求。

Webhook 负载

我们发送到您的 Webhook 终端节点的负载包含

  • "rule_id"这是发送此有效负载的自动化的 ID
  • "start_time""end_time"这些是我们找到匹配运行的时间边界
  • "runs"这是一个 run 数组,其中每个 run 都是一个字典。如果您需要有关每次运行的更多信息,我们建议您在终端节点中使用我们的 SDK,以便从我们的 API 中获取它。
  • "feedback_stats"这是一本包含运行反馈统计信息的字典。此字段的示例有效负载如下所示。
"feedback_stats": {
"about_langchain": {
"n": 1,
"avg": 0.0,
"show_feedback_arrow": true,
"values": {}
},
"category": {
"n": 0,
"avg": null,
"show_feedback_arrow": true,
"values": {
"CONCEPTUAL": 1
}
},
"user_score": {
"n": 2,
"avg": 0.0,
"show_feedback_arrow": false,
"values": {}
},
"vagueness": {
"n": 1,
"avg": 0.0,
"show_feedback_arrow": true,
"values": {}
}
},
从 S3 URL 获取

根据您的运行时间,inputs_s3_urlsoutputs_s3_urls字段可能包含指向实际数据而不是数据本身的 S3 URL。

inputsoutputs可以通过ROOT.presigned_url提供于inputs_s3_urlsoutputs_s3_urls分别。

以下是我们发送到 Webhook 终端节点的整个有效负载的示例:

{
"rule_id": "d75d7417-0c57-4655-88fe-1db3cda3a47a",
"start_time": "2024-04-05T01:28:54.734491+00:00",
"end_time": "2024-04-05T01:28:56.492563+00:00",
"runs": [
{
"status": "success",
"is_root": true,
"trace_id": "6ab80f10-d79c-4fa2-b441-922ed6feb630",
"dotted_order": "20230505T051324571809Z6ab80f10-d79c-4fa2-b441-922ed6feb630",
"run_type": "tool",
"modified_at": "2024-04-05T01:28:54.145062",
"tenant_id": "2ebda79f-2946-4491-a9ad-d642f49e0815",
"end_time": "2024-04-05T01:28:54.085649",
"name": "Search",
"start_time": "2024-04-05T01:28:54.085646",
"id": "6ab80f10-d79c-4fa2-b441-922ed6feb630",
"session_id": "6a3be6a2-9a8c-4fc8-b4c6-a8983b286cc5",
"parent_run_ids": [],
"child_run_ids": null,
"direct_child_run_ids": null,
"total_tokens": 0,
"completion_tokens": 0,
"prompt_tokens": 0,
"total_cost": null,
"completion_cost": null,
"prompt_cost": null,
"first_token_time": null,
"app_path": "/o/2ebda79f-2946-4491-a9ad-d642f49e0815/projects/p/6a3be6a2-9a8c-4fc8-b4c6-a8983b286cc5/r/6ab80f10-d79c-4fa2-b441-922ed6feb630?trace_id=6ab80f10-d79c-4fa2-b441-922ed6feb630&start_time=2023-05-05T05:13:24.571809",
"in_dataset": false,
"last_queued_at": null,
"inputs": null,
"inputs_s3_urls": null,
"outputs": null,
"outputs_s3_urls": null,
"extra": null,
"events": null,
"feedback_stats": null,
"serialized": null,
"share_token": null
}
]
}

Webhook 安全性

我们强烈建议您向 Webhook URL 添加密钥查询字符串参数,并在任何传入请求中对其进行验证。这可确保在有人发现您的 Webhook URL 时,您可以将这些调用与真实的 Webhook 通知区分开来。

一个例子是

https://api.example.com/langsmith_webhook?secret=38ee77617c3a489ab6e871fbeb2ec87d

Webhook 自定义 HTTP 标头

如果您想使用 Webhook 发送任何特定的标头,可以按 URL 进行配置。要进行设置,请单击HeadersURL 字段旁边的选项,然后添加标头。

注意

标头以加密格式存储。

Webhook 交付

在将事件传送到您的 Webhook 终端节点时,我们遵循以下准则

  • 如果我们无法连接到您的终端节点,我们会在声明传输失败之前重试传输连接最多 2 次。
  • 如果您的终端节点回复时间超过 5 秒,我们会声明传输失败,并且不会 。
  • 如果您的终端节点在 5 秒内返回 5xx 状态代码,我们将使用指数退避最多重试 2 次。
  • 如果您的终端节点返回 4xx 状态代码,我们将声明传输失败,并且不会重试。
  • 您的终端节点在正文中返回的任何内容都将被忽略

模态示例

设置

有关如何设置的示例,我们将使用 Modal。Modal 提供用于推理和微调的自动扩展 GPU、代码代理的安全容器化以及无服务器 Python Web 终端节点。我们将在此处重点介绍 Web 终端节点。

首先,创建一个 Modal 帐户。然后,在本地安装 Modal SDK:

pip install modal

要完成账户设置,请运行以下命令:

modal setup

并按照说明作

秘密

接下来,你需要在 Modal 中设置一些 secret。

首先,LangSmith 需要通过传入 secret 来向 Modal 进行身份验证。 执行此作的最简单方法是在查询参数中传入密钥。 要验证这个 secret,我们需要在 Modal 中添加一个 secret 来验证它。 我们将通过创建一个 Modal 密钥来做到这一点。 您可以在此处查看 secret 的说明。 为此,我们将我们的 secret 称为ls-webhook并设置一个名称为LS_WEBHOOK.

我们还可以设置 LangSmith 密钥 - 幸运的是,已经有一个集成模板了!

LangSmith 模态模板

服务

之后,您可以创建一个 Python 文件作为您的终端节点。 下面是一个示例,其中的注释解释了发生了什么:

from fastapi import HTTPException, status, Request, Query
from modal import Secret, Stub, web_endpoint, Image

stub = Stub("auth-example", image=Image.debian_slim().pip_install("langsmith"))


@stub.function(
secrets=[Secret.from_name("ls-webhook"), Secret.from_name("my-langsmith-secret")]
)
# We want this to be a `POST` endpoint since we will post data here
@web_endpoint(method="POST")
# We set up a `secret` query parameter
def f(data: dict, secret: str = Query(...)):
# You can import dependencies you don't have locally inside Modal functions
from langsmith import Client

# First, we validate the secret key we pass
import os

if secret != os.environ["LS_WEBHOOK"]:
raise HTTPException(
status_code=status.HTTP_401_UNAUTHORIZED,
detail="Incorrect bearer token",
headers={"WWW-Authenticate": "Bearer"},
)

# This is where we put the logic for what should happen inside this webhook
ls_client = Client()
runs = data["runs"]
ids = [r["id"] for r in runs]
feedback = list(ls_client.list_feedback(run_ids=ids))
for r, f in zip(runs, feedback):
try:
ls_client.create_example(
inputs=r["inputs"],
outputs={"output": f.correction},
dataset_name="classifier-github-issues",
)
except Exception:
raise ValueError(f"{r} and {f}")
# Function body
return "success!"

我们现在可以使用modal deploy ...(请参阅此处的文档)。

您现在应该得到如下内容:

✓ Created objects.
├── 🔨 Created mount /Users/harrisonchase/workplace/langsmith-docs/example-webhook.py
├── 🔨 Created mount PythonPackage:langsmith
└── 🔨 Created f => https://hwchase17--auth-example-f.modal.run
✓ App deployed! 🎉

View Deployment: https://modal.com/apps/hwchase17/auth-example

要记住的重要一点是https://hwchase17--auth-example-f.modal.run- 我们创建的用于运行的函数。 注意:这不是最终的部署 URL,请确保不要意外使用它。

连接它

我们现在可以将上面创建的函数 URL 添加为 Webhook。 我们还必须记住将密钥作为查询参数传入。 将它们放在一起,它应该看起来像这样:

https://hwchase17--auth-example-f-dev.modal.run?secret={SECRET}

取代{SECRET}替换为您创建的用于访问 Modal 服务的密钥。


这个页面有帮助吗?


您可以在 GitHub 上留下详细的反馈。