The "distributor" receives notifications onto the device and sends them to the apps via a standardized API.
The apps themselves then post the notifications to the user via the android on-device notification API.
The "gateway" receives the notifications from the services over a standardized API and sends them to the distributor.
How the gateways actually distribute the notifications is actually completely up to the gateways. The main gateway (ntfy) uses websocket, another (nextpush) piggybacks off of nextcloud, and the new kid on the block (sunup) uses the Mozilla Push Service behind the scenes.
Nothing in this is restricted or locked in to a centralised platform.
What is a "push notification" exactly?
They’re “notifications” in common speech but there’s also stuff like “now playing” and live activities and rich content that are also “notifications” but do require the app to run.
From what you're saying, it doesn't sound like the OS-based polling would be more power efficient, as someone in this chain suggested, just more reliable. Though, I think you can just turn off battery optimization for the ntfy app, in which case I'd expect them to be on par.
If that's right, it seems like ntfy with battery optimization turned off is effectively a "real" push notification system.