NewAds Insights — see what each Facebook ad costs and the WhatsApp leads it brings. Free on every plan. See Ads Insights →
Lead Pattern

Developers · cURL

Send a WhatsApp message with cURL

The quickest way to try the Lead Pattern WhatsApp API: copy these cURL commands into a terminal, swap in your API key and a test number, and see the real response before you write any code.

Last updated: 6 November 2026

✨ Ask AI about this page:ChatGPT logoChatGPTClaude logoClaudePerplexity logoPerplexity

Quick answer

Create an API key in your Lead Pattern dashboard, then run curl -X POST against https://public.leadpattern.com/v2/whatsapp/message/template (approved template) or https://public.leadpattern.com/whatsapp/message/text (reply within 24 hours) with -H "Authorization: YOUR_API_KEY" — no "Bearer" prefix — and a JSON body. HTTP 201 with type "success" means WhatsApp accepted the message.

API reference

Step by step

Send a WhatsApp message with cURL

1

Get an API key

In your Lead Pattern project dashboard, open API Keys and create a key. A key can call every public API endpoint your plan includes — keep it secret and on your server, never in browser or app code.

2

Set the Authorization header

Send the key as-is in the Authorization header on every request — no "Bearer" prefix — plus Content-Type: application/json. The base URL is https://public.leadpattern.com.

3

Send a template message

To start a conversation, or to message someone whose 24-hour window has closed, POST an approved template to /v2/whatsapp/message/template with named placeholders (or /whatsapp/message/template with positional ones).

4

Send a text message inside the 24-hour window

Once the customer has written to you in the last 24 hours, POST to /whatsapp/message/text with "to" and content.text. Outside the window this returns 403 — send a template instead.

5

Handle the response and errors

A successful send returns 201 with type "success" and a WhatsApp messageId. Errors come back with an HTTP status (400, 401, 402, 403, 404, 409, 422, 429, 500). On 429, wait for the Retry-After header before retrying. The cURL code below does all of this.

1–2 · API key, Authorization header and response helperbash
# 1. Check connectivity (public endpoint, no key needed)
curl https://public.leadpattern.com/health-check

# 2. Keep your key in an environment variable (YOUR_API_KEY, starts with lp_)
export LEADPATTERN_API_KEY="YOUR_API_KEY"

# Every request then sends:
#   Authorization: $LEADPATTERN_API_KEY     <- raw key, NO "Bearer " prefix
#   Content-Type: application/json
3 · Send an approved template (v2, named placeholders)bash
curl -X POST https://public.leadpattern.com/v2/whatsapp/message/template \
  -H "Authorization: $LEADPATTERN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "messages": [
      {
        "to": "+91XXXXXXXXXX",
        "content": {
          "templateName": "order_confirmation",
          "language": "en",
          "templateData": {
            "body": { "placeholders": [ { "name": "Customer" }, { "order_id": "ORD-1234" } ] }
          }
        }
      }
    ]
  }'

# v1 alternative — positional placeholders, matched in order:
curl -X POST https://public.leadpattern.com/whatsapp/message/template \
  -H "Authorization: $LEADPATTERN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"messages":[{"to":"+91XXXXXXXXXX","content":{"templateName":"order_confirmation","language":"en","templateData":{"body":{"placeholders":["Customer","ORD-1234"]}}}}]}'
Success response (201) — templatejson
{
  "type": "success",
  "data": {
    "messages": [
      {
        "status": "SENT",
        "recipient": "91XXXXXXXXXX",
        "messageId": "wamid.abc123"
      }
    ]
  }
}
4 · Send a text message inside the 24-hour windowbash
# Free-form text — only works within 24 hours of the customer's last message.
curl -X POST https://public.leadpattern.com/whatsapp/message/text \
  -H "Authorization: $LEADPATTERN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"to":"+91XXXXXXXXXX","content":{"text":"Hello! How can I help you?","previewUrl":false}}'
