Webhook 模式
Webhook 模式会立即返回任务 ID,任务完成后把结果推送到你的回调地址,无需轮询。
前置条件
请先准备好 API Key。配置方式见 API 入门。
第一步:提交带 webhook 的任务
在提交接口上加上 ?webhook=YOUR_CALLBACK_URL:
bash
curl -X POST "https://api.get3w.com/v1/google/nano-banana-pro/text-to-image?webhook=https://your-server.com/callback" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"prompt": "A sunset over mountains",
"aspect_ratio": "16:9",
"resolution": "1k",
"output_format": "png",
"channel": "stable"
}'python
import requests
response = requests.post(
"https://api.get3w.com/v1/google/nano-banana-pro/text-to-image",
params={"webhook": "https://your-server.com/callback"},
headers={
"Authorization": "Bearer YOUR_API_KEY",
"Content-Type": "application/json"
},
json={
"prompt": "A sunset over mountains",
"aspect_ratio": "16:9",
"resolution": "1k",
"output_format": "png",
"channel": "stable"
}
)
task = response.json()
print(task["id"]) # Task is running; result will be sent to your webhookjavascript
const apiKey = "YOUR_API_KEY";
const webhookUrl = encodeURIComponent("https://your-server.com/callback");
const response = await fetch(
`https://api.get3w.com/v1/google/nano-banana-pro/text-to-image?webhook=${webhookUrl}`,
{
method: "POST",
headers: {
"Authorization": `Bearer ${apiKey}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
prompt: "A sunset over mountains",
aspect_ratio: "16:9",
resolution: "1k",
output_format: "png",
channel: "stable"
})
}
);
const task = await response.json();
console.log(task.id); // Result will be sent to your webhook响应(立即返回):
json
{
"id": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
"status": "created",
"estimated_duration": 52
}第二步:接收 webhook
任务完成(或失败)时,Get3W 会向你的回调地址发送一个带结果的 POST 请求:
json
{
"id": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
"model": "google/nano-banana-pro/text-to-image",
"status": "completed",
"code": 0,
"created_at": "2026-03-28T07:50:42",
"input": {
"prompt": "A sunset over mountains",
"aspect_ratio": "16:9",
"resolution": "1k",
"output_format": "png",
"channel": "stable"
},
"outputs": [
"https://storage.example.com/output.png"
],
"error": null
}失败时字段结构相同 —— outputs 为空数组,error 有内容:
json
{
"id": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
"model": "google/nano-banana-pro/text-to-image",
"status": "failed",
"code": 1400,
"created_at": "2026-03-28T07:50:42",
"input": { "prompt": "A sunset over mountains" },
"outputs": [],
"error": "Invalid input: prompt is required"
}每次推送都会带上全部八个字段,因此你可以直接按 status 分支处理,不必判断字段是否缺失。
第三步:处理 webhook
下面是一个接收 webhook 回调的最小服务示例:
python
from flask import Flask, request, jsonify
app = Flask(__name__)
@app.route("/callback", methods=["POST"])
def webhook_handler():
data = request.json
if data["status"] == "completed":
print(f"Task {data['id']} completed!")
print(f"Outputs: {data['outputs']}")
elif data["status"] == "failed":
print(f"Task {data['id']} failed: {data['error']}")
return jsonify({"received": True}), 200
if __name__ == "__main__":
app.run(port=3000)javascript
const express = require("express");
const app = express();
app.use(express.json());
app.post("/callback", (req, res) => {
const data = req.body;
if (data.status === "completed") {
console.log(`Task ${data.id} completed!`);
console.log(`Outputs: ${data.outputs}`);
} else if (data.status === "failed") {
console.log(`Task ${data.id} failed: ${data.error}`);
}
res.json({ received: true });
});
app.listen(3000, () => console.log("Webhook server running on port 3000"));Webhook 回调字段
| 字段 | 类型 | 说明 |
|---|---|---|
id | string | 任务 ID |
model | string | 模型 slug(如 google/nano-banana-pro/text-to-image) |
status | string | completed 或 failed |
code | int | 成功为 0;失败时见 错误码 |
created_at | string | ISO 8601 时间戳 |
input | object | 原始请求参数 |
outputs | string[] | 输出 URL 列表;任务失败时为空数组 |
error | string | 错误信息;任务成功时为 null |
重试策略
如果你的服务返回非 2xx 状态或无法访问,Get3W 最多尝试 3 次推送:第一次立即发送,之后间隔 2 秒、再间隔 4 秒。每次尝试的超时时间为 30 秒。
第三次失败后放弃推送。结果不会丢失 —— 在任务记录保留期内可通过 GET /v1/requests/{request_id} 获取。因此建议把 webhook 当作快速通道,同时为没收到回调的任务保留一条对账轮询。
什么时候用 Webhook 模式
- 服务端到服务端集成 —— 不需要保持连接,也不用跑轮询循环
- 事件驱动架构 —— 任务完成时触发下游流程
- 高吞吐流水线 —— 提交数百个任务,结果到达时逐个处理
提示
你的 webhook 地址必须可公网访问。本地开发时可以用 ngrok 之类的隧道工具把本地服务暴露出去。