# Opt-outs and keywords

When someone texts one of your numbers, Bird reads the message against a catalogue of keywords and acts on it before you see it. A recognised **stop** keyword suppresses your future messages to that person, a **start** keyword releases them again, and **help** answers with your support information. This happens with no setup on your side, because honouring an opt-out is not something a sender should have to opt into.

This guide covers what Bird does by default, how to see it, and how to change it.

## What happens by default

A subscriber texts `STOP` to one of your numbers. Bird:

1. **Recognises it** against the keyword catalogue for that number's country.
2. **Records a suppression** on that exact sender-and-subscriber pair.
3. **Confirms it** by replying with the opt-out message for that country.

From then on, a send from that sender to that subscriber is refused with [`E12077 SMSRecipientSuppressed`](/docs/api/errors/E12077) instead of going out. A `START` ends the suppression and confirms that too, and `HELP` replies without changing anything.

A suppression covers **one sender and one subscriber**, not your whole workspace. Someone who opts out of one of your numbers still hears from the others, which is what lets a customer stop your marketing number and keep getting delivery notifications from your transactional one.

The confirmation is exempt from the suppression it concerns. Bird answers a subscriber who just texted you even when you may no longer message them, because a reply to a message someone just sent is not traffic pushed at them.

## Coverage is per country

Bird's catalogue covers a **subset of countries**, not all of them. Where a country is covered, opt-out, opt-in, and help are answered out of the box. Where it is not, no keyword is recognised, nothing is answered, and **no opt-out is recorded**, so if you send to a country Bird's catalogue does not cover, you are responsible for honouring opt-outs there yourself.

Check what a country has before you rely on it:

```bash
bird sms keyword-rules list --country NL
```

An empty result for a country means no coverage. You can still add `custom` keywords of your own there, but `stop`, `start`, and `help` rules can only be created for a country Bird's catalogue already covers.

## Seeing what applies

`GET /v1/sms/keyword-rules` answers "what happens when someone replies to my numbers". Unfiltered, it returns Bird's whole catalogue alongside any rules you have created; narrow it with `country`, `number`, `operation`, or `scope`:

- `scope=system` browses Bird's catalogue on its own, which is how you read the default a rule of yours has replaced.
- `scope=workspace` returns only your own rules.
- `number=+18005551234` returns the rules that apply to one of your numbers, in the order they are applied to an inbound message; add `from_country` to see what a sender messaging from elsewhere gets, which can differ.

Rules come back most specific first, and each carries `effective_keywords`: Bird's set for that operation and country plus anything you added.

## Changing the reply

Bird's default replies are correct but generic. To answer in your own name, create a rule for that country and operation:

```bash
bird sms keyword-rules create \
  --operation stop \
  --country NL \
  --reply "You are unsubscribed from MyBrand. Reply START to resume."
```

Your rule wins over Bird's default for that country and **keeps Bird's keywords** unless you add more, including keywords Bird adds later, so you do not have to track the catalogue to stay compliant. What an opt-out or opt-in keyword _does_ cannot be changed: a rule that tries to bind `STOP` to another operation is rejected.

To confine a rule to one number rather than every number you hold in the country, set `number` instead of relying on the country alone.

If you answer these messages from your own system rather than through Bird, set `reply` to null together with `confirmed_self_managed`. That switches Bird's auto-reply off for the rule while the suppression itself keeps working.

## Campaign keywords

`custom` rules carry no built-in behaviour: they match keywords you choose and send the reply you write, which is how a campaign keyword like `PIZZA` is handled. A `custom` rule inherits no keywords, so it needs at least one of its own, and it may omit `country` to apply everywhere you send.

A keyword Bird has bound to a compliance operation cannot be reused as a custom one.

## Reading and managing suppressions

`GET /v1/sms/suppressions` lists the pairs your messages are currently stopped for, most recent first. Filter by `destination` to check one subscriber before sending to them, by `originator` for one of your senders, or by `reason`:

- `keyword_stop`: the subscriber texted a stop keyword.
- `carrier_opted_out`: their carrier reported the opt-out.
- `manual`: added through the API or the dashboard.

Suppressions that have ended are not listed, so what you get back is the answer to "who can I not message right now".

You can add one yourself, honouring an opt-out a customer gave you on the phone, say:

```bash
bird sms suppressions add --destination +15550001234 --originator +15557654321
```

A manual suppression blocks **every category, including transactional**, and adding is idempotent. Removing one is deliberately narrow: only a `manual` suppression can be ended this way. A subscriber's own stop keyword and a carrier's opt-out are refused, because those are not yours to reverse.

## Next steps

- [Sending SMS](/docs/guides/sms/sending-sms): categories, senders, and what a send is refused for
- [Events](/docs/guides/sms/events): the `sms.*` events a send and its outcome emit
- [SMS log](/docs/guides/sms/sms-log): the per-message view, including refused sends