Opt-Out Management

How senderZ handles STOP and START keywords, opt-out compliance, and the opt-out API.

senderZ automatically handles opt-out compliance on every message you send. When a recipient texts STOP, they are immediately blocked from receiving further messages from your tenant. When they text START, they are re-subscribed. You do not need to build any opt-out logic yourself.

Why Opt-Outs Matter

The Telephone Consumer Protection Act (TCPA) requires that recipients can opt out of receiving messages at any time. Ignoring an opt-out can result in fines of $500 to $1,500 per message. senderZ enforces opt-out rules at the infrastructure level so you are never at risk of accidentally messaging someone who has opted out.

How It Works

STOP Keywords

When any of these keywords arrive as an inbound message to your tenant’s phone number, senderZ automatically opts out the sender:

STOP · STOPALL · UNSUBSCRIBE · CANCEL · END · QUIT

Keywords are case-insensitive. “stop”, “STOP”, and “Stop” all trigger an opt-out.

When senderZ processes a STOP keyword:

  1. An opt-out record is created in the opt_outs table, linking the phone number to your tenant.
  2. A confirmation reply is sent automatically: “You have been unsubscribed and will receive no further messages.”
  3. All future outbound messages to this number from your tenant are blocked at the router layer, before any delivery attempt.

START Keywords

These keywords re-subscribe a previously opted-out number:

START · UNSTOP · YES

When senderZ processes a START keyword:

  1. The opt-out record is updated with an opted_back_in_at timestamp.
  2. A confirmation reply is sent: “You have been re-subscribed.”
  3. Future messages to this number are allowed again.

The Compliance Check

Before every outbound message — whether sent individually via POST /v1/messages or as part of a campaign — the router checks:

Is there an active opt-out record for this tenant + phone number?
  → Yes: Block the message. Status = "blocked", reason = "opted_out"
  → No: Proceed with delivery.

This check happens before phone selection, before iMessage detection, and before any delivery attempt. Opted-out messages never leave the system.


Viewing Opt-Outs

GET /v1/compliance/opt-outs

List all opted-out phone numbers for your tenant.

Query Parameters

page number

Page number, starting at 1. Defaults to 1.

limit number

Results per page. Defaults to 25, maximum 100.

curl https://api.senderz.com/v1/compliance/opt-outs \
  -H "Authorization: Bearer sz_live_YOUR_KEY"
200 OK
{
  "data": [
    {
      "phone_number": "+15551234567",
      "opted_out_at": "2026-04-10T14:22:00Z",
      "opted_back_in_at": null
    },
    {
      "phone_number": "+15559876543",
      "opted_out_at": "2026-04-08T09:15:00Z",
      "opted_back_in_at": "2026-04-12T11:30:00Z"
    }
  ],
  "meta": {
    "total": 2,
    "page": 1,
    "limit": 25
  }
}

Numbers with a non-null opted_back_in_at have re-subscribed and can receive messages again. They still appear in the list for your audit records.


Beyond opt-outs, TCPA requires that you have documented consent before messaging someone. The Consent API lets you log when and how a recipient consented to receive messages.

POST /v1/compliance/consent

Log a consent record for a phone number.

phone_number string Required

The phone number that gave consent, in E.164 format.

consent_type string Required

Type of consent: express_written, express, or implied.

consent_source string

How consent was collected: web_form, sms_keyword, api, manual, or a custom value.

ip_address string

The IP address of the person who consented, if collected via a web form.

curl -X POST https://api.senderz.com/v1/compliance/consent \
  -H "Authorization: Bearer sz_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "phone_number": "+15551234567",
    "consent_type": "express_written",
    "consent_source": "web_form",
    "ip_address": "203.0.113.42"
  }'
201 Created
{
  "data": {
    "id": "01JCNS789GHI",
    "phone_number": "+15551234567",
    "consent_type": "express_written",
    "consent_source": "web_form",
    "consented_at": "2026-04-15T10:30:00Z"
  }
}

Best Practices

  1. Always include opt-out language. Append “Reply STOP to unsubscribe.” to marketing messages. This is required by TCPA and expected by recipients.
  2. Log consent at the point of collection. When someone submits a web form, signs up for notifications, or gives verbal consent, immediately log it via the Consent API with the source and timestamp.
  3. Export your opt-out list regularly. Download your opt-out list from the developer portal as a CSV for your compliance records. Keep these records for at least 4 years per TCPA guidelines.
  4. Do not re-add opted-out numbers. If you import a contact list that includes opted-out numbers, senderZ will still block messages to those numbers. Importing a contact does not clear an opt-out.
  5. Monitor your opt-out rate. A high opt-out rate (above 2-3%) may indicate your messaging frequency is too high or your content is not relevant to your audience.

Frequently Asked Questions

What happens if I try to message an opted-out number? The message is blocked immediately at the router layer. It never reaches the delivery system. The message status is set to “blocked” with the reason “opted_out”. You are not charged for blocked messages and they do not count against your quota.

Can I manually opt out a number? Currently, opt-outs are only triggered by inbound STOP keywords. If a customer asks to be removed via email or phone, instruct them to text STOP to your number, or contact support for a manual removal.

Are opt-outs per-tenant or global? Per-tenant. If a recipient sends STOP to Tenant A’s phone number, they are only opted out of Tenant A’s messages. They can still receive messages from Tenant B. This is standard multi-tenant behavior.

Does senderZ handle HELP keyword responses? Currently, senderZ processes STOP and START keywords. HELP keyword responses are not automated — you can handle HELP via your inbound webhook if needed.