Success response (201) — textjson
{
  "type": "success",
  "data": {
    "messageId": "wamid.abc123",
    "status": "sent",
    "recipient": "91XXXXXXXXXX"
  }
}
5 · Handle errors and rate limitsbash
# -i prints the HTTP status line and headers, so you can see 201 / 403 / 429 and Retry-After
curl -i -X POST https://public.leadpattern.com/whatsapp/message/text \
  -H "Authorization: $LEADPATTERN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"to":"+91XXXXXXXXXX","content":{"text":"Test"}}'

# Print only the status code:
curl -s -o /dev/null -w "%{http_code}\n" -X POST https://public.leadpattern.com/whatsapp/message/text \
  -H "Authorization: $LEADPATTERN_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"to":"+91XXXXXXXXXX","content":{"text":"Test"}}'
Error response example (403, window closed)json
{
  "type": "error",
  "code": 403,
  "message": "Cannot send a free-form message. The 24-hour customer service window has expired. You may only send template messages after 24 hours of the last user message."
}

HTTP status codes

What each response means

StatusMeaning (from the API docs)
201Created — the message was accepted by WhatsApp. The response has type "success" and data with the messageId.
400Malformed payload, invalid JSON or a missing required field (e.g. "to" is required). Also returned when the project has not finished WhatsApp onboarding.
401Missing, revoked, inactive or malformed API key.
402Workspace subscription inactive or blocked, or plan quota exceeded.
403IP not in the key's whitelist, plan does not include the feature, project suspended — or, for a free-form message, the 24-hour window has closed.
404The entity, template or recipient does not exist.
409Conflict — the resource already exists or is in the wrong state.
422Validation failed, e.g. the phone number is not valid or the WhatsApp account is unlinked.
429Rate limit exceeded. Wait for the Retry-After header, then retry.
500Unexpected server error.

Default limits per API key: 60 requests a minute and 10 requests in flight at once, plus 300 requests a minute per IP address. The effective limit is the lower of the key's limit and your plan's maximum.

Template v1 or v2?

  • v2 — /v2/whatsapp/message/template (recommended by the docs): body placeholders are named, an array of objects like {"name": "..."}. Supports carousel templates (content.templateData.cards) and an optional scheduledAt (a future ISO date-time) per message to schedule instead of sending now.
  • v1 — /whatsapp/message/template: body placeholders are positional — a flat array of values matched in order to the template's variables. Carousel is not supported on v1.
  • Both take a messages array, so one request can send to several recipients. AUTHENTICATION (OTP) templates use their own endpoint — see the API docs.
  • For a DOCUMENT header, pass templateData.header with type, mediaUrl and filename (e.g. "invoice.pdf") so WhatsApp shows a readable file name.

When you need a template

The WhatsApp 24-hour window, which Meta calls the customer service window, starts when a customer messages your business and resets with every new message from them. While it is open you can send normal replies without approval. Once 24 hours pass with no customer message, you can only send pre-approved templates. The 24-hour window explained →

Questions developers ask

Can I test the API without writing code?+

Yes. Run the cURL commands on this page from any terminal, or use the Try It console on each endpoint page of the API docs.

How do I send a WhatsApp message with cURL?+

Create an API key in your Lead Pattern dashboard, then POST JSON to https://public.leadpattern.com with the key in the Authorization header (no Bearer prefix). Use /v2/whatsapp/message/template for an approved template, or /whatsapp/message/text for a reply inside the 24-hour window.

Why does my text message return 403?+

Most often the customer's 24-hour window has closed — free-form messages are only allowed within 24 hours of the customer's last message. Send an approved template instead. A 403 can also mean the key's IP whitelist blocks your server, or your plan does not include the feature.

What are the API rate limits?+

By default 60 requests a minute and 10 concurrent requests per API key, plus 300 requests a minute per IP address. Going over returns 429 with a Retry-After header. Starter includes 1,000 API calls a month; Growth includes 1,00,000 a month with unlimited API keys.

Which phone number format does the API expect?+

E.164 with the country code, for example +91XXXXXXXXXX for India.

Lead Pattern

Get your API key — free 14-day trial.

Set up the official WhatsApp Business API, create a key and send your first message today.

14-day free trial · No credit card · Free WhatsApp API setup

Ask AI about this page

Get a quick summary of this page from your favourite AI assistant — based only on leadpattern.com. Be one of the first to try it.