> ## Documentation Index
> Fetch the complete documentation index at: https://docs.vambe.me/llms.txt
> Use this file to discover all available pages before exploring further.

# Send a template message

> Learn how to send WhatsApp template messages via Vambe API for notifications, confirmations, and marketing campaigns.

## 🚀 What you'll build

You'll send your first WhatsApp template message using the Vambe API with the correct 3-step flow to gather required IDs.

<Tip>
  Template messages allow you to reach customers outside the 24-hour window and
  send structured, pre-approved content for notifications and marketing.
</Tip>

***

## Prerequisites

Before sending template messages, ensure you have:

* ✅ [Connected WhatsApp Business API](/docs/connect-whatsapp-api)
* ✅ [Created and approved templates](/docs/create-template)
* ✅ Valid Vambe API key from [developers page](https://app.vambeai.com/developers)
* ✅ Customer phone numbers (must have opted in to receive messages)

<Warning>
  **Important:** Only send template messages to customers who have explicitly
  opted in. Sending unsolicited messages violates WhatsApp's policies and can
  result in account suspension.
</Warning>

***

## Complete API Flow for Sending Templates

To send a template message, you need to make 3 API calls in sequence to get the required IDs:

<Steps>
  <Step title="Get Channel Information">
    First, retrieve your channel details:

    ```bash theme={null}
    curl -X GET \
      -H "x-api-key: YOUR_API_KEY" \
      https://api.vambe.me/api/public/channels/whatsapp
    ```

    **Sample Response:**

    ```json theme={null}
    {
      "phone_number": "56211111111",
      "client_id": "339e9487-8168-4e14-b1d8-3dce22d07760",
      "id": 1951,
      "name": "Test"
    }
    ```

    <Tip>
      This endpoint retrieves the channel configuration by type. Use `whatsapp`, `instagram`, `web-whatsapp`, or `playground` as channel types. Save the `phone_number` and `client_id` for the template call.
    </Tip>
  </Step>

  <Step title="Get Pipeline and Stage IDs">
    Retrieve your pipeline configuration to get stage IDs:

    ```bash theme={null}
    curl -X GET \
      -H "x-api-key: YOUR_API_KEY" \
      https://api.vambe.me/api/public/pipeline
    ```

    **Sample Response:**

    ```json theme={null}
    [
      {
        "id": "6c9804e2-0b8d-4df1-98f7-7e5be7f69ddb",
        "name": "Support Iris",
        "description": "Este embudo califica leads que ten",
        "stages": [
          {
            "id": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
            "name": "Inicial",
            "description": "En esta etapa la IA de Vambe i"
          },
          {
            "id": "3690b160-3c79-45f2-b88f-b640d96a36aa",
            "name": "Asistencia Humana",
            "description": "Si es que en cualquier punto d"
          }
        ]
      }
    ]
    ```

    <Warning>
      **Save the stage ID** where you want to send the message. You'll need this `stageId` parameter for the template call.
    </Warning>
  </Step>

  <Step title="Get Template ID">
    Find your approved template ID:

    ```bash theme={null}
    curl -X GET \
      -H "x-api-key: YOUR_API_KEY" \
      https://api.vambe.me/api/public/templates
    ```

    **Look for your template name and copy its ID for the final call.**
  </Step>

  <Step title="Send the Template Message">
    Now send your template using the collected IDs:

    ```bash theme={null}
    curl -X POST \
      -H "x-api-key: YOUR_API_KEY" \
      -H "Content-Type: application/json" \
      -d '{
        "contactName": "John Doe",
        "variables": ["John Doe", "ORD-12345", "89.99"],
        "meta_data": {},
        "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
        "toPhoneNumber": "+1234567890"
      }' \
      https://api.vambe.me/api/public/whatsapp/message/send/template/{templateId}
    ```

    <Info>
      **Required fields based on Vambe API:**

      * `contactName`: Customer name
      * `variables`: Array of values for template variables (in order)
      * `stageId`: Stage ID from pipeline response
      * `toPhoneNumber`: Destination number
      * `meta_data`: Additional metadata object (can be empty)
      * `agent_id`: (Optional) Agent ID to assign to the conversation
    </Info>
  </Step>

  <Step title="Handle the Response">
    Process the API response to confirm delivery:

    ```json theme={null}
    {
      "success": true,
      "message_id": "wamid.HBgMNTU1MjM...",
      "status": "sent",
      "timestamp": "2025-01-15T10:30:00Z"
    }
    ```

    **Response codes:**

    * `201`: Message sent successfully
    * `400`: Bad request (check required fields)
    * `401`: Unauthorized (verify API key)
  </Step>
</Steps>

***

## Vambe Template Examples

### Simple Template (No Variables)

<CodeGroup>
  ```bash Welcome Message theme={null}
  curl -X POST \
    -H "x-api-key: YOUR_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "contactName": "John Doe",
      "variables": [],
      "meta_data": {},
      "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
      "toPhoneNumber": "+1234567890"
    }' \
    https://api.vambe.me/api/public/whatsapp/message/send/template/welcome_message_id
  ```

  ```javascript JavaScript theme={null}
  const response = await fetch(
    'https://api.vambe.me/api/public/whatsapp/message/send/template/welcome_message_id',
    {
      method: 'POST',
      headers: {
        'x-api-key': process.env.VAMBE_API_KEY,
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        contactName: 'John Doe',
        variables: [],
        meta_data: {},
        stageId: '72ba8482-5c1c-4bed-8a6e-16fdb1495776',
        toPhoneNumber: '+1234567890',
      }),
    },
  );
  ```

  ```python Python theme={null}
  import requests

  response = requests.post(
    'https://api.vambe.me/api/public/whatsapp/message/send/template/welcome_message_id',
    headers={
      'x-api-key': os.environ['VAMBE_API_KEY'],
      'Content-Type': 'application/json'
    },
    json={
      "contactName": "John Doe",
      "variables": [],
      "meta_data": {},
      "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
      "toPhoneNumber": "+1234567890"
    }
  )
  ```
</CodeGroup>

### Template with Variables

<CodeGroup>
  ```bash Order Confirmation theme={null}
  curl -X POST \
    -H "x-api-key: YOUR_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "contactName": "Sarah Johnson",
      "variables": ["Sarah Johnson", "ORD-12345", "$159.99", "December 28, 2024"],
      "meta_data": {
        "order_id": "ORD-12345",
        "customer_type": "premium",
        "payment_method": "credit_card"
      },
      "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
      "toPhoneNumber": "+1234567890"
    }' \
    https://api.vambe.me/api/public/whatsapp/message/send/template/order_confirmation_id
  ```

  ```javascript Appointment Reminder theme={null}
  const response = await fetch(
    'https://api.vambe.me/api/public/whatsapp/message/send/template/appointment_reminder_id',
    {
      method: 'POST',
      headers: {
        'x-api-key': process.env.VAMBE_API_KEY,
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        contactName: 'Dr. Smith',
        variables: [
          'Dr. Smith',
          'January 15, 2024',
          '2:30 PM',
          'Downtown Medical Center',
        ],
        meta_data: {
          appointment_id: 'APT-789',
          department: 'cardiology',
          patient_id: 'PAT-456',
        },
        stageId: '3690b160-3c79-45f2-b88f-b640d96a36aa',
        toPhoneNumber: '+1234567890',
      }),
    },
  );
  ```

  ```python Payment Reminder theme={null}
  import requests

  response = requests.post(
    'https://api.vambe.me/api/public/whatsapp/message/send/template/payment_reminder_id',
    headers={
      'x-api-key': os.environ['VAMBE_API_KEY'],
      'Content-Type': 'application/json'
    },
    json={
      "contactName": "Mike Wilson",
      "variables": ["Mike Wilson", "INV-2024-001", "$250.00", "January 20, 2024"],
      "meta_data": {
        "invoice_id": "INV-2024-001",
        "payment_method": "bank_transfer",
        "due_date": "2024-01-20"
      },
      "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
      "toPhoneNumber": "+1987654321"
    }
  )
  ```
</CodeGroup>

### Carousel Template

Carousel templates allow you to send multiple product cards with images, descriptions, and action buttons in a single message.

<Note>
  The `from-phone-number` query parameter specifies which WhatsApp Business number to send from. This is useful when you have multiple phone numbers connected to your account.
</Note>

<CodeGroup>
  ```bash Product Carousel theme={null}
  curl -X POST \
    -H "x-api-key: YOUR_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "variables": ["Customer Name", "Store Name"],
      "meta_data": {},
      "carouselVariables": [
        {
          "cardIndex": 0,
          "headerVariable": "https://example.com/product1.jpg",
          "bodyVariables": ["15000"],
          "buttonVariables": ["https://store.com/product1"]
        },
        {
          "cardIndex": 1,
          "headerVariable": "https://example.com/product2.jpg",
          "bodyVariables": ["16000"],
          "buttonVariables": ["https://store.com/product2"]
        },
        {
          "cardIndex": 2,
          "headerVariable": "https://example.com/product3.jpg",
          "bodyVariables": ["13000"],
          "buttonVariables": ["https://store.com/product3"]
        }
      ]
    }' \
    "https://api.vambe.me/api/public/whatsapp/message/send/+1234567890/template/{templateId}?from-phone-number=+1987654321"
  ```

  ```javascript Product Carousel theme={null}
  const response = await fetch(
    'https://api.vambe.me/api/public/whatsapp/message/send/+1234567890/template/{templateId}?from-phone-number=+1987654321',
    {
      method: 'POST',
      headers: {
        'x-api-key': process.env.VAMBE_API_KEY,
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        variables: ['Customer Name', 'Store Name'],
        meta_data: {},
        carouselVariables: [
          {
            cardIndex: 0,
            headerVariable: 'https://example.com/product1.jpg',
            bodyVariables: ['15000'],
            buttonVariables: ['https://store.com/product1'],
          },
          {
            cardIndex: 1,
            headerVariable: 'https://example.com/product2.jpg',
            bodyVariables: ['16000'],
            buttonVariables: ['https://store.com/product2'],
          },
          {
            cardIndex: 2,
            headerVariable: 'https://example.com/product3.jpg',
            bodyVariables: ['13000'],
            buttonVariables: ['https://store.com/product3'],
          },
        ],
      }),
    },
  );
  ```

  ```python Product Carousel theme={null}
  import requests
  import os

  response = requests.post(
    'https://api.vambe.me/api/public/whatsapp/message/send/+1234567890/template/{templateId}?from-phone-number=+1987654321',
    headers={
      'x-api-key': os.environ['VAMBE_API_KEY'],
      'Content-Type': 'application/json'
    },
    json={
      "variables": ["Customer Name", "Store Name"],
      "meta_data": {},
      "carouselVariables": [
        {
          "cardIndex": 0,
          "headerVariable": "https://example.com/product1.jpg",
          "bodyVariables": ["15000"],
          "buttonVariables": ["https://store.com/product1"]
        },
        {
          "cardIndex": 1,
          "headerVariable": "https://example.com/product2.jpg",
          "bodyVariables": ["16000"],
          "buttonVariables": ["https://store.com/product2"]
        },
        {
          "cardIndex": 2,
          "headerVariable": "https://example.com/product3.jpg",
          "bodyVariables": ["13000"],
          "buttonVariables": ["https://store.com/product3"]
        }
      ]
    }
  )
  ```
</CodeGroup>

***

## Understanding Vambe Template Format

Based on the `SendTemplateDto` schema, here are the required and optional fields:

| Field               | Type      | Required | Description                                       |
| ------------------- | --------- | -------- | ------------------------------------------------- |
| `contactName`       | string    | Optional | Customer's name for personalization               |
| `variables`         | string\[] | Required | Array of values for template variables in order   |
| `meta_data`         | object    | Optional | Additional metadata (key-value pairs)             |
| `stageId`           | string    | Optional | Pipeline stage ID where to send the message       |
| `toPhoneNumber`     | string    | Optional | Destination phone number                          |
| `carouselVariables` | object\[] | Optional | Variables for carousel template cards (see below) |

<Note>
  **Variable Order:** The `variables` array must match the order of variables in your template. If your template has `{{1}}` for name and `{{2}}` for order number, then `variables: ["John Doe", "ORD-123"]`.
</Note>

### Carousel Card Variables

When sending carousel templates, each card in the `carouselVariables` array has the following structure:

| Field             | Type      | Required | Description                                            |
| ----------------- | --------- | -------- | ------------------------------------------------------ |
| `cardIndex`       | number    | Required | Zero-based index of the carousel card (0, 1, 2, ...)   |
| `headerVariable`  | string    | Required | URL for the card's header image or video               |
| `bodyVariables`   | string\[] | Optional | Array of variables for the card's body text            |
| `buttonVariables` | string\[] | Optional | Array of variables for the card's buttons (e.g., URLs) |

<Tip>
  **Carousel Templates** allow you to send multiple cards with images/videos in a single message. Each card can have its own header media, body text variables, and button actions. Cards are indexed starting from 0.
</Tip>

***

## Alternative Endpoint: Body-based V2

There's an alternative endpoint that accepts all parameters in the request body, including the phone number and template name:

**Endpoint:** `POST /api/public/whatsapp/message/send`

### V2 Request Body Schema

| Field               | Type      | Required | Description                                           |
| ------------------- | --------- | -------- | ----------------------------------------------------- |
| `phone`             | string    | Required | Phone number to send the template to                  |
| `template_name`     | string    | Required | Name of the template to send                          |
| `contact_name`      | string    | Optional | Customer's name for personalization                   |
| `variables`         | string\[] | Required | Array of values for template variables in order       |
| `meta_data`         | object    | Optional | Additional metadata (key-value pairs)                 |
| `stage_id`          | string    | Optional | Pipeline stage ID where to send the message           |
| `agent_id`          | string    | Optional | Agent ID to assign to the conversation                |
| `from_phone_number` | string    | Optional | Phone number to send the template from                |
| `carouselVariables` | object\[] | Optional | Variables for carousel template cards (same as above) |

### V2 Carousel Template Example

<CodeGroup>
  ```bash V2 Product Carousel theme={null}
  curl -X POST \
    -H "x-api-key: YOUR_API_KEY" \
    -H "Content-Type: application/json" \
    -d '{
      "phone": "+1234567890",
      "template_name": "product_carousel",
      "contact_name": "John Doe",
      "variables": ["John Doe", "Store Name"],
      "meta_data": {},
      "from_phone_number": "+1987654321",
      "carouselVariables": [
        {
          "cardIndex": 0,
          "headerVariable": "https://example.com/product1.jpg",
          "bodyVariables": ["15000"],
          "buttonVariables": ["https://store.com/product1"]
        },
        {
          "cardIndex": 1,
          "headerVariable": "https://example.com/product2.jpg",
          "bodyVariables": ["16000"],
          "buttonVariables": ["https://store.com/product2"]
        }
      ]
    }' \
    https://api.vambe.me/api/public/whatsapp/message/send
  ```

  ```javascript V2 Product Carousel theme={null}
  const response = await fetch(
    'https://api.vambe.me/api/public/whatsapp/message/send',
    {
      method: 'POST',
      headers: {
        'x-api-key': process.env.VAMBE_API_KEY,
        'Content-Type': 'application/json',
      },
      body: JSON.stringify({
        phone: '+1234567890',
        template_name: 'product_carousel',
        contact_name: 'John Doe',
        variables: ['John Doe', 'Store Name'],
        meta_data: {},
        from_phone_number: '+1987654321',
        carouselVariables: [
          {
            cardIndex: 0,
            headerVariable: 'https://example.com/product1.jpg',
            bodyVariables: ['15000'],
            buttonVariables: ['https://store.com/product1'],
          },
          {
            cardIndex: 1,
            headerVariable: 'https://example.com/product2.jpg',
            bodyVariables: ['16000'],
            buttonVariables: ['https://store.com/product2'],
          },
        ],
      }),
    },
  );
  ```

  ```python V2 Product Carousel theme={null}
  import requests
  import os

  response = requests.post(
    'https://api.vambe.me/api/public/whatsapp/message/send',
    headers={
      'x-api-key': os.environ['VAMBE_API_KEY'],
      'Content-Type': 'application/json'
    },
    json={
      "phone": "+1234567890",
      "template_name": "product_carousel",
      "contact_name": "John Doe",
      "variables": ["John Doe", "Store Name"],
      "meta_data": {},
      "from_phone_number": "+1987654321",
      "carouselVariables": [
        {
          "cardIndex": 0,
          "headerVariable": "https://example.com/product1.jpg",
          "bodyVariables": ["15000"],
          "buttonVariables": ["https://store.com/product1"]
        },
        {
          "cardIndex": 1,
          "headerVariable": "https://example.com/product2.jpg",
          "bodyVariables": ["16000"],
          "buttonVariables": ["https://store.com/product2"]
        }
      ]
    }
  )
  ```
</CodeGroup>

<Note>
  The V2 endpoint uses `template_name` instead of `templateId` in the URL path, and uses snake\_case for field names (`contact_name`, `stage_id`, `from_phone_number`) instead of camelCase.
</Note>

***

## Advanced Use Cases

### Bulk Template Sending

Send templates to multiple customers efficiently:

<CodeGroup>
  ```javascript Bulk Send theme={null}
  const customers = [
    { name: "John Doe", phone: "+1234567890", orderId: "ORD-001" },
    { name: "Jane Smith", phone: "+1987654321", orderId: "ORD-002" },
    { name: "Bob Johnson", phone: "+1555123456", orderId: "ORD-003" }
  ];

  const results = await Promise.allSettled(
  customers.map(async (customer) => {
  const response = await fetch(
  'https://api.vambe.me/api/public/whatsapp/message/send/template/order_confirmation_id',
  {
  method: 'POST',
  headers: {
  'x-api-key': process.env.VAMBE_API_KEY,
  'Content-Type': 'application/json'
  },
  body: JSON.stringify({
  contactName: customer.name,
  variables: [customer.name, customer.orderId],
  meta_data: { order_id: customer.orderId },
  stageId: '72ba8482-5c1c-4bed-8a6e-16fdb1495776',
  toPhoneNumber: customer.phone
  })
  }
  );
  return { customer: customer.name, result: await response.json() };
  })
  );

  console.log('Bulk send results:', results);

  ```

  ```python Batch Processing theme={null}
  import requests
  import time
  from concurrent.futures import ThreadPoolExecutor

  def send_template_message(customer):
      try:
          response = requests.post(
              'https://api.vambe.me/api/public/whatsapp/message/send/template/order_confirmation_id',
              headers={
                  'x-api-key': os.environ['VAMBE_API_KEY'],
                  'Content-Type': 'application/json'
              },
              json={
                  "contactName": customer['name'],
                  "variables": [customer['name'], customer['order_id']],
                  "meta_data": {"order_id": customer['order_id']},
                  "stageId": "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
                  "toPhoneNumber": customer['phone']
              }
          )
          return {"customer": customer['name'], "success": response.status_code == 201}
      except Exception as e:
          return {"customer": customer['name'], "error": str(e)}

  # Rate-limited batch sending
  customers = [
      {"phone": "+1234567890", "name": "John Doe", "order_id": "ORD-001"},
      {"phone": "+1987654321", "name": "Jane Smith", "order_id": "ORD-002"}
  ]

  with ThreadPoolExecutor(max_workers=5) as executor:
      results = list(executor.map(send_template_message, customers))

  print("Batch results:", results)
  ```
</CodeGroup>

***

## Error Handling

### Common Error Responses

<AccordionGroup>
  <Accordion title="Template Not Found (404)" icon="exclamation">
    ```json theme={null}
    {
      "error": "Template not found",
      "code": "TEMPLATE_NOT_FOUND",
      "details": "Template ID 'invalid_template_id' does not exist or is not approved"
    }
    ```

    **Solutions:**

    * Verify template ID is correct
    * Check template approval status in Vambe dashboard
    * Ensure template exists for your account
  </Accordion>

  <Accordion title="Invalid Stage ID (400)" icon="ban">
    ```json theme={null}
    {
      "error": "Invalid stage ID",
      "code": "INVALID_STAGE_ID",
      "details": "Stage ID does not exist in your pipelines"
    }
    ```

    **Solutions:**

    * Check stage ID from pipeline API response
    * Verify stage belongs to your account
    * Ensure pipeline is active and configured
  </Accordion>

  <Accordion title="Invalid Phone Number (400)" icon="phone">
    ```json theme={null}
    {
      "error": "Invalid recipient",
      "code": "INVALID_PHONE_NUMBER",
      "details": "Phone number must include country code"
    }
    ```

    **Solutions:**

    * Include country code (e.g., +1 for US)
    * Validate phone number format
    * Ensure number is active on WhatsApp
  </Accordion>

  <Accordion title="Rate Limit Exceeded (429)" icon="clock">
    ```json theme={null}
    {
      "error": "Rate limit exceeded",
      "code": "RATE_LIMIT_EXCEEDED",
      "retry_after": 3600
    }
    ```

    **Solutions:**

    * Implement exponential backoff retry logic
    * Check your messaging tier limits
    * Spread messages over longer time periods
  </Accordion>
</AccordionGroup>

### Robust Error Handling Example

<CodeGroup>
  ```javascript Error Handling theme={null}
  async function sendVambeTemplate(contactName, variables, stageId, toPhoneNumber, templateId) {
    try {
      const response = await fetch(
        `https://api.vambe.me/api/public/whatsapp/message/send/template/${templateId}`,
        {
          method: 'POST',
          headers: {
            'x-api-key': process.env.VAMBE_API_KEY,
            'Content-Type': 'application/json'
          },
          body: JSON.stringify({
            contactName,
            variables,
            meta_data: {},
            stageId,
            toPhoneNumber
          })
        }
      );

      if (!response.ok) {
        const error = await response.json();
        throw new Error(`API Error: ${error.code} - ${error.details}`);
      }

      const result = await response.json();
      console.log('Message sent successfully:', result.message_id);
      return result;

    } catch (error) {
      console.error('Failed to send template message:', error.message);

      // Handle specific error cases
      if (error.message.includes('RATE_LIMIT_EXCEEDED')) {
        console.log('Rate limit hit, retrying in 1 hour...');
        // Implement retry logic
      } else if (error.message.includes('TEMPLATE_NOT_FOUND')) {
        console.log('Template needs to be created or approved');
      }

      throw error;
    }

  }

  // Usage with error handling
  try {
  await sendVambeTemplate(
  "John Doe",
  ["John Doe", "ORD-12345"],
  "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
  "+1234567890",
  "order_confirmation_template_id"
  );
  } catch (error) {
  console.error('Template message failed:', error);
  }

  ```

  ```python Error Handling theme={null}
  import requests
  import time
  from typing import List, Dict

  def send_vambe_template(
      contact_name: str,
      variables: List[str],
      stage_id: str,
      to_phone: str,
      template_id: str
  ) -> Dict:
      url = f"https://api.vambe.me/api/public/whatsapp/message/send/template/{template_id}"

      payload = {
          "contactName": contact_name,
          "variables": variables,
          "meta_data": {},
          "stageId": stage_id,
          "toPhoneNumber": to_phone
      }

      headers = {
          'x-api-key': os.environ['VAMBE_API_KEY'],
          'Content-Type': 'application/json'
      }

      try:
          response = requests.post(url, json=payload, headers=headers)

          if response.status_code == 429:  # Rate limit
              retry_after = response.headers.get('Retry-After', 3600)
              print(f"Rate limited. Retrying after {retry_after} seconds")
              time.sleep(int(retry_after))
              return send_vambe_template(contact_name, variables, stage_id, to_phone, template_id)

          response.raise_for_status()
          result = response.json()
          print(f"Message sent successfully: {result.get('message_id')}")
          return result

      except requests.exceptions.HTTPError as e:
          error_data = e.response.json() if e.response.content else {}
          error_code = error_data.get('code', 'UNKNOWN_ERROR')
          error_details = error_data.get('details', str(e))

          print(f"HTTP Error {e.response.status_code}: {error_code} - {error_details}")

          if error_code == 'TEMPLATE_NOT_FOUND':
              print("Check if template exists and is approved")
          elif error_code == 'INVALID_STAGE_ID':
              print("Verify stage ID from pipeline API")

          raise

      except requests.exceptions.RequestException as e:
          print(f"Request failed: {e}")
          raise

  # Usage
  try:
      send_vambe_template(
          "Jane Smith",
          ["Jane Smith", "ORD-67890"],
          "72ba8482-5c1c-4bed-8a6e-16fdb1495776",
          "+1234567890",
          "order_confirmation_template_id"
      )
  except Exception as e:
      print(f"Failed to send template: {e}")
  ```
</CodeGroup>

***

## Best Practices

<CardGroup cols={2}>
  <Card title="Message Timing" icon="clock">
    * **Respect time zones** - Send during business hours
    * **Consider urgency** - Use appropriate delivery timing
    * **Batch wisely** - Spread bulk sends over time
    * **Avoid peak hours** - Prevent rate limiting
  </Card>

  <Card title="Content Optimization" icon="thumbs-up">
    * **Personalize content** - Use customer data effectively - **Keep variables
      relevant** - Don't include unnecessary data - **Test thoroughly** - Verify all
      variable combinations - **Monitor performance** - Track delivery and
      engagement
  </Card>

  <Card title="Compliance" icon="shield">
    * **Verify opt-ins** - Only message consenting customers - **Honor opt-outs**
    * Respect unsubscribe requests - **Follow policies** - Adhere to WhatsApp
      guidelines - **Document consent** - Keep records of permissions
  </Card>

  <Card title="Technical Excellence" icon="code">
    * **Handle errors gracefully** - Implement proper error handling
    * **Use rate limiting** - Respect API limits
    * **Monitor delivery** - Track message status
    * **Log thoroughly** - Maintain audit trails
  </Card>
</CardGroup>

***

## Next Steps

<Check>
  Congratulations! You've successfully sent your first WhatsApp template
  message.
</Check>

Now you can:

<CardGroup cols={2}>
  <Card title="Automate with Pipelines" icon="sitemap" href="/docs/create-pipeline">
    Integrate template messages into automated conversation flows
  </Card>

  <Card title="Track Performance" icon="chart-line" href="/docs/analytics">
    Monitor delivery rates, engagement, and customer responses
  </Card>

  <Card title="Webhook Integration" icon="webhook" href="/docs/webhooks">
    Set up real-time notifications for message status updates
  </Card>

  <Card title="Channel Management" icon="phone" href="/docs/connect-channel">
    Connect additional channels for multi-platform messaging
  </Card>
</CardGroup>

<Info>
  **Remember:** Template messages are powerful tools for customer communication.
  Use them responsibly and always prioritize customer value and consent.
</Info>
