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

# Senders

> Understanding senders, smart routing, and automatic fallback in Zavu

# Senders

A **Sender** is a messaging profile that represents "who" is sending the message. Senders can be configured with multiple channels — SMS, WhatsApp, Email, Telegram, Instagram, and Voice — and Zavu intelligently routes messages through them.

## What is a Sender?

Think of a sender as your messaging identity. It contains:

* **Phone number** — used for SMS, WhatsApp, and [Voice](/guides/sending-messages/easy-way) messaging
* **WhatsApp Business Account** — for [WhatsApp](/guides/whatsapp/overview) messaging (rich media, templates, interactive messages)
* **Email domain** — for [transactional email](/guides/sending-messages/email) via Amazon SES
* **Telegram bot** — for [Telegram](/guides/telegram/overview) messaging
* **Instagram Business Account** — for Instagram direct messaging
* **Webhooks** — real-time notifications for [inbound messages and delivery updates](/guides/receiving-messages/webhooks)
* **Allowed destinations** — countries you can send to

<CodeGroup>
  ```json Example Sender theme={null}
  {
    "id": "sender_12345",
    "name": "Primary Sender",
    "phoneNumber": "+13125551212",
    "isDefault": true,
    "webhook": {
      "url": "https://your-app.com/webhooks",
      "events": ["message.inbound", "message.delivered"],
      "active": true
    },
    "whatsapp": {
      "phoneNumberId": "123456789",
      "displayPhoneNumber": "+13125551212"
    },
    "emailReceivingEnabled": false,
    "createdAt": "2025-01-15T10:00:00Z",
    "updatedAt": "2025-01-15T10:00:00Z"
  }
  ```
</CodeGroup>

## Channels

Zavu supports 6 messaging channels. Each has different requirements and routing behavior:

| Channel       | Identifier           | Smart Routing | Fallback | Setup Guide                                           |
| ------------- | -------------------- | ------------- | -------- | ----------------------------------------------------- |
| **SMS**       | Phone number (E.164) | Yes           | Yes      | [SMS Guide](/guides/sending-messages/sms)             |
| **WhatsApp**  | Phone number (E.164) | Yes           | Yes      | [WhatsApp Guide](/guides/whatsapp/overview)           |
| **Email**     | Email address        | No            | No       | [Email Guide](/guides/sending-messages/email)         |
| **Telegram**  | Telegram chat ID     | No            | No       | [Telegram Guide](/guides/telegram/overview)           |
| **Instagram** | Instagram-scoped ID  | No            | No       | —                                                     |
| **Voice**     | Phone number (E.164) | No            | No       | [Sending Messages](/guides/sending-messages/easy-way) |

<Note>
  **Smart routing and automatic fallback only apply to SMS and WhatsApp.** Email, Telegram, Instagram, and Voice are standalone channels that must be explicitly specified with the `channel` parameter.
</Note>

## Default Sender

Every project has a **default sender**. When you send a message without specifying a sender, Zavu uses the default.

```bash theme={null}
# Uses default sender automatically
curl -X POST https://api.zavu.dev/v1/messages \
  -H "Authorization: Bearer zv_live_xxx" \
  -d '{"to": "+14155551234", "text": "Hello!"}'
```

To use a specific sender, include the `Zavu-Sender` header:

```bash theme={null}
curl -X POST https://api.zavu.dev/v1/messages \
  -H "Authorization: Bearer zv_live_xxx" \
  -H "Zavu-Sender: sender_67890" \
  -d '{"to": "+14155551234", "text": "Hello!"}'
```

## Smart Routing

Zavu's smart routing system automatically selects the **optimal channel** for each message based on cost, deliverability, and contact history. Smart routing applies only to SMS and WhatsApp.

<Note>
  **Smart routing only applies to outbound messages.** When replying to an inbound message, Zavu always responds on the **same channel** the contact used.
</Note>

### When Smart Routing Applies

| Message Type                        | Routing Behavior                      |
| ----------------------------------- | ------------------------------------- |
| **Outbound** (you initiate)         | Smart routing selects optimal channel |
| **Inbound reply** (direct response) | Always use the contact's channel      |

### How It Works

For outbound messages, the router checks if the contact has previously messaged you. If they have, this affects channel availability:

```
Has contact messaged via WhatsApp in last 24h?
      |
   +--+--+
   |     |
  Yes   No
   |     |
   v     v
WhatsApp    WhatsApp only
available   with template
(preferred)
```

Since WhatsApp is cheaper than SMS, the router **prefers WhatsApp when the 24-hour window is open**. This means contacts who have messaged you before will typically receive messages via WhatsApp.

### Channel Selection Algorithm

The router evaluates channels in this order:

1. **Filter viable channels**: Remove channels that can't deliver (e.g., WhatsApp without open window)
2. **Sort by cost**: Cheapest channels first
3. **Check success rate**: Channel must have at least 80% success rate (or fewer than 3 attempts for exploration)
4. **Select best option**: First channel meeting all criteria

### Cost Optimization

| Channel  | Approximate Cost |
| -------- | ---------------- |
| WhatsApp | \~\$0.01/message |
| SMS      | \~\$0.05/message |

Smart routing can reduce messaging costs by **up to 80%** by preferring WhatsApp when available.

### WhatsApp 24-Hour Window

WhatsApp has a strict rule: you can only send free-form messages within **24 hours** of the last message received from the contact.

```
Contact sends message ... 24-hour window opens
      |
Within 24h: Send any message type
      |
After 24h: Only template messages allowed
```

<Warning>
  If the 24-hour window is closed and you don't have a [template](/concepts/templates) configured, the smart router will automatically select SMS instead of failing.
</Warning>

### Channel Metrics

Zavu tracks delivery metrics for each [contact](/guides/contacts/overview) and channel:

```json theme={null}
{
  "channelMetrics": {
    "sms": {
      "successCount": 45,
      "failureCount": 2,
      "avgDeliveryTimeMs": 3200,
      "lastSuccessAt": "2025-01-15T10:30:00Z"
    },
    "whatsapp": {
      "successCount": 120,
      "failureCount": 1,
      "avgDeliveryTimeMs": 1100,
      "lastSuccessAt": "2025-01-15T14:22:00Z"
    }
  }
}
```

The router uses these metrics to:

* Avoid channels with low success rates (below 80%)
* Prefer faster channels when speed matters
* Explore new channels (first 3 attempts get a chance regardless of stats)

## Automatic Fallback

When a message fails on one channel, Zavu **automatically retries** on an alternate channel. Fallback works between SMS and WhatsApp only.

### Fallback Flow

```
Send via WhatsApp
      |
      v
  Failed?
      |
   +--+--+
   |     |
  No    Yes
   |     |
   v     v
Done   Wait 5s
         |
         v
   Retry via SMS
         |
         v
     Success?
         |
      +--+--+
      |     |
     Yes   No
      |     |
      v     v
   Done   Mark Failed
```

### Fallback Rules

| Rule                     | Description                                                |
| ------------------------ | ---------------------------------------------------------- |
| Max 2 attempts           | Each message is tried on at most 2 channels                |
| 5-second delay           | Wait 5 seconds before retry to avoid race conditions       |
| No duplicate channels    | Never retry on a channel that already failed               |
| Sender must support both | Fallback only works if sender has both channels configured |

### Enabling/Disabling Fallback

Fallback is **enabled by default**. You can disable it per message by setting `fallbackEnabled: false`:

```json theme={null}
{
  "id": "msg_abc123",
  "status": "delivered",
  "channel": "sms",
  "fallbackEnabled": true
}
```

## Standalone Channels

Email, Telegram, Instagram, and Voice operate independently from smart routing. You must explicitly specify the `channel` parameter when using them.

| Channel       | Key Requirement                    | Docs                                                  |
| ------------- | ---------------------------------- | ----------------------------------------------------- |
| **Email**     | KYC verification + domain setup    | [Email Setup](/guides/email/setup)                    |
| **Telegram**  | Bot token via BotFather            | [Telegram Setup](/guides/telegram/setup)              |
| **Instagram** | Instagram Business Account         | —                                                     |
| **Voice**     | Phone number with voice capability | [Sending Messages](/guides/sending-messages/easy-way) |

These channels don't participate in smart routing or automatic fallback because they use different recipient identifiers and have different delivery semantics than SMS/WhatsApp.

## Rate Limiting

Zavu implements fair [rate limiting](/concepts/rate-limiting) to ensure reliable delivery for all users.

### Limits by Channel

| Channel  | Rate Limit         | Level    |
| -------- | ------------------ | -------- |
| SMS      | 10 messages/second | Global   |
| Email    | 14 messages/second | Global   |
| WhatsApp | 60 messages/second | Per WABA |

### Round-Robin Fairness

When multiple projects are sending messages, Zavu uses **round-robin scheduling** to ensure fairness:

```
Without round-robin:
Project A: 10 messages = A1, A2, A3... A10 (1 second)
Project B: 1 message  = B1 waits 1 second

With round-robin:
A1 (0ms), B1 (100ms), A2 (200ms), A3 (300ms)...
B1 only waits 100ms instead of 1 second
```

This prevents high-volume senders from blocking smaller senders.

<Note>
  Messages are never dropped due to rate limiting. They're queued and sent at the next available slot.
</Note>

## Managing Senders

### List Senders

```bash theme={null}
curl https://api.zavu.dev/v1/senders \
  -H "Authorization: Bearer zv_live_xxx"
```

### Create Sender

```bash theme={null}
curl -X POST https://api.zavu.dev/v1/senders \
  -H "Authorization: Bearer zv_live_xxx" \
  -d '{
    "name": "Marketing Sender",
    "phoneNumber": "+13125559999",
    "setAsDefault": false
  }'
```

### Update Sender

```bash theme={null}
curl -X PATCH https://api.zavu.dev/v1/senders/sender_12345 \
  -H "Authorization: Bearer zv_live_xxx" \
  -d '{
    "name": "Updated Name",
    "setAsDefault": true
  }'
```

## Webhook Configuration

Each sender can have one webhook configured to receive real-time notifications for events like incoming messages and delivery updates. See the [Webhooks guide](/guides/receiving-messages/webhooks) for payload details and security.

### Create Sender with Webhook

```bash theme={null}
curl -X POST https://api.zavu.dev/v1/senders \
  -H "Authorization: Bearer zv_live_xxx" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Support",
    "phoneNumber": "+15551234567",
    "webhookUrl": "https://your-app.com/webhooks",
    "webhookEvents": ["message.inbound", "message.delivered", "message.failed"]
  }'
```

The response includes the webhook secret (only shown once):

```json theme={null}
{
  "id": "sender_12345",
  "name": "Support",
  "webhook": {
    "url": "https://your-app.com/webhooks",
    "events": ["message.inbound", "message.delivered", "message.failed"],
    "secret": "whsec_abc123...",
    "active": true
  }
}
```

### Update Webhook

```bash theme={null}
curl -X PATCH https://api.zavu.dev/v1/senders/sender_12345 \
  -H "Authorization: Bearer zv_live_xxx" \
  -d '{
    "webhookUrl": "https://new-url.com/webhooks",
    "webhookEvents": ["message.inbound"],
    "webhookActive": false
  }'
```

### Regenerate Webhook Secret

If your webhook secret is compromised:

```bash theme={null}
curl -X POST https://api.zavu.dev/v1/senders/sender_12345/webhook/secret \
  -H "Authorization: Bearer zv_live_xxx"
```

### Available Webhook Events

| Event                     | Description                               |
| ------------------------- | ----------------------------------------- |
| `message.queued`          | Message created and queued for sending    |
| `message.sent`            | Message accepted by the provider          |
| `message.delivered`       | Message delivered to recipient            |
| `message.failed`          | Message delivery failed                   |
| `message.inbound`         | Contact sent you a message                |
| `message.unsupported`     | Received an unsupported message type      |
| `conversation.new`        | First message from a new contact          |
| `template.status_changed` | WhatsApp template approval status changed |

<Note>
  For webhook payload structure and signature verification, see the [Webhooks guide](/guides/receiving-messages/webhooks) and [Webhook Security](/guides/receiving-messages/security).
</Note>

## Best Practices

<CardGroup cols={2}>
  <Card title="Configure Multiple Channels" icon="layer-group">
    Set up both SMS and WhatsApp on your sender to enable smart routing and automatic fallback.
  </Card>

  <Card title="Use Templates for Outreach" icon="file-lines">
    When initiating conversations, use [WhatsApp templates](/concepts/templates) to avoid 24-hour window issues.
  </Card>

  <Card title="Monitor Metrics" icon="chart-line">
    Check your [contact](/guides/contacts/overview) metrics to understand channel performance in your region.
  </Card>

  <Card title="Set Allowed Destinations" icon="globe">
    Restrict senders to specific countries to control costs and compliance.
  </Card>
</CardGroup>

## Next Steps

<CardGroup cols={2}>
  <Card title="Adding Channels" icon="plus" href="/guides/senders/adding-channels">
    Connect SMS, WhatsApp, Email, Telegram, and more to your sender
  </Card>

  <Card title="Phone Numbers" icon="phone" href="/concepts/phone-numbers">
    Purchase and manage phone numbers for SMS and voice
  </Card>

  <Card title="Templates" icon="file-code" href="/concepts/templates">
    Create WhatsApp templates for outbound messaging
  </Card>

  <Card title="Smart Routing Guide" icon="route" href="/guides/sending-messages/smart-routing">
    Deep dive into routing configuration
  </Card>
</CardGroup>
