Architecture
Design your channels around who needs the update
An order changes status. The customer needs to see it, the operations team may need to see it, and everyone else probably does not. Channel design starts with that audience. A good channel model makes it clear where an event belongs and who is allowed to receive it.
Separate the audience from the event
A channel groups listeners. An event describes something that happened. For a shared project, private-project-1042 could carry task.created, task.moved and comment.added events. The audience stays the same while the type of update changes. This gives each screen a clear place to listen without creating a subscription for every possible action.
Use separate channels when the audiences differ. A personal notification and a project-wide activity can come from the same action but belong to different groups. Before adding a channel, write down one sentence: everyone subscribed here is allowed to receive every payload published here. If that sentence is false, split the audience or reduce the payload.
Choose public, private or presence deliberately
In pubb, a public channel can be subscribed to by anyone with the application’s public key. That can fit an openly shared poll result or a public activity display. It does not fit customer orders, internal metrics or personal messages. An obscure public channel name is still public.
Private channels require a signature from your backend. Use them when a subscription needs an access decision, such as membership in a workspace or participation in a conversation. Presence channels add user identity and membership events, which are useful when a shared screen needs to show who is currently there. Choose presence because the product uses that membership information, rather than adding it to every channel by default.
Make names predictable and permissions explicit
A naming convention such as private-workspace-17 or private-order-1042 makes it easier to follow an event from the publishing code to its subscribers. Use stable IDs instead of display names, which can change. Keep email addresses, secrets and other sensitive information out of channel names.
Predictable names are safe only when access checks are correct. Your authorization endpoint should validate the current user and their relationship to the requested resource. Never sign an arbitrary channel name just because a browser supplied it. Channel names are isolated by application in pubb, but your product still needs to decide which users may join each restricted channel within that application.
Let the channel boundary shape the payload
Consider an order update. The customer channel might carry the order ID, its new status and an update version. An internal operations channel might need assignment details that the customer should never receive. Publish audience-appropriate payloads instead of sending one large internal object everywhere and hiding fields in the interface.
A compact event can also tell the screen to fetch the latest authorized resource. This is useful when several views need different fields or when a record is too large to send as an event. pubb currently limits event data to 10 KiB of UTF-8 JSON, so keep large documents and attachments outside the event payload.
Start with one product flow
For a project board, start with one private channel per project and a few clearly named events. Subscribe while the project is open, and clean up that subscription when the view no longer needs it. Add a personal channel if you introduce individual notifications, and use presence where showing current collaborators improves the experience.
Before extending the model, check two cases: a user from another project must be denied access, and every field in a valid subscriber’s payload must be appropriate for them. This keeps channel design tied to the product’s actual sharing rules as new realtime features arrive.