Announcer
Carrying a broadcast as one post where the platform keeps a place for announcements, mentioning the audience in the platform's idiom, instead of a message to every member.
Subscriby\Connector\Contracts\Ports\Announcer. Bound by connectors that declare announcements, which in turn requires broadcasts.
On some platforms a bot writing the same message to every member one by one is what the platform's spam filter looks for, and the platform has a channel for exactly this. A connector that binds the announcer receives each broadcast once per installation and posts it where the creator said; members who asked to be told directly ("Notify me here" on the portal) still receive the core's per-person copy through your Messenger.
The method
public function announce(InstallationRef $installation, CredentialBag $credentials, Announcement $announcement): DeliveryResult;Announcement carries the canonical Message (body and buttons), the audience (a list of ResourceRefs: the places whose holders the broadcast is for, empty for everyone the installation reaches) and an optional title. Render the body through your TextRenderer, mention the audience in your own idiom (the role behind each place), and answer a DeliveryResult: delivered with the platform's id for the post, or the classified failure. An installation with nowhere to post (the creator picked no channel yet) answers a Configuration failure, and the core falls back to the per-member copies for that installation. The message arrives whole, never split: a body over your max_length is refused before you see it and becomes copies too.
What the core does around you
- The broadcast composer shows your
broadcast_hintsslot, which is where you say which channel the post goes to and which roles it will mention. - The broadcast job posts first, once per live installation whose connector binds the port and has the
announcementsswitch on, and only for a segment a post can address: a broadcast to everyone arrives with an empty audience, a broadcast to customers with the gated resources the project sells on your platform (or the filtered plan's), and an installation on whose platform the project gates none of them is skipped. Segments narrower than the holders of a place (trials ending, leads, the churned, one window's holders) are never posted, because a post in a shared place cannot address some of its readers without reaching the rest. - The members your post reached get no copy of their own unless they switched "Notify me here" on for that account; everyone else, and every member of an installation whose post was refused, gets the copy as before. A continued run of a rate-limited broadcast carries the posts made and never posts again.
- The post's id and the refusal, when there is one, are logged and counted under the delivery metric, so an operator can see a channel the app can no longer write to.
How Discord does it
One embed in the installation's announcement_channel with <@&role> mentions for the plans' roles and allowed_mentions.roles set to exactly those roles, so nothing else in the body pings anyone.
What the kit checks
announcer.answers_delivery_result: an announcement for everyone comes back as a DeliveryResult, delivered or carrying a classified failure, never an exception.
Announcements are not a second messaging path
The port carries broadcasts and nothing else. A grant notice, a receipt or a support reply is one person's and stays on the Messenger.
How is this guide?
Last updated on
SpaceBrowser
Listing the places an installation could gate, so a creator picks a role, a channel or a room from a list instead of answering a prompt on the platform.
InstallationActions
The things a creator can have an installation do on its platform beyond gating, declared as data so the dashboard, the REST API, the MCP server, the automation surfaces and the Copilot all offer them the same way.