Mobile previously fired a completion notification only when the entire
cloud run went terminal (status `completed`/`failed`/`cancelled`). For a
typical cloud run that's a long-lived sandbox processing successive
prompts, the canonical "your prompt is done" signal is the per-turn
`_posthog/turn_complete` event, not the run-level status — so users
sending a prompt and backgrounding the app got no banner when the agent
finished.
Worse, the existing terminal-status path was effectively dead for normal
completions: the final `turn_complete` log entry arrived before the
status update and cleared `awaitingPing`, so the status branch's
`shouldPing` check always read false by the time it ran.
Extend `analyzeEntries` to surface a distinct `hasTurnCompleted` flag for
`_posthog/turn_complete` / `_posthog/task_complete`, and fire the
`turn_complete` local notification (plus sound + haptic) from the live
`logs` branch when the user was awaiting a ping and the batch isn't also
an `awaiting_user_input` (which keeps its own dedicated banner). Mirrors
desktop PR #2344 — same gap, same shape of fix.
Generated-By: PostHog Code
Task-Id: 4d2246b1-ddde-4ded-bb3c-a25109305477
Problem
Mobile cloud tasks never fired completion notifications for normal turn
endings. The user would send a prompt, background the app, and the agent
would finish without the device ringing — because mobile only had two
notification paths and both missed the common case:
logspath fired a notification only on_posthog/awaiting_user_input(agent blocking on the user). Plain_posthog/turn_complete(agent done, run still alive) was a no-opbeyond clearing
isPromptPending.completed/failed/cancelled. But the finalturn_completelogentry arrives via the SSE stream before the status update, and the
log batch already clears
awaitingPing— so the status branch'sshouldPing = preState.awaitingPingcheck always readfalseby thetime it ran. Effectively dead for normal completions.
Same shape of gap as desktop PR #2344 ("fire completion notifications
for cloud tasks"), where the cloud branch of
updatePromptStateFromEventswas clearingisPromptPendingonturn_completebut never callingnotifyPromptComplete.Changes
analyzeEntriesnow surfaces a distincthasTurnCompletedflag for_posthog/turn_complete/_posthog/task_complete, in addition tothe existing
hasTurnEnd(which covers all four turn-end methodsincluding
awaiting_user_inputanderror).logsbranch of_handleCloudUpdatenow fires theturn_completelocal notification (plus the existing sound + hapticside effects, gated by
pingsEnabled) when:hasTurnCompletedis true, ANDhasAwaitingUserInputis false (which has its own dedicated banner).historical entries and would re-notify for turns that completed in
past app runs.
maybePresentLocalNotification(30s per task) andthe
focusedTaskIdsuppression continue to apply, so the new pathdoesn't double-fire when status terminal arrives shortly after
turn_complete.
No desktop code changes; only the React Native app.
Test plan
pnpm --filter @posthog/mobile test— 25 files / 105 tests pass.pnpm exec biome ci apps/mobile/src/features/tasks/stores/taskSessionStore.ts— clean.npx tsc --noEmitinapps/mobile— no new errors introduced by this change (the pre-existing test-file errors are untouched).awaiting_user_inputturn end — still get the "needs your input" banner, not the generic "finished" one.