REST API Reference¶
Wappa provides a comprehensive REST API for sending WhatsApp messages and managing user state handlers. All endpoints are automatically documented with OpenAPI/Swagger at /docs when running your Wappa application.
API Base URL
All endpoints are prefixed with /api/whatsapp by default. If you're running locally, the base URL would be http://localhost:8000/api/whatsapp.
Authentication¶
WhatsApp API endpoints require proper credentials configured in your Wappa application. These are set when initializing your Wappa instance:
app = Wappa(
whatsapp_token="your_whatsapp_token",
whatsapp_phone_id="your_phone_id",
whatsapp_business_id="your_business_id"
)
Response Format¶
All successful responses follow this pattern:
Error responses include detailed error information:
Text Messages¶
Send Text Message¶
Send a simple text message to a WhatsApp user.
Media Messages¶
Send Image Message¶
Send an image with an optional caption.
AI Context with Description Field
The description field (max 2048 chars) is NOT sent to WhatsApp. It's stored for AI agent context to understand what media was sent to the user. This helps AI assistants provide better conversational experiences.
Field Details: - media_source - Either a URL or WhatsApp media ID - caption - User-visible text (max 1024 chars) - description - AI context only, not sent to WhatsApp (max 2048 chars) - reply_to_message_id - Optional message ID to reply to
Supported formats: JPEG, PNG (max 5MB)
Send Video Message¶
Send a video with an optional caption.
Supported formats: MP4, 3GP (max 16MB) Codec requirements: H.264 video, AAC audio
Send Audio Message¶
Send an audio file or voice message.
No Caption for Audio
Audio messages do not support captions. Use the description field for AI context.
Supported formats: AAC, MP3, MP4, AMR, OGG (max 16MB)
Send Document Message¶
Send a document file with optional caption and filename.
Supported formats: TXT, PDF, DOC, DOCX, XLS, XLSX, PPT, PPTX (max 100MB)
Send Sticker Message¶
Send a sticker to a user.
No Caption for Stickers
Stickers do not support captions. Use the description field for AI context.
Supported formats: WebP only Size limits: Static: 100KB, Animated: 500KB
Interactive Messages¶
Send Interactive Buttons¶
Send a message with up to 3 action buttons.
Limits: Max 3 buttons, button titles max 20 characters
Send Interactive List¶
Send a message with a list of selectable items (up to 10 items).
{
"recipient": "+1234567890",
"body_text": "Select a product category:",
"button_text": "View Options",
"sections": [
{
"title": "Electronics",
"rows": [
{
"row_id": "electronics_phones",
"title": "Phones",
"description": "Latest smartphones"
},
{
"row_id": "electronics_laptops",
"title": "Laptops",
"description": "Business laptops"
}
]
},
{
"title": "Clothing",
"rows": [
{
"row_id": "clothing_mens",
"title": "Men's Wear",
"description": "Men's fashion"
}
]
}
],
"header_text": "Product Catalog", // Optional
"footer_text": "Select to learn more" // Optional
}
Limits: Max 10 items across all sections, max 24 characters per title
Template Messages¶
Send Text Template¶
Send a pre-approved WhatsApp template with text content.
{
"recipient": "+1234567890",
"template_name": "appointment_reminder",
"language_code": "en",
"components": [
{
"type": "body",
"parameters": [
{
"type": "text",
"text": "John Doe"
},
{
"type": "text",
"text": "January 15, 2025"
}
]
}
],
"state_config": {
"state_value": "reschedule_flow",
"ttl_seconds": 3600,
"initial_context": {
"appointment_id": "12345"
}
}
}
Template State Management
Use state_config to automatically assign a state handler after the template is sent. This enables workflow routing when users respond.
Send Media Template¶
Send a template with media header (image, video, or document).
Supported header types: image, video, document
State Handler Management¶
State handlers allow you to route user responses to specific event handlers based on their current state. This is perfect for multi-step workflows and automation.
New Feature
State handler API is message-agnostic - use it after sending ANY message type (text, media, templates, interactive messages).
Set State Handler¶
Assign a state handler to a user for workflow routing.
# Step 1: Send a message (any type)
await client.post(
"http://localhost:8000/api/whatsapp/media/send-image",
json={
"recipient": "+1234567890",
"media_source": "https://example.com/appointment.jpg",
"caption": "Your appointment details"
}
)
# Step 2: Assign state handler via automation
await client.post(
"http://localhost:8000/api/whatsapp/state-handlers/set",
json={
"recipient": "+1234567890",
"handler_config": {
"handler_value": "reschedule_flow",
"ttl_seconds": 3600,
"initial_context": {
"appointment_id": "12345"
}
}
}
)
# Now when user responds, your event dispatcher will route to the handler
Use Cases: - Multi-step workflows - Guide users through forms, surveys, or onboarding - Appointment management - Handle reschedules, cancellations, confirmations - Order processing - Track order status, modifications, and support requests - Automation integration - Route responses after external events or triggers
Parameters: - handler_value - Unique identifier for the state handler (1-100 chars) - ttl_seconds - Time-to-live for the handler state (60-86400 seconds = 1 min to 24 hours) - initial_context - Optional context data for the handler
Cache Key Pattern: api-handler-{handler_value}
Get State Handler¶
Retrieve the current state handler assigned to a user.
{
"success": true,
"recipient": "+1234567890",
"handler_value": "reschedule_flow",
"state": {
"handler_value": "reschedule_flow",
"recipient": "+1234567890",
"assigned_at": "2025-01-12T16:30:00Z",
"expires_at": "2025-01-12T17:30:00Z",
"appointment_id": "12345",
"original_time": "2025-01-15T10:00:00Z",
"max_reschedules": 3
}
}
Delete State Handler¶
Remove a state handler assignment from a user.
Common Patterns¶
Pattern 1: Send Message + Assign Handler¶
Perfect for automation workflows where you need to route user responses.
import httpx
async def send_with_handler(recipient: str, image_url: str):
async with httpx.AsyncClient() as client:
# Step 1: Send message
response = await client.post(
"http://localhost:8000/api/whatsapp/media/send-image",
json={
"recipient": recipient,
"media_source": image_url,
"caption": "Please confirm your appointment",
"description": "Appointment confirmation card with date and time"
}
)
# Step 2: Assign state handler
await client.post(
"http://localhost:8000/api/whatsapp/state-handlers/set",
json={
"recipient": recipient,
"handler_config": {
"handler_value": "appointment_confirmation",
"ttl_seconds": 7200, # 2 hours
"initial_context": {
"appointment_id": "12345",
"can_reschedule": True
}
}
}
)
return response.json()
Pattern 2: Template with Auto State¶
Use template state config for automatic handler assignment.
async def send_reminder_with_state(recipient: str, name: str, date: str):
async with httpx.AsyncClient() as client:
response = await client.post(
"http://localhost:8000/api/whatsapp/templates/send-text",
json={
"recipient": recipient,
"template_name": "appointment_reminder",
"language_code": "en",
"components": [
{
"type": "body",
"parameters": [
{"type": "text", "text": name},
{"type": "text", "text": date}
]
}
],
"state_config": {
"state_value": "reschedule_flow",
"ttl_seconds": 3600,
"initial_context": {
"appointment_id": "12345",
"original_time": date
}
}
}
)
return response.json()
Pattern 3: AI Context with Media¶
Provide rich context for AI agents handling conversations.
async def send_product_with_ai_context(recipient: str, product_id: str):
async with httpx.AsyncClient() as client:
response = await client.post(
"http://localhost:8000/api/whatsapp/media/send-image",
json={
"recipient": recipient,
"media_source": f"https://example.com/products/{product_id}.jpg",
"caption": "Check out this product!",
"description": (
f"Product ID: {product_id}, Winter Collection 2025, "
"Price: $49.99, Available in sizes S-XL, "
"Rating: 4.5/5 stars, Best seller in electronics category"
)
}
)
return response.json()
Error Handling¶
All endpoints return standard HTTP status codes:
| Status Code | Meaning |
|---|---|
200 | Success |
201 | Created (for POST /state-handlers/set) |
400 | Bad Request - Invalid input parameters |
401 | Unauthorized - Invalid WhatsApp credentials |
404 | Not Found - Resource doesn't exist |
429 | Rate Limited - Too many requests |
500 | Internal Server Error - Server-side issue |
Example error response:
Rate Limits¶
WhatsApp Business API has rate limits based on your tier:
- Tier 1: 1,000 messages per day
- Tier 2: 10,000 messages per day
- Tier 3: 100,000 messages per day
- Unlimited: No daily limit
Rate Limiting
Exceeding rate limits will result in 429 Too Many Requests responses. Implement exponential backoff for retries.
Interactive API Documentation¶
Wappa automatically generates interactive API documentation using FastAPI's built-in Swagger UI:
Features: - ✅ Try endpoints directly from the browser - ✅ View request/response schemas - ✅ See all available parameters - ✅ Copy curl commands - ✅ Download OpenAPI spec
Next Steps¶
Sending messages from code? → Use the Messaging API for direct Python integration
Building event handlers? → Check Event Handlers to handle incoming messages
Managing state? → Explore Cache API for state management patterns
Need webhooks? → Reference Webhooks API for webhook data structures
Build powerful conversational experiences with Wappa's REST API! 🚀