
# WhatsApp 模板 API

WhatsApp 消息模板是预先编写的消息，已获准在正常的 24 小时会话窗口之外发送——例如欢迎消息、预约提醒或重新互动提示。此 API 允许您以编程方式列出、创建、编辑、提交、检查、删除和发送模板。

以下所有路径均相对于 API 基础 URL：

```
https://api.youraiconnector.com/v1
```

每个请求都必须经过身份验证。有关四种接受的方法，请参阅 [身份验证](authentication.md)。本页上的示例使用 `X-API-Key` 标头（以及一种用于 cURL 的查询参数形式）。

::: note
**注意：** 模板运行在 WhatsApp Business API 通道上，因此 API 的这一部分既需要 API 访问权限，也需要包含 WhatsApp 通道的套餐。如果没有这些，请求将被 `403` 拒绝。
:::


---

## 使用子账户（代理机构）


---

## 审批状态

由于在开放会话之外发送的消息必须先由 WhatsApp 审核，因此每个模板都带有审批 `status`：

| 状态 | 含义 |
|---|---|
| `draft` | 已创建或保存，但尚未发送以供审核。您仍然可以对其进行编辑。 |
| `received` | 已提交并进入审核队列。 |
| `pending` | 审核中。 |
| `approved` | 已获准发送。 |
| `rejected` | 已拒绝。`rejection_reason` 字段解释了原因；请修复它，然后再次提交。 |

只有 `draft` 和 `rejected` 状态的模板可以被编辑或（重新）提交。一旦模板处于 `approved` 状态，它就会被锁定——如果您需要更改，请创建一个新模板。

> **自动审批：** 某些通道不需要外部审核步骤。在此类通道上为营销活动创建或提交的模板会立即存储为 `approved`，且没有内容 ID (`sid`)。

---

## Meta 连接账户上的模板

无论您的账户使用哪种 WhatsApp 连接方式，这些端点的工作方式都是相同的，但其背后的处理逻辑有所不同：

- 在**托管 WhatsApp 连接**上，模板会在消息服务提供商处注册，且 `sid` 是该提供商的内容 ID (`HXXXXXXXX…`)。
- 在使用**自有 WhatsApp Business 账户**（任一 Meta 连接选项）的账户上，模板是在**该 WhatsApp Business 账户**中创建并审核的，且 `sid` 是 Meta 自己的模板 ID——一个数字字符串，例如 `"3394843740694756"`。`status` 仍然使用上表中的值，`rejection_reason` 仍然包含 Meta 的说明。

为此提供了两个额外的端点：一个用于查询您当前使用的连接方式，另一个用于将您的模板列表与您的 WhatsApp Business 账户进行对账。同步操作会将 WhatsApp Business 账户中已存在的模板导入到您的库中，因此同步后的 `GET /whatsapp-templates` 会像列出其他模板一样列出它们。

### 检查模板运行所在的连接方式

`GET /whatsapp-templates/provider`

| 字段 | 描述 |
|---|---|
| `provider` | 当模板在托管消息服务提供商处注册时为 `twilio`，当模板位于您自己的 WhatsApp Business 账户中时为 `meta`。 |
| `lane` | 当前使用的 Meta 连接方式 — `meta_cloud_api`（您自己的 Meta 应用）或 `meta_embedded`（通过我们的 Meta 应用连接）。在托管连接上为 `null`。 |
| `waba_id` | 模板所在的 WhatsApp Business 账户，或 `null`。 |
| `templates_enabled` | 当 Meta 连接尚未完成（未存储 WhatsApp Business 账户或访问令牌）时为 `false`。在此之前，创建或提交模板的操作将失败并返回 `400`。 |

**cURL**

```bash
curl "https://api.youraiconnector.com/v1/whatsapp-templates/provider?apiKey=YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/provider", {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/whatsapp-templates/provider",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "provider": "meta",
  "lane": "meta_cloud_api",
  "waba_id": "2357661648036355",
  "templates_enabled": true
}
```

### 从 Meta 同步模板

刷新位于您的 WhatsApp Business 账户中的每个模板的审核状态，并导入所有存在于该账户中但尚未进入您库中的模板。可以根据需要随时调用，无需担心风险。在托管连接上，由于没有可同步的内容，该调用不会执行任何操作，仅报告您拥有的模板数量。

