# A WhatsApp API for your personal number

> Circles gives your scripts, n8n workflows and own agents the WhatsApp chats you choose, as JSON over HTTP with a key. It works with your existing personal number, with no WhatsApp Business account and no bridge to run. It reads by default and writes only where you allow.

**Circles is an HTTP API for a personal WhatsApp number:** link your number as a linked device, make a key, and call `https://app.usecircles.app/api/v1/agent` with `Authorization: Bearer circ_...`, described in OpenAPI 3.1 at `https://app.usecircles.app/api/openapi.json`. It reads the chats you opened, voice notes as text, and, on Pro, sends, replies and reacts only where you allowed sending. Circles is free for 2 chats, or $29 a month on Pro (₪99 in Israel) with 14 days free, as of October 2026.

Source: https://usecircles.app/en/whatsapp-api-personal-number · Updated 2026-10-27

## The API at a glance

|  | Circles HTTP API |
| --- | --- |
| Base URL | `https://app.usecircles.app/api/v1/agent` |
| Auth | `Authorization: Bearer `: a key made on the Agents page (`circ_...`) or an MCP client's OAuth token. No cookies. |
| Spec | OpenAPI 3.1 at `https://app.usecircles.app/api/openapi.json`; a readable reference at `https://app.usecircles.app/api` |
| Format | JSON. Times in UTC, as milliseconds (`at`) and ISO 8601 (`at_iso`) |
| Paging | Follow `pagination.next_url` until it is null; `has_more` says if there is more. Each page re-checks what the key may reach. |
| Same as MCP | The nine operations, the same chats, the same permissions and cap |
| Only in the API | Quoted replies, emoji reactions, write receipts, finding or starting a chat by number |
| Your number | Your personal WhatsApp, as a linked device. No WhatsApp Business, no second number. |

## From signup to the first call

1. **Link your WhatsApp in Circles**: Start your trial, then link your number as a linked device: a code typed on your phone, or a QR on your computer. Same number, same WhatsApp on your phone. History arrives in about 5 to 15 minutes, and you can connect your agent meanwhile.
2. **Make a key**: On Circles' Agents page, choose *New token*, pick the agent (or Other), choose *API with a key*, what it allows, and how long it works: no limit, 90 days or a year.
3. **Hand it over in two messages**: Circles gives you instructions without the key, then the key on its own, so the key goes only into the agent's secrets. For a script or n8n, paste the key straight into your credentials.
4. **Make the first call**: `GET https://app.usecircles.app/api/v1/agent/allowed_chats` with `Authorization: Bearer circ_...`. That list is the whole world the key can reach.

Two reads, with the key in an environment variable:

```
curl -s "https://app.usecircles.app/api/v1/agent/allowed_chats" \
  -H "Authorization: Bearer $CIRCLES_KEY"

curl -s "https://app.usecircles.app/api/v1/agent/catch_up?since=2026-10-26T00:00:00Z" \
  -H "Authorization: Bearer $CIRCLES_KEY"
```

## Endpoints

All under `/api/v1/agent` unless shown. The OpenAPI document has every parameter and response.

| Endpoint | What it does |
| --- | --- |
| `GET allowed_chats` | The chats open to this key and what it may do in each. The whole world. |
| `GET activity` | Which chats moved since a time: counts, last time, last sender, no text |
| `GET catch_up` | Messages since a time, one chat or all, senders by name, voice notes with their transcript. `kind=voice\|audio\|recording` filters. |
| `GET search` | Text search in one chat or all, including what was said in voice notes |
| `GET people` | Who you talk with across open chats, and where |
| `GET group_members` | Members of one open group, by name, admins marked, never numbers |
| `GET documents` | Every PDF, Word file and sheet sent in open chats, with its state |
| `POST get_media` | One attachment; asks your phone to re-upload an older one if needed |
| `GET media/{ref}/status`, `content`, `view` | An attachment's state, its bytes, or the file for showing in a browser |
| `GET chats/{chat_ref}`, `messages/{message_ref}` | Details, with the complete `actions` you may take there |
| `POST chats/{chat_ref}/messages` | Send text, a file, or a file with a caption |
| `POST messages/{message_ref}/replies` | A native quoted reply. API only. |
| `POST messages/{message_ref}/reactions` | An emoji reaction. API only. |
| `GET writes/{submission_ref}` | The read-only receipt of a write |
| `GET recipients?to=` | Find a chat by number or exact saved name, or start one, when your number allows starting chats |
| `POST /api/v1/connect/exchange` | Swaps a one-time connect code for a key (how Instinct connects). The one call with no Authorization. |

## Sending, replies and reactions

A chat's or a message's details carry its `actions`: complete requests with method, URL, headers and body. Perform one as given, add your `Authorization` header, and fill in only the text, file or emoji.

- **Idempotent.** Each write carries a submission reference Circles issued, bound to its target. Reusing it within 24 hours cannot send again or take another slot of the daily cap.
- **Never retried.** If the answer is `delivery_unknown`, check the receipt at `writes/{submission_ref}` and the chat before you decide to send again. A message that may have left is never sent twice by Circles.
- **Only where allowed.** Sends, replies and reactions all need the key's send permission and a chat open for sending, and all count against the same daily cap. A refusal says what is missing and what is still allowed.
- **Quotes fail closed.** A reply that cannot be quoted is refused.
- **Not supported:** voting in polls, removing a reaction, quoting a message that is not text.

Sending a file: add it to the body the send action gives you. A JPEG, PNG or WebP arrives as a photo, an MP4 as a video, anything else as a document under its filename.

```
"text": "Signed copy attached",
"file": {
  "mime": "application/pdf",
  "data_base64": "<the file, base64, up to about 3 MB>",
  "filename": "nda.pdf"
}
```

## Voice notes and files

A voice note (`kind: voice`) or audio file (`kind: audio`) carries its `transcript`, transcribed automatically in Hebrew and English, so you read what was said without fetching the audio. `transcript_state` says `pending` while it is still being written.

Other attachments come as an announcement: filename, type, size and a `status_url`, plus `content_url` once Circles holds the file. Circles serves the bytes, and your code reads the PDF or image. Files older than about 25 days at linking come from your phone on request: POST to `acquire_url`, and the phone, if it is online, re-uploads the file.

## Limits

| Limit | Value |
| --- | --- |
| Text message | Up to 65,536 characters |
| Caption | Up to 4,096 characters |
| File to send | About 3 MB |
| File to fetch | Up to 50 MB each |
| Daily send cap | Per number, across all agents together: default 5; 5, 10, 20 or no cap; counted per UTC day |
| Write idempotency | 24 hours per submission reference |
| Key lifetime | No limit (default), 90 days or a year; revocable at once |
| One-time connect code | Single use, one hour, ten tries a minute per address |

More on limits and errors: [the API and MCP documentation](https://usecircles.app/en/api-mcp-docs#limits).

## n8n, scripts, and agents you built

- **n8n:** an HTTP Request node with a header credential, `Authorization: Bearer circ_...`. This reaches your personal chats. n8n's own WhatsApp node is for WhatsApp Business accounts.
- **Scripts:** a morning digest of three groups, an export of every document sent in a project chat, a weekly count of who asked you what. Plain GETs, JSON back.
- **Your own agent:** anything that calls HTTP. The instructions Circles gives with the key tell an agent how to read, page and act, and that a send is never retried.
- **Dots** connects this way too: instructions first, then its key in a message of its own.

Prefer MCP? The same chats and permissions are at `https://app.usecircles.app/api/mcp`: [the WhatsApp MCP hub](https://usecircles.app/en/whatsapp-mcp).

## Questions and answers

### Does personal WhatsApp have an API?

WhatsApp offers an official API only for WhatsApp Business. Circles gives your personal number an HTTP API by linking it as a linked device and serving only the chats you open, with a key.

### Is this the WhatsApp Business API?

No. The Business API is Meta's official way for businesses to message customers, on a business number. Circles works with your personal number and your existing chats. [The difference in detail](https://usecircles.app/en/compare/whatsapp-business-api).

### Can I use it with n8n?

Yes. Use an HTTP Request node with the header `Authorization: Bearer circ_...` and the base URL `https://app.usecircles.app/api/v1/agent`. n8n's built-in WhatsApp node is for Business accounts.

### Will a retry send the same message twice?

No. Each write carries a submission reference, and reusing it within 24 hours cannot send again or use another cap slot. If delivery is uncertain, Circles says so and never retries on its own.

### Can WhatsApp disconnect my number for this?

Linked-device access by an unofficial client is outside WhatsApp's terms, and no one can promise a device is never logged out. Circles reads by default, caps sends, never broadcasts, and connects each customer through a dedicated IP address shared with no other customer.

### What does it cost?

The API is in every Circles plan: Free, Starter at $9.90 a month, and Pro at $29 a month (₪99 in Israel) with 14 days free. Sending through the API is on Pro.

## Keep reading

- [Personal number vs the Business API](https://usecircles.app/en/compare/whatsapp-business-api): Who each one is for.
- [API and MCP docs](https://usecircles.app/en/api-mcp-docs): For agents: tools, answers, limits, auth, API.
- [What a key can reach](https://usecircles.app/en/security): Per-chat permissions, the cap, the activity log.

---

14 days free. Link your number, pick the chats, then connect Instinct with one tap or Claude, ChatGPT and Codex with one address. Start: https://usecircles.app/start?lang=en
