[relaybell docs › Sending › AI writing](https://relaybell.com/docs/ai-writing) · [All docs as Markdown](https://relaybell.com/docs.md) · [Index for AI assistants](https://relaybell.com/llms.txt)

# AI writing

> Write it for me, Improve my text and AI wording per person: where the AI runs, what it sees, what it is never allowed to write, daily limits, and the /api/v1/ai routes.

relaybell can write the words of a notification for you. It is AI: normally a small language model that runs **on relaybell's own servers**, not a third-party AI service (see [where it runs](https://relaybell.com/docs/ai-writing#privacy)). There are three ways to use it:

- **Write it for me** (the composer): say in a sentence what the notification is about, pick a tone and, if you like, a product or article from your [catalog](https://relaybell.com/docs/personalization#catalog). You get 3 versions to choose from, then edit the one you pick.
- **Improve my text** (the composer): 3 clearer, more clickable rewrites of the title and message you wrote.
- **AI tailors the wording for each person** (a send, an automation or a journey message): each person gets a version written around their interests, and a share of people get your original so you can compare. See [AI-written wording](https://relaybell.com/docs/personalization#ai-wording).

The AI can get things wrong. Read what it wrote before you send it.

## What the AI sees {#privacy}

Only what it needs to write the copy:

- your title, message and the sentence you typed,
- your website's name and language,
- the product or article you picked (its name, price, category and summary), and
- for wording per person, **interest names** such as "Running shoes" or "Camping".

It never receives who a person is: no email, name, user id, location, browser, history or anything else from a subscriber profile, and the text isn't used to train anything.

**Where it runs.** The composer's privacy line and `GET /api/v1/ai/status` (`provider`) say which applies to relaybell right now:

- `relaybell` — the model runs on relaybell's own servers. Nothing above leaves relaybell's servers.
- `anthropic` — relaybell is set to use Anthropic's AI (Claude). The items above are sent to Anthropic to write the copy; still nothing about your subscribers.
- `external` — another AI service. The items above are sent to it; still nothing about your subscribers.

## What it is never allowed to write {#rules}

Every version is checked before you see it, or before anyone receives it. A version that breaks a rule is thrown away; if none is left, you get a plain message, and a send goes out with your original words.

- **No made-up facts.** Every number, percentage, price and amount must already be in your text, your sentence or the product, written in digits or in words ("ten percent", "three days"). Sales, discounts, "% off", "save $20", coupon codes and anything "free" need the same kind of offer in your own title, message or sentence (or the product's price); the same goes for deadlines ("last chance", "ends tonight") and low-stock claims ("selling fast", "only 3 left") — "back in stock" doesn't allow "selling fast". Days, months, seasons and holidays ("summer", "Diwali") must be in what you gave. If you want "20% off this week only" in it, say so.
- **No links, email addresses or phone numbers.** The link is the notification's own `url`.
- **Merge tags stay as you wrote them.** The AI never sees your tags: each one is swapped for a neutral mark before it writes and put back after. Every version keeps each tag of your copy exactly as written (`{name|there}`, [recommendation tags](https://relaybell.com/docs/personalization#rec-tags) like `{rec.title}`) and as often as you used it; a version that drops, repeats or changes one, or writes a name or `[there]` in its place, is thrown away.
- **No shouting or spam.** No words in capitals you didn't use, no "!!", "act now", "click here" or "you've won", at most 2 emojis.
- **Plain, clean text** within 65 characters for the title and 140 for the message, in the language you wrote in — or, when that isn't clear, your website's language (the most common language of your subscribers).

## Limits {#limits}

- **500 AI versions per website per day** (UTC). Each "Write it for me" or "Improve my text" counts as one; for wording per person, each version written counts as one. The same request again within 7 days reuses the earlier answer and isn't counted. When the day's allowance is used up, the buttons say so, and sends go out with your original words until midnight UTC.
- **30 writing requests an hour** from one IP address ([rate limits](https://relaybell.com/docs/errors-limits#rate-limits)).
- Writing takes a few seconds (about 10–20 s for 3 versions). When the AI is busy with other requests or slow, you get a "try again in a minute" message instead of a long wait.

## API {#api}

The same routes the composer uses. Session or an API key with the `send` scope ([scopes](https://relaybell.com/docs/authentication#scopes)).

**GET** `/api/v1/ai/status` — is AI writing available for this website right now?

```json
{ "available": true, "provider": "relaybell", "dailyLimit": 500, "usedToday": 12 }
```

`provider` is `relaybell` (the model on relaybell's own servers), `anthropic` (Anthropic's AI), `external` (another AI service) or `off` — see [where it runs](https://relaybell.com/docs/ai-writing#privacy).

**POST** `/api/v1/ai/write` — 3 versions from a short description.

```bash
curl -X POST https://relaybell.com/api/v1/ai/write \
  -H "Authorization: Bearer rb_live_xxxxx" -H "Content-Type: application/json" \
  -d '{ "brief": "Our autumn jackets are in. 20% off this week only.", "tone": "friendly" }'
```

```json
{
  "options": [
    { "title": "Autumn jackets are here", "body": "20% off every jacket this week only. Find your new favourite." },
    { "title": "New jackets, 20% off", "body": "Warm, light and ready for chilly mornings. This week only." },
    { "title": "Your autumn layer is in", "body": "Take 20% off our new jackets this week." }
  ],
  "provider": "relaybell",
  "model": "qwen2.5:3b"
}
```

| Field | Description |
| --- | --- |
| `brief` | What the notification is about, up to 300 characters. Put in any price, discount or date you want used. Needed unless `item` is given. |
| `tone` | `friendly` (default), `urgent`, `playful` or `professional`. |
| `item` | Optional, what it is about: `{ "productId": "…" }` for an item in your [catalog](https://relaybell.com/docs/catalog-api), or `{ "title", "price", "category", "summary", "type" }` given directly. |
| `language` | Optional BCP-47 language of the copy, e.g. `es` or `hi-IN`. Left out: the language of your `brief` when it's clear, else your website's language (the most common language of your subscribers), else English. |
| `variant` | Optional whole number, 0–1000. The same request is answered from a 7-day cache (and not counted again); send another number for new versions, as the composer's **Write 3 more** does. |

Fewer than 3 versions come back when some didn't pass the [checks](https://relaybell.com/docs/ai-writing#rules).

**POST** `/api/v1/ai/suggest` — "Improve my text": `{ "title", "body", "tone"?, "language"?, "variant"? }` → `{ "ai": true, "suggestions": [{ "title", "body" }], "provider", "model" }` with up to 3 rewrites (`language` left out: the language of your title and message, else your website's). When AI writing is switched off for relaybell it still answers `200` with `"ai": false` and 3 simple rewordings of your own text.

**Errors** — each with a plain `message` you can show as it is:

| Status | Code | When |
| --- | --- | --- |
| `400` | `brief_required` | `/write` with no `brief` and no `item`; `/suggest` with no title or message. |
| `400` | `invalid_brief`, `invalid_tone`, `invalid_item` | A `brief` over 300 characters or not text; another tone; an `item` of the wrong shape. |
| `404` | `item_not_found` | `item.productId` isn't in this website's catalog. |
| `429` | `ai_limit` | The website used today's AI allowance (500 by default). It starts again at midnight UTC. |
| `429` | `rate_limited` | More than 30 writing requests in an hour from one IP address. |
| `503` | `ai_unavailable` | No usable answer this time. `reason`: `off` (AI writing isn't switched on), `busy` (other requests are using the AI; try again in a minute), `paused` (the AI failed several times in a row and is skipped for half a minute; try again in a minute), `timeout` (it took too long), `unsafe` (nothing passed the [checks](https://relaybell.com/docs/ai-writing#rules); reword the brief), `error` (the AI isn't answering). |
