> ## 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.

# Phone Numbers

> Understanding phone number formats, validation, and introspection in Zavu

# Phone Numbers

Phone numbers are the primary identifier for messaging recipients in Zavu. Understanding how phone numbers work will help you build reliable messaging applications.

## E.164 Format

All phone numbers in Zavu must be in **E.164 format**. This is the international standard that ensures phone numbers are globally unique and unambiguous.

### Format Rules

```
+[country code][subscriber number]
```

* Starts with `+` sign
* Country code (1-3 digits)
* Subscriber number (up to 14 digits)
* No spaces, dashes, or parentheses

### Examples

| Country        | E.164 Format     | Notes            |
| -------------- | ---------------- | ---------------- |
| United States  | `+14155551234`   | Country code: 1  |
| United Kingdom | `+447700900123`  | Country code: 44 |
| Chile          | `+56912345678`   | Country code: 56 |
| Germany        | `+4915123456789` | Country code: 49 |

<Warning>
  Always store and send phone numbers in E.164 format. Zavu will reject numbers that don't match this format.
</Warning>

## Phone Number Introspection

Before sending a message, you can validate and get information about a phone number using the introspection endpoint.

<CodeGroup>
  ```typescript TypeScript theme={null}
  const response = await zavu.introspect.phone({
    phoneNumber: "+14155551234"
  });
  ```

  ```python Python theme={null}
  response = zavu.introspect.phone(
      phone_number="+14155551234"
  )
  ```

  ```ruby Ruby theme={null}
  response = zavu.introspect.phone(
    phone_number: "+14155551234"
  )
  ```

  ```go Go theme={null}
  response, err := client.Introspect.Phone(context.TODO(), zavudev.IntrospectPhoneParams{
      PhoneNumber: zavudev.String("+14155551234"),
  })
  ```

  ```php PHP theme={null}
  $response = $client->introspect->phone([
      'phoneNumber' => '+14155551234',
  ]);
  ```

  ```bash cURL theme={null}
  curl -X POST https://api.zavu.dev/v1/introspect/phone \
    -H "Authorization: Bearer zv_live_xxx" \
    -H "Content-Type: application/json" \
    -d '{
      "phoneNumber": "+14155551234"
    }'
  ```
</CodeGroup>

### Response

```json theme={null}
{
  "phoneNumber": "+14155551234",
  "validNumber": true,
  "countryCode": "US",
  "nationalFormat": "(415) 555-1234",
  "lineType": "mobile",
  "carrier": {
    "name": "Verizon Wireless",
    "type": "mobile"
  },
  "availableChannels": ["sms", "whatsapp"]
}
```

### Response Fields

| Field               | Description                                                        |
| ------------------- | ------------------------------------------------------------------ |
| `phoneNumber`       | The E.164 formatted number                                         |
| `validNumber`       | Whether the number is valid                                        |
| `countryCode`       | ISO country code (e.g., "US", "CL")                                |
| `nationalFormat`    | Number in local format                                             |
| `lineType`          | Type of line: `mobile`, `landline`, `voip`, `toll_free`, `unknown` |
| `carrier`           | Carrier information if available                                   |
| `availableChannels` | Channels that can reach this number (based on line type)           |

### Available Channels by Line Type

The `availableChannels` array is determined automatically based on the line type:

| Line Type   | SMS | WhatsApp | Explanation                                                         |
| ----------- | --- | -------- | ------------------------------------------------------------------- |
| `mobile`    | Yes | Yes      | Mobile numbers support all messaging channels                       |
| `voip`      | Yes | No       | VoIP numbers (Google Voice, Skype) can receive SMS but not WhatsApp |
| `toll_free` | Yes | No       | Toll-free numbers support SMS only                                  |
| `landline`  | No  | No       | Landlines cannot receive text messages                              |
| `unknown`   | Yes | No       | When line type is uncertain, we default to SMS only                 |

<Info>
  If `availableChannels` is empty, the number cannot receive any messages. This typically happens with landline numbers.
</Info>

<Tip>
  Use introspection to validate numbers before adding them to your database, or to determine which channels are available for a contact.
</Tip>

## Contacts

When you send a message to a phone number, Zavu automatically creates a **Contact** record. Contacts track:

* **Channel metrics**: Success/failure rates per channel
* **Channel availability**: Which channels can reach this contact
* **Last inbound**: When the contact last messaged you (important for WhatsApp)
* **Preferences**: Default channel preference

### Contact Lifecycle

```
First message sent to +14155551234
         |
         v
Contact automatically created
         |
         v
Delivery callbacks update metrics
         |
         v
Future routing decisions use this data
```

### Retrieving Contact Information

<CodeGroup>
  ```typescript TypeScript theme={null}
  const contact = await zavu.contacts.getByPhone({
    phoneNumber: "+14155551234"
  });
  ```

  ```python Python theme={null}
  contact = zavu.contacts.get_by_phone(
      phone_number="+14155551234"
  )
  ```

  ```ruby Ruby theme={null}
  contact = zavu.contacts.get_by_phone(
    phone_number: "+14155551234"
  )
  ```

  ```go Go theme={null}
  contact, err := client.Contacts.GetByPhone(context.TODO(), "+14155551234")
  ```

  ```php PHP theme={null}
  $contact = $client->contacts->getByPhone('+14155551234');
  ```

  ```bash cURL theme={null}
  curl https://api.zavu.dev/v1/contacts/phone/+14155551234 \
    -H "Authorization: Bearer zv_live_xxx"
  ```
</CodeGroup>

### Contact Response

```json theme={null}
{
  "id": "contact_abc123",
  "phoneNumber": "+14155551234",
  "countryCode": "US",
  "availableChannels": ["sms", "whatsapp"],
  "defaultChannel": "whatsapp",
  "verified": true,
  "metadata": {
    "source": "checkout"
  },
  "createdAt": "2025-01-15T10:30:00Z"
}
```

## Country Detection

Zavu automatically detects the country from the phone number's dial code. This is used for:

* **Routing decisions**: Some channels work better in certain regions
* **Cost optimization**: Channel costs vary by country
* **Compliance**: Ensuring messages comply with local regulations

### Supported Regions

Zavu supports phone numbers from all countries. The country code is extracted from the E.164 number automatically.

## Best Practices

<CardGroup cols={2}>
  <Card title="Validate Early" icon="check">
    Use the introspection API when collecting phone numbers to catch errors early.
  </Card>

  <Card title="Store E.164" icon="database">
    Always store phone numbers in E.164 format in your database.
  </Card>

  <Card title="Handle Line Types" icon="phone">
    Some channels only work with mobile numbers. Check `lineType` if channel selection matters.
  </Card>

  <Card title="Respect Preferences" icon="user">
    Let users set their preferred channel via the contact's `defaultChannel` field.
  </Card>
</CardGroup>

## Next Steps

<CardGroup cols={2}>
  <Card title="Senders" icon="paper-plane" href="/concepts/senders">
    Learn how senders work with phone numbers
  </Card>

  <Card title="Send a Message" icon="message" href="/guides/sending-messages/easy-way">
    Start sending messages to phone numbers
  </Card>
</CardGroup>
