The {:notification, notification} message a screen receives when a
notification arrives or is tapped, on both platforms.
def handle_info({:notification, %{presentation: :tap, data: data}}, socket) do
{:noreply, Mob.Socket.push_screen(socket, MyApp.ThreadScreen, data)}
end
# Arrived while the app was open; the OS still shows its banner.
def handle_info({:notification, %{presentation: :foreground}}, socket) do
{:noreply, socket}
endFields
:presentation—:foregroundwhen the notification arrived while the app was in the foreground,:tapwhen the user opened it from the banner or notification centre, including the tap that launched the app from a killed state.:action— for a:tap,"default"for a tap on the notification itself. An app that registers its own notification categories also sees"dismiss"and its own action identifiers here (iOS).nilfor:foreground.:source—:pushfor a remote notification,:localfor one scheduled on the device.:id— the notification's identifier (theid:given toMobNotify.schedule/2), ornil.:title,:body— the displayed text, ornil.:data— the custom payload:data:fromMobNotify.schedule/2, or the custom keys of a push payload (iOS'sapsdictionary is not included). Top-level keys are atoms; nested values are as JSON decodes them (maps with string keys, lists, numbers, booleans,nil).
Where it is delivered
To the process that registered for notifications through mob_notify
(MobNotify.register_push/1, or MobNotify.schedule/2 on iOS) while it is
alive. Otherwise to the screen currently showing. A tap that launches the
app arrives at the root screen once it has mounted, exactly once.
Each native layer serialises the notification to one JSON envelope and hands
it to the :mob_screen router, which decodes it with decode/1. That keeps
the shape in one place rather than one per platform; see
decisions/2026-10-01-notification-delivery-envelope.md.
Summary
Functions
Decodes the JSON envelope native code hands to the router.
Types
Functions
@spec decode(binary()) :: {:ok, t()} | {:error, :invalid_json | :not_an_object | :data_key_too_long}
Decodes the JSON envelope native code hands to the router.
presentation defaults to "tap" when absent. Most callers that predate
the field send taps: app-owned Android MainActivity code and callers of
the iOS mob_set_launch_notification_json/1 hook. The exception is the
app-owned MobFirebaseService that mob_new 0.1.45–0.4.10 generated, which
hands over foreground pushes without it; such an app must add
"presentation": "foreground" (see the push notifications guide).