Skip to main content
A topic is a named category of notification, such as gym-reminders, running-reminders or marketing. Subscribers hold a preference per topic, so you need no preferences table of your own. Preferences are per topic and per channel. Someone can keep running-reminder pushes and kill running-reminder emails. When you send to a topic, BuzzKit filters to the opted-in subscribers for you.

Create a topic

Every channel in channels must already have a live credential on the tenant. A topic offered on a channel with no credential is a 400 channel_not_connected. Connect Apple or Firebase first, as in the quickstart.
GET /v1/topics pages the catalog newest first with limit, cursor and total, and GET /v1/topics/:topicSlug retrieves one. PATCH /v1/topics/:topicSlug updates any field, checking a renamed slug for conflicts. Narrowing channels drops the channelDefaults entries for channels no longer offered, but the subscribers’ stored preferences for those channels are kept and come back if you offer the channel again. DELETE /v1/topics/:topicSlug soft-deletes it, and it disappears from every preference list.

How preferences resolve

A subscriber’s preference list is always the full topic catalog with a resolved state per offered channel. Subscribers store only their deviations.
isDefault: true means the subscriber never chose for that channel, so the topic’s default applies and keeps following it if you change it later. The order of resolution is the subscriber’s explicit choice, then channelDefaults[channel], then defaultOptedIn.

Sending to a topic

Every opted-in subscriber is reached, on the message’s channel only, through their enabled and active subscriptions. Combine topic with to or with a segment and the topic acts as a filter on that audience instead of being the audience. A topic that is not offered on the message’s channel is a 400 channel_not_offered.
A send reaches a subscription only when the subscription is enabled and active and the topic and channel preference is opted in. Muting one device and opting out of a topic are separate controls that compose. See subscribers.

Reading and writing preferences from your backend

The PATCH takes a preferences map with merge semantics. A value is either a boolean, which applies to every offered channel, or a per-channel map.
An unknown topic is a 404. An unknown channel is a 400, as is naming a channel the topic does not offer. A channel a topic does not offer is absent from its channels map, and the boolean shorthand applies to the offered channels only.

Reading and writing preferences from the app

The same pair exists on the client API, authenticated by a client key you ship in the app, so no endpoint of your own sits in front of it. GET /v1/client/preferences returns the resolved list with each topic’s category, ready to render as grouped sections, and PATCH /v1/client/preferences writes a change back.
BuzzKit-Subscriber names the caller. BuzzKit-Identity carries the identity hash and is required once verification is enforced on the tenant. Identify the subscriber before showing the screen so preferences work even when push permission was denied. The iOS SDK wraps both calls.

Caps and quiet hours

A topic’s dailyCap limits how many messages from that one topic a subscriber receives per local day. A send past it is recorded as capped in the delivery ledger rather than delivered.It sits on top of the tenant-wide sendPolicy.dailyCap, which counts sent deliveries per subscriber per local day across everything. Three workout reminders a day at most, while the rest of your notifications flow under the wider limit.The tenant policy also carries quietHours, which defers a delivery to the next allowed local time instead of failing it. With timezone: "subscriber" it follows each person’s $timezone; a fixed IANA name reads one clock. Both halves are off by default and set per tenant. See tenants.

Next

Subscribers

Identity, attributes and the subscriptions a topic send is filtered against.

Messages

Content, targeting and what happens after a send is accepted.