`POST /whatsapp-templates/meta-sync`

| 字段 | 描述 |
|---|---|
| `imported` | 在 WhatsApp Business 账户中找到并通过此调用添加到您库中的模板。 |
| `updated` | 状态或详细信息发生更改的现有模板。 |
| `total` | 同步后您库中的模板。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/meta-sync?apiKey=YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/meta-sync", {
  method: "POST",
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/meta-sync",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "provider": "meta",
  "imported": 2,
  "updated": 5,
  "total": 12
}
```

### 直接与 Meta 对话（高级）

如果您需要上述端点未公开的功能（例如模板页眉、页脚、按钮或完全手动构建的模板），`/v1/meta-templates` 会将您的请求直接传递给 Meta 自己的模板 API，而不会在您的模板库中存储任何内容。它仅适用于号码运行在自有 WhatsApp Business 账户上的账户；在托管连接上，每次调用都会返回 `400`，要求您先连接一个 Meta 应用。

| 端点 | 功能 |
|---|---|
| `GET /meta-templates` | 列出您 WhatsApp Business 账户上的模板及其最新状态。添加 `?name=` 可筛选至特定的模板名称。返回 `{ "success": true, "templates": [...] }`。 |
| `POST /meta-templates` | 创建模板并将其提交给 Meta 进行审核（一步完成）。需要 `name`、`language` 和 `body`（或完整的 `components` 数组，而非 `body`）。可选：`variables`（字符串数组）、`category`（`MARKETING`、`UTILITY` 或 `AUTHENTICATION`）、`header`、`footer`、`buttons`。返回 `201` 以及 `{ "success": true, "template": {...} }`。 |
| `DELETE /meta-templates/{name}` | 按 Meta 名称删除模板 — 删除其**所有语言版本**。添加带有 Meta 模板 ID 的 `?hsm_id=` 可仅删除单一语言版本。返回 `{ "success": true, "name": "..." }`。 |

Meta 拒绝的模板会返回 `400`，并在 `error` 中包含 Meta 自己的解释。

---

## 列出模板

返回您账户上的所有模板，并附带每个模板的简要摘要。

`GET /whatsapp-templates`

**cURL**

```bash
curl "https://api.youraiconnector.com/v1/whatsapp-templates?apiKey=YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates", {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/whatsapp-templates",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": [
    {
      "id": "template_abc123",
      "name": "welcome_message",
      "status": "approved",
      "language": "en",
      "body": "Hi {{first_name}}, thanks for reaching out!"
    },
    {
      "id": "template_def456",
      "name": "appointment_reminder",
      "status": "pending",
      "language": "en",
      "body": "Hi {{first_name}}, this is a reminder about your appointment."
    }
  ]
}
```

---

## 获取模板

返回单个模板的完整详细信息，包括其变量、状态和时间戳。

`GET /whatsapp-templates/{templateId}`

**cURL**

```bash
curl "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123" \
  -H "X-API-Key: YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
  { headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template": {
    "id": "template_abc123",
    "name": "welcome_message",
    "body": "Hi {{first_name}}, thanks for reaching out!",
    "language": "en",
    "variables": ["first_name"],
    "status": "approved",
    "sid": "HXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX",
    "type": "general",
    "category": "marketing",
    "rejection_reason": null,
    "campaign_id": "campaign123",
    "date_created": "2026-06-01T10:00:00.000Z",
    "date_updated": "2026-06-02T08:30:00.000Z",
    "submitted_at": "2026-06-01T10:05:00.000Z",
    "approved_at": "2026-06-02T08:30:00.000Z"
  }
}
```

如果您的账户中不存在该模板，则会返回 `404` 以及 `{ "success": false, "error": "Template not found" }`。

---

## 创建模板

为营销活动的开场消息创建一个模板，并将其一步提交以供审核。

`POST /whatsapp-templates`

| 字段 | 必填 | 描述 |
|---|---|---|
| `campaign_id` | 是 | 模板所属的营销活动。 |
| `name` | 是 | 模板名称。 |
| `language` | 是 | 语言代码，例如 `en`、`es`、`de`、`pt_BR`、`zh_CN`。 |
| `body` | 是 | 消息文本，最多 1024 个字符。 |
| `variables` | 否 | 正文中使用的变量名称的有序列表。 |

变量占位符可以写为 `{{first_name}}`、`{first_name}` 或 `[first_name]` —— 它们都会被标准化为双花括号形式。

结果取决于营销活动的渠道：

- **WhatsApp Business API 营销活动：** 内容会被发送以进行 WhatsApp 审核。响应包含 `campaign_status`（`received` 或 `pending`）以及 `template_sid`。
- **无需外部审核步骤的渠道：** 模板会被存储并自动批准（`campaign_status: "approved"`，`template_sid: null`）。
- **营销活动中没有 WhatsApp 渠道：** 不会创建任何内容，且 `campaign_status` 为 `not_applicable`。

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "campaign_id": "campaign123",
    "name": "welcome_message",
    "language": "en",
    "body": "Hi {{first_name}}, thanks for reaching out!",
    "variables": ["first_name"]
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    campaign_id: "campaign123",
    name: "welcome_message",
    language: "en",
    body: "Hi {{first_name}}, thanks for reaching out!",
    variables: ["first_name"],
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "campaign_id": "campaign123",
        "name": "welcome_message",
        "language": "en",
        "body": "Hi {{first_name}}, thanks for reaching out!",
        "variables": ["first_name"],
    },
)
data = res.json()
```

**响应**（已提交审核）

```json
{
  "success": true,
  "campaign_status": "pending",
  "template_sid": "HXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
}
```

---

## 创建独立模板

在您的模板库中创建一个模板，而不将其绑定到营销活动的开场消息。这是本页面后续生命周期中的创建步骤：在此处创建、编辑、提交审核、轮询其状态，并在不再需要时将其删除。

`POST /whatsapp-templates/docs`

| 字段 | 必填 | 描述 |
|---|---|---|
| `name` | 是 | 模板名称。 |
| `language` | 是 | 语言代码，例如 `en`、`es`、`de`、`pt_BR`、`zh_CN`。 |
| `body` | 是 | 消息文本，最多 1024 个字符。 |
| `variables` | 否 | 正文中使用的变量名称的有序列表。 |
| `status` | 否 | `draft`（默认）仅存储而不提交；`submitted` 立即将其加入 WhatsApp 审核队列。 |
| `type` | 否 | `general`（默认）或 `smart_followup`。 |
| `category` | 否 | `marketing`、`utility`、`authentication` 或 `authentication-international`。 |
| `campaign_id` | 否 | 将模板链接到您的某个营销活动。 |

> **身份验证（一次性代码）模板。** WhatsApp 不接受自由文本形式的身份验证模板：消息正文由 WhatsApp 预设，且模板必须包含一个“复制验证码”按钮。当您使用 `category: "authentication"` 创建模板时，我们会以该固定格式为您提交。您的 `body` 将作为应用中显示的预览保留，但您的联系人收到的文本是 WhatsApp 自己的措辞（包含验证码、安全提醒和 10 分钟过期提示）。请声明一个变量（例如 `["code"]`），并在发送时传入验证码（请参阅[向联系人发送模板](#send-a-template-to-a-contact)中的 `variables` 字段）。验证码必须短于 15 个字符。

> **我应该使用哪个创建接口？** 当您想要一个可以自行编辑和提交的模板时，请使用此接口。当您想要设置营销活动的开场消息时，请使用 `POST /whatsapp-templates`（见上文）——该接口需要 `campaign_id` 并直接写入营销活动中。

以 `submitted` 方式创建的模板会在后台发送以进行 WhatsApp 审核，因此请检查状态端点以获取结果，而不是期望在响应中直接获得结果。

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/docs?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "welcome_message",
    "language": "en",
    "body": "Hi {{first_name}}, thanks for reaching out!",
    "variables": ["first_name"],
    "status": "draft",
    "category": "marketing"
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/docs", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    name: "welcome_message",
    language: "en",
    body: "Hi {{first_name}}, thanks for reaching out!",
    variables: ["first_name"],
    status: "draft",
    category: "marketing",
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/docs",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "name": "welcome_message",
        "language": "en",
        "body": "Hi {{first_name}}, thanks for reaching out!",
        "variables": ["first_name"],
        "status": "draft",
        "category": "marketing",
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template_id": "template_abc123",
  "status": "draft"
}
```

缺少 `name`、`language` 或 `body`，使用不支持的语言，`status` 不是 `draft` 或 `submitted`，未知的 `type` 或 `category`，或者正文超过 1024 个字符，将返回 `400` 并附带解释性的 `error`。如果 `campaign_id` 不是您的营销活动之一，将返回 `404`。

---

## 更新模板

编辑尚未批准的模板。只有状态为 `draft` 或 `rejected` 的模板可以编辑。提供 `name`、`body`、`language` 和 `variables` 的任意组合 —— 仅会更改您发送的字段。

`PUT /whatsapp-templates/{templateId}`

> 编辑**不会**将模板重新提交以供审核。之后请使用提交端点。

**cURL**

```bash
curl -X PUT "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "body": "Hi {{first_name}}, here is an update for you.",
    "variables": ["first_name"]
  }'
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
  {
    method: "PUT",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      body: "Hi {{first_name}}, here is an update for you.",
      variables: ["first_name"],
    }),
  }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.put(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "body": "Hi {{first_name}}, here is an update for you.",
        "variables": ["first_name"],
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template_id": "template_abc123"
}
```

尝试编辑已处于 `approved`（或以其他方式不可编辑）状态的模板、不发送任何字段或发送无效值，将返回 `400` 以及解释性的 `error`。

---

## 提交模板以供审核

提交 `draft` 或 `rejected` 模板以供审核。在不需要外部审核的渠道上的模板会立即获得批准；所有其他模板都会发送至 WhatsApp，返回的 `status`（通常为 `received` 或 `pending`）将存储在模板中。

`POST /whatsapp-templates/{templateId}/submit`

> **跟进模板**在提交前必须声明并使用其所需的变量：一个名字占位符，以及一个用于智能跟进的个人语境占位符。

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/submit" \
  -H "X-API-Key: YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/submit",
  { method: "POST", headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/submit",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template_id": "template_abc123",
  "status": "pending",
  "sid": "HXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
}
```

---

## 检查审核状态

一个用于轮询模板当前状态的轻量级端点。该状态从存储的记录中读取，记录会在后台定期刷新，因此最近的批准或拒绝可能需要一点时间才能显示。

`GET /whatsapp-templates/{templateId}/status`

**cURL**

```bash
curl "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/status" \
  -H "X-API-Key: YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/status",
  { headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/status",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template_id": "template_abc123",
  "name": "welcome_message",
  "status": "approved",
  "sid": "HXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX",
  "rejection_reason": null,
  "date_updated": "2026-06-02T08:30:00.000Z"
}
```

---

## 删除模板

从您的账户中删除模板记录。

`DELETE /whatsapp-templates/{templateId}`

::: warning
**重要提示：** 在托管连接上，仅会删除存储的记录——WhatsApp 已经批准的内容可能仍会在消息服务提供商处注册。在独立运行 WhatsApp Business 账户的账户上，该模板也会从该账户中删除。无论哪种情况，如果某个营销活动仍在使用此模板，请**在**删除前将该营销活动重新指向另一个模板，否则依赖该模板的发送任务将会失败。
:::


**cURL**

```bash
curl -X DELETE "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123" \
  -H "X-API-Key: YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
  { method: "DELETE", headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.delete(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "template_id": "template_abc123",
  "note": "The template record was removed from your account. Content already approved by WhatsApp may remain registered with the messaging provider."
}
```

---

## 向联系人发送模板

即使在没有开启对话的情况下，也可以向联系人发送已批准的模板——这会重新开启聊天会话。您可以通过 `contactId` 或 `phoneNumber` 指定联系人，并通过 `whatsappTemplateId` 或 `templateName` 选择模板。

`POST /whatsapp-templates/send`

| 字段 | 必填 | 说明 |
|---|---|---|
| `contactId` | 二选一 | 联系人的 ID。 |
| `phoneNumber` | 二选一 | 联系人的电话号码（带国家/地区代码，无空格）。如有需要，将进行查找或创建。 |
| `whatsappTemplateId` | 二选一 | 模板的 ID。 |
| `templateName` | 二选一 | 模板名称，如应用中所示。 |
| `firstName` | 否 | 用于填充新创建的联系人。 |
| `lastName` | 否 | 用于填充新创建的联系人。 |
| `email` | 否 | 用于填充新创建的联系人。 |
| `variables` | 否 | 模板变量的显式值，以变量名为键，例如 `{ "code": "482913" }`。此处提供的值优先于联系人字段中该变量的值；您未指定的变量仍将按如下所述从联系人信息中填充。这就是您如何将一次性代码传递给身份验证模板的方法。 |

模板正文支持高级变量替换：

- **基本变量：** `{{first_name}}`, `{{email}}`, `{{company}}`
- **默认值：** 如果字段为空，`{{first_name|there}}` 将显示 `there`
- **转换：** `{{company|uppercase}}`, `{{name|lowercase}}`, `{{name|capitalize}}`
- **组合：** `{{company|Your Company|uppercase}}`

> **额度：** 发送模板会消耗额度。具体费用取决于收件人所在的国家/地区以及模板的类别。

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/send?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "contactId": "contact123",
    "whatsappTemplateId": "template_abc123"
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/send", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    contactId: "contact123",
    whatsappTemplateId: "template_abc123",
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/send",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "contactId": "contact123",
        "whatsappTemplateId": "template_abc123",
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "WhatsApp template message sent successfully"
}
```

如果请求中同时缺少联系人标识符和两个模板标识符，则会返回 `400`。如果您的账户缺少发送所需的通信凭据，响应将为 `403`。

---

## 创建或更新营销活动的实时模板

这是针对营销活动开场模板的第二组端点，通过路径而非正文中的 `campaign_id` 进行作用域限定。对于已经上线的营销活动，请使用这些端点：与上文的 [创建模板](#create-a-template) 不同，在此处进行更新还会重新提交营销活动的后续草稿以供审核，从而确保开场模板及其后续内容保持同步。

`POST /whatsapp-templates/campaign/{campaignId}` 用于创建营销活动的开场模板。`PUT /whatsapp-templates/campaign/{campaignId}` 用于编辑模板——营销活动必须已经拥有模板，否则将返回 `400`。

| 字段 | 必填 | 描述 |
|---|---|---|
| `name` | 是 | 模板名称。 |
| `language` | 是 | 语言代码，例如 `en`、`es`、`de`、`pt_BR`、`zh_CN`。 |
| `body` | 是 | 消息文本，最多 1024 个字符。 |
| `variables` | 是 | 正文中使用的变量名称的有序列表。如果模板未使用任何变量，请传递一个空数组。 |

**cURL** (创建)

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/campaign/campaign123?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "welcome_message",
    "language": "en",
    "body": "Hi {{first_name}}, thanks for reaching out!",
    "variables": ["first_name"]
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/campaign/campaign123", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    name: "welcome_message",
    language: "en",
    body: "Hi {{first_name}}, thanks for reaching out!",
    variables: ["first_name"],
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/campaign/campaign123",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "name": "welcome_message",
        "language": "en",
        "body": "Hi {{first_name}}, thanks for reaching out!",
        "variables": ["first_name"],
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "campaign_status": "pending",
  "template_sid": "HXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX",
  "message": "WhatsApp template created and campaign updated successfully."
}
```

若要进行编辑，请将方法更改为 `PUT` 并使用相同的字段——这会重新提交开场模板（以及 WhatsApp API 营销活动中的后续草稿）以供审核。

如果营销活动不属于您的账户，将返回 `404`；如果营销活动属于您无权访问的其他账户，将返回 `403`。编辑没有现有模板的营销活动将返回 `400`。

---

## 向现有联系人发送模板

这是上文 [向联系人发送模板](#send-a-template-to-a-contact) 的一种更简单的路径作用域替代方案：模板和联系人都必须已经存在——系统不会按名称查找或即时创建任何内容。

`POST /whatsapp-templates/{templateId}/send-to-contact`

| 字段 | 必填 | 描述 |
|---|---|---|
| `contactId` | 是 | 联系人 ID。必须属于您的账户。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/send-to-contact?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "contactId": "contact123" }'
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/send-to-contact",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ contactId: "contact123" }),
  }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/send-to-contact",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"contactId": "contact123"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "WhatsApp template message sent successfully"
}
```

> **积分：** 发送消息会消耗积分，定价方式与上述端点相同。如果 `contactId` 缺失或不在您的账户中，将返回 `403`；如果 `templateId` 不存在，将返回 `404`。

---

## 批量发送模板

在单次调用中向多个联系人发送一个模板，并提供可在提交前展示的费用预览。

### 先估算费用

返回发送成本，按目标国家/地区细分，且不会实际发送任何内容或扣除额度。模板定价按目标国家/地区计算，因此必须在服务器端针对真实联系人进行计算，而不是在客户端进行估算。

`POST /whatsapp-templates/{templateId}/estimate-bulk-cost`

| 字段 | 必填 | 说明 |
|---|---|---|
| `contactIds` | 是 | 需要定价的联系人，每次调用最多 500 个。重复项仅计算一次。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/estimate-bulk-cost?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "contactIds": ["contact123", "contact456"] }'
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/estimate-bulk-cost",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ contactIds: ["contact123", "contact456"] }),
  }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/estimate-bulk-cost",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"contactIds": ["contact123", "contact456"]},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": {
    "countries": [
      {
        "countryCode": "1",
        "name": "United States",
        "iso": "US",
        "flag": "🇺🇸",
        "contactCount": 120,
        "costPerContact": 0.5,
        "subtotal": 60.0
      }
    ],
    "totalContacts": 120,
    "totalTemplateCost": 60.0,
    "templateCategory": "marketing",
    "skippedContacts": 2
  }
}
```

`skippedContacts` 计算的是缺失的、不属于您的或没有电话号码的 ID 数量——估算仅涵盖其余部分，因此非零值意味着实际发送量将少于您选择的联系人数量。

### 发送批次

将模板发送给列表中的每个联系人，解析每个联系人的智能变量，并按发送次数扣除额度。

`POST /whatsapp-templates/{templateId}/bulk-send`

| 字段 | 必填 | 说明 |
|---|---|---|
| `contactIds` | 是 | 发送目标联系人，每次调用最多 5000 个。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/bulk-send?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "contactIds": ["contact123", "contact456"] }'
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/bulk-send",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ contactIds: ["contact123", "contact456"] }),
  }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/template_abc123/bulk-send",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"contactIds": ["contact123", "contact456"]},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": { "sent": 118, "failed": 2, "total": 120 }
}
```

失败的联系人（未找到、不属于您的账户或发送错误）将被跳过并计入 `failed`，而不会停止整个批次。空的 `contactIds`、单次发送超过 5000 个 ID（估算为 500 个）或缺失 `templateId` 将返回 `400`。

---

## 重试失败的消息

用于重新发送失败消息的两个端点，无需创建新的消息记录或再次消耗额度。

`POST /whatsapp-templates/messages/{contactId}/{messageId}/retry-template` 专门用于重试失败的模板消息——如果失败的消息本身不包含内容，它会从营销活动中重新解析模板内容。只有状态为 `failed` 且类型为 `template` 的消息才能通过这种方式重试。

`POST /whatsapp-templates/messages/{contactId}/{messageId}/retry` 与渠道无关，适用于任何失败的非模板消息（例如 WhatsApp Web），并根据消息的渠道分发到正确的发送路径。它接受状态 `failed`、`failed_connection`、`limit_exceeded` 或 `queued_retry`。

这两个端点都不需要请求正文。

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/messages/contact123/msg_abc789/retry-template?apiKey=YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/messages/contact123/msg_abc789/retry-template",
  { method: "POST", headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/messages/contact123/msg_abc789/retry-template",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "Message retry initiated successfully"
}
```

对于与渠道无关的版本，请将路径切换为 `.../msg_abc789/retry`。如果消息的状态不符合重试条件，或者（在模板端点上）不是模板消息，则返回 `400`。如果联系人或消息缺失，则返回 `404`。

---

## WhatsApp Business 个人资料

管理在 WhatsApp 上向联系人显示的 WhatsApp Business 个人资料（关于、地址、描述、电子邮件、网站、业务类别和徽标）。适用于托管连接以及运行自身 WhatsApp Business 账户的账户。

### 保存个人资料

`PUT /whatsapp-templates/profile`

| 字段 | 必填 | 描述 |
|---|---|---|
| `phoneNumber` | 是 | 此个人资料所属的 WhatsApp 号码。必须在您的账户上已连接。 |
| `about` | 否 | 个人资料上显示的简短“关于”文本。 |
| `address` | 否 | 商家地址。 |
| `description` | 否 | 较长的商家描述。 |
| `email` | 否 | 个人资料上显示的联系电子邮件。 |
| `websites` | 否 | 网站 URL 数组。每个 URL 都必须是有效的 URL。 |
| `vertical` | 否 | 业务类别，例如 `Retail` 或 `Professional Services`。 |
| `profilePictureHandle` | 否 | 由下方的图片上传端点返回的句柄，用于设置个人资料照片。 |

**cURL**

```bash
curl -X PUT "https://api.youraiconnector.com/v1/whatsapp-templates/profile?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "phoneNumber": "+31612345678",
    "about": "We reply within a few hours",
    "email": "support@example.com",
    "websites": ["https://example.com"]
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/profile", {
  method: "PUT",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    phoneNumber: "+31612345678",
    about: "We reply within a few hours",
    email: "support@example.com",
    websites: ["https://example.com"],
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.put(
    "https://api.youraiconnector.com/v1/whatsapp-templates/profile",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "phoneNumber": "+31612345678",
        "about": "We reply within a few hours",
        "email": "support@example.com",
        "websites": ["https://example.com"],
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "WhatsApp Business profile updated successfully"
}
```

缺少 `phoneNumber`、无效的网站 URL 或未在您的账户上连接的 `phoneNumber` 将返回 `400` 或 `404`。

### 上传个人资料图片

从您提供的 URL 下载图片并将其上传到 WhatsApp，然后返回一个句柄。将该句柄作为上述保存个人资料调用中的 `profilePictureHandle` 传递，以将其设置为照片——此端点仅上传图片，不会自行设置它。

`POST /whatsapp-templates/profile/picture`

| 字段 | 必填 | 描述 |
|---|---|---|
| `phoneNumber` | 是 | 此个人资料所属的 WhatsApp 号码。 |
| `fileUrl` | 是 | 可公开访问的待上传图片 URL。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/whatsapp-templates/profile/picture?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "phoneNumber": "+31612345678",
    "fileUrl": "https://example.com/logo.png"
  }'
```

**JavaScript**

```javascript
const res = await fetch("https://api.youraiconnector.com/v1/whatsapp-templates/profile/picture", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    phoneNumber: "+31612345678",
    fileUrl: "https://example.com/logo.png",
  }),
});
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/whatsapp-templates/profile/picture",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "phoneNumber": "+31612345678",
        "fileUrl": "https://example.com/logo.png",
    },
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "1234567890123456"
}
```

`data` 是已上传图片的句柄。缺少 `phoneNumber` 或 `fileUrl`，或者存档中没有 WhatsApp 访问令牌的 `phoneNumber` 将返回 `400`；无法访问或无效的 `fileUrl` 将返回描述下载失败原因的错误。

---

## 检查发送方状态

轮询（并刷新）已连接的 WhatsApp 号码在消息服务提供商处的实时发送状态。在您依赖某个号码之前，这对于确认该号码确实能够发送消息非常有用。

`GET /whatsapp-templates/sender-status/{phoneNumber}`

**cURL**

```bash
curl "https://api.youraiconnector.com/v1/whatsapp-templates/sender-status/+31612345678" \
  -H "X-API-Key: YOUR_API_KEY"
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/whatsapp-templates/sender-status/+31612345678",
  { headers: { "X-API-Key": "YOUR_API_KEY" } }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/whatsapp-templates/sender-status/+31612345678",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()
```

**响应**

```json
{
  "success": true,
  "data": "ONLINE"
}
```

`data` 为 `ONLINE`（正常发送）、`PENDING`（仍在验证中）或 `DELETED`（提供商不再识别此发送方——请重新连接该号码）之一。存档中没有 WhatsApp 业务信息的 `phoneNumber` 将返回 `404`。

---

## 使用 AI 生成跟进模板

该平台可以根据营销活动的说明和目标，为您编写 WhatsApp 跟进模板（即当对话静默时发送的提醒消息）。目前有一个在后台运行的作业端点，以及三个为兼容现有集成而保留的旧版端点。所有这些操作都会消耗 AI 点数。

### 启动生成作业

`POST /campaigns/{campaignId}/template-generation`

| 字段 | 必填 | 说明 |
|---|---|---|
| `type` | 否 | `all`（默认值）编写整套跟进内容。`cold_only` 仅为从未回复的联系人编写消息。 |

**cURL**

```bash
curl -X POST "https://api.youraiconnector.com/v1/campaigns/campaign_abc123/template-generation?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "type": "all" }'
```

**JavaScript**

```javascript
const res = await fetch(
  "https://api.youraiconnector.com/v1/campaigns/campaign_abc123/template-generation",
  {
    method: "POST",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({ type: "all" }),
  }
);
const data = await res.json();
```

**Python**

```python
import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/campaigns/campaign_abc123/template-generation",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"type": "all"},
)
data = res.json()
```

**响应** (`202`)

```json
{ "success": true, "campaign_id": "campaign_abc123", "type": "all" }
```

该调用在作业进入队列后立即返回。请读取营销活动（`GET /campaigns/{campaignId}`，参见 [营销活动 API](campaigns.md)）并观察其 `template_generation_status` 对象，直到作业完成：

| 字段 | 说明 |
|---|---|
| `status` | 作业运行时为 `processing`，完成后为 `completed` 或 `failed`。 |
| `progress` | 0 到 100。 |
| `current_template`, `total_templates` | 已编写的模板数量，以及作业总共将编写的模板数量（外呼或组合营销活动为 11 个，否则为 9 个）。 |
| `error` | `failed` 作业停止的原因，例如点数不足。 |
| `started_at`, `completed_at` | 作业开始和结束的时间。 |

生成的模板会像其他模板一样存放在营销活动中，因此它们会出现在 [列出模板](#list-templates) 中，并且在发送前仍需经过 WhatsApp 审核。`400` 表示 `type` 不是 `all` 或 `cold_only`；`404` 表示营销活动不存在或属于其他账户。

代理（Agents）拥有此调用的对应版本 `POST /agents/{agentId}/template-generation`，它为代理编写跟进内容，通常在调用期间即可完成 —— 参见 AI 代理 API 中的 [生成跟进消息](agents.md#generate-follow-up-messages)。

### 旧版生成端点

三个较早的端点执行相同的工作，保留它们是为了确保现有集成能够继续运行。新代码应使用上述的作业端点。

| 端点 | 功能 |
|---|---|
| `POST /whatsapp-templates/campaign/{campaignId}/generate-async` | 在后台启动营销活动的跟进生成，并返回 `202` 和 `{ "success": true, "data": { "result": "success", "message": "..." } }`。点数会预先扣除（自带 AI 密钥的账户除外），营销活动的 `template_generation_status` 会按上述方式报告进度。 |
| `POST /whatsapp-templates/campaign/{campaignId}/generate-followups` | 在调用期间生成所有九个跟进模板 —— 适用于在自动跟进功能出现之前创建的营销活动，或需要重新编写模板的营销活动 —— 并返回 `200`，其中包含 `templatesGenerated` 和 `data`。 |
| `POST /whatsapp-templates/agent/{agentId}/generate-followups` | 与代理相关的同步生成。响应增加了 `agent_id`、`campaign_id` 和 `target`：当模板被写入代理的营销活动时为 `"campaign"`；当代理没有营销活动且模板存储在代理本身时为 `"agent"`（包含 `campaign_id: null`）。代理缺失或属于其他账户时返回 `404`。 |

这三个端点都需要账户开启自动跟进功能且拥有足够的点数 —— `400` 会指出缺失的内容 —— 且针对营销活动的两个端点在营销活动属于其他账户时会返回 `403`。

---

## 模板 API 错误

模板端点返回标准的错误封装：

```json
{
  "success": false,
  "error": "Template not found"
}
```

在这些端点上收到 `404` 通常意味着未找到资源——要么是资源不存在，要么是它属于另一个账户。少数端点（活动范围内的创建/更新，以及发送给现有联系人）在活动或联系人属于他人而非不存在时，会返回 `403`。一些端点还包含一个反映 HTTP 状态的 `error_code` 字段。所有端点都可能返回的共享代码——`400`、`401`、`403`（您的套餐不包含 API 访问权限）、`429`（速率限制）和 `500`——以及重试指南，请参阅 [错误与分页](errors-and-pagination.md)。

---

## 后续步骤

- [身份验证](authentication.md) — 请求身份验证的四种方式。
- [错误与速率限制](errors-and-pagination.md) — 状态码及 300 次请求/分钟的限制。
- [营销活动 API](campaigns.md) — 管理模板所关联的营销活动。
