Hub 文档

Webhook 指南:设置当数据集更改时自动重新训练模型的系统

Hugging Face's logo
加入 Hugging Face 社区

并获得增强的文档体验

开始使用

Webhook 指南:设置当数据集更改时自动重新训练模型的系统

Webhooks 现已公开!

本指南将引导您在 Hugging Face 平台上使用 HF Datasets、Webhooks、Spaces 和 AutoTrain 设置自动训练管道。

我们将构建一个 Webhook,它监听图像分类数据集的变化,并使用 AutoTrain 触发 microsoft/resnet-50 的微调。

先决条件:将数据集上传到 Hub

为了示例,我们将使用一个简单的图像分类数据集。有关将数据上传到 Hub 的更多信息,请点击此处

dataset

创建 Webhook 以响应数据集更改

首先,让我们从您的设置中创建一个 Webhook。

  • 选择您的数据集作为目标存储库。在此示例中,我们将目标设置为 huggingface-projects/input-dataset
  • 现在可以放置一个虚拟 Webhook URL。定义 Webhook 后,您就可以查看将发送到 Webhook 的事件。您还可以重播它们,这对于调试很有用!
  • 输入一个密钥以使其更安全。
  • 订阅“仓库更新”事件,因为我们希望响应数据更改

您的 Webhook 将如下所示

webhook-creation

创建 Space 以响应 Webhook

我们现在需要一种方法来响应您的 Webhook 事件。一种简单的方法是使用Space

您可以在此处找到一个示例 Space。

此 Space 使用 Docker、Python、FastAPIuvicorn 来运行一个简单的 HTTP 服务器。在此处阅读有关 Docker Spaces 的更多信息:https://huggingface.co/docs/hub/spaces-sdks-docker

入口点是 src/main.py。让我们详细介绍一下这个文件及其功能

  1. 它启动了一个 FastAPI 应用程序,该应用程序将监听 /webhook 上的 HTTP POST 请求
from fastapi import FastAPI

# [...]
@app.post("/webhook")
async def post_webhook(
	# ...
):

# ...
    1. 此路由检查 X-Webhook-Secret 标头是否存在,以及其值是否与您在 Webhook 设置中设置的值相同。WEBHOOK_SECRET 密钥必须在 Space 的设置中设置,并且与 Webhook 中设置的密钥相同。
# [...]

WEBHOOK_SECRET = os.getenv("WEBHOOK_SECRET")

# [...]

@app.post("/webhook")
async def post_webhook(
	# [...]
	x_webhook_secret:  Optional[str] = Header(default=None),
	# ^ checks for the X-Webhook-Secret HTTP header
):
	if x_webhook_secret is None:
		raise HTTPException(401)
	if x_webhook_secret != WEBHOOK_SECRET:
		raise HTTPException(403)
	# [...]
  1. 事件的有效负载以 JSON 编码。在这里,我们将使用 pydantic 模型来解析事件有效负载。我们还指定只在以下情况运行 Webhook:
  • 事件与输入数据集有关
  • 事件是仓库内容的更新,即有新的提交
# defined in src/models.py
class WebhookPayloadEvent(BaseModel):
	action: Literal["create", "update", "delete"]
	scope: str

class WebhookPayloadRepo(BaseModel):
	type: Literal["dataset", "model", "space"]
	name: str
	id: str
	private: bool
	headSha: str

class WebhookPayload(BaseModel):
	event: WebhookPayloadEvent
	repo: WebhookPayloadRepo

# [...]

@app.post("/webhook")
async def post_webhook(
	# [...]
	payload: WebhookPayload,
	# ^ Pydantic model defining the payload format
):
	# [...]
	if not (
		payload.event.action == "update"
		and payload.event.scope.startswith("repo.content")
		and payload.repo.name == config.input_dataset
		and payload.repo.type == "dataset"
	):
		# no-op if the payload does not match our expectations
		return {"processed": False}
	#[...]
  1. 如果有效负载有效,下一步是在 AutoTrain 上创建一个项目,安排对输入模型(在我们的示例中是 microsoft/resnet-50)进行微调,并在完成后在数据集上创建讨论!
def schedule_retrain(payload: WebhookPayload):
	# Create the autotrain project
	try:
		project = AutoTrain.create_project(payload)
		AutoTrain.add_data(project_id=project["id"])
		AutoTrain.start_processing(project_id=project["id"])
	except requests.HTTPError as err:
		print("ERROR while requesting AutoTrain API:")
		print(f"  code: {err.response.status_code}")
		print(f"  {err.response.json()}")
		raise
	# Notify in the community tab
	notify_success(project["id"])

访问评论中的链接以查看训练成本估算,并开始微调模型!

community tab notification

在此示例中,我们使用 Hugging Face AutoTrain 快速微调了模型,但您当然可以接入自己的训练基础设施!

您可以随意将 Space 复制到您的个人命名空间并进行操作。您需要提供两个密钥

  • WEBHOOK_SECRET:您的 Webhook 中的密钥。
  • HF_ACCESS_TOKEN:一个具有 write 权限的用户访问令牌。您可以从您的设置中创建一个。

您还需要修改 config.json 文件,以使用您选择的数据集和模型

{
	"target_namespace": "the namespace where the trained model should end up",
	"input_dataset": "the dataset on which the model will be trained",
	"input_model": "the base model to re-train",
	"autotrain_project_prefix": "A prefix for the AutoTrain project"
}

配置您的 Webhook 以向您的 Space 发送事件

最后但同样重要的是,您需要配置 Webhook 以向您的 Space 发送 POST 请求。

让我们首先从上下文菜单中获取 Space 的“直接 URL”。单击“嵌入此 Space”并复制“直接 URL”。

embed this Space

direct URL

更新您的 Webhook 以向该 URL 发送请求

webhook settings

就是这样!现在,对输入数据集的每次提交都将触发使用 AutoTrain 对 ResNet-50 进行微调 🎉

< > 在 GitHub 上更新