You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Inbox search in the desktop app, Android app and web inbox: the filter row's search icon or / opens a field, hidden by default, matching a case-insensitive substring in title, summary, folder, repo, branch, agent or session title together with chip filters. Esc or × clears and closes it, reset clears both search and filters, and no matching requests shows No matches; / now searches Inbox as well as History
History API: outcome, kind and agent accept comma-separated lists, matching any value within a filter and combining different filters; invalid outcome or kind values return 400, and single-value queries work as before
Licensed Android push gateway is live at https://push.gethandup.dev for license holders using the official app: notifications.backends now defaults to [desktop, push]; an installed signed license and proof-of-possession device ticket are required, so only verified phones get woken, without customer Firebase credentials. Android handles verification pushes silently and registers the token and optional ticket with every paired daemon. notifications.push.url selects the gateway and notifications.push.payload defaults to wake (no title or previews); title opts into redacted titles. handup doctor reports local verified-phone prerequisites and warns no verified phone for tokens without tickets; readiness does not prove phone delivery. Relay pairings also register tokens with the daemon; self-hosted fcm takes precedence over push
Releases include the self-hosted relay for Linux servers: handup-relay__linux_amd64.tar.gz and _linux_arm64.tar.gz (static musl binary with LICENSE and THIRD_PARTY_NOTICES.md), listed in checksums.txt and releases.json (kind relay); the downloads page has a Self-hosted relay section and the relay guide shows how to install it
Android: computers paired through a relay now get push wake-ups when the relay has compatible sender credentials. The phone registers its push token with both the relay channel and the computer, so relay push: wake and push: title notifications reach it; they show the relay title or "Approval requested" and open the inbox, and unpairing attempts to remove both registrations. Direct and Tailscale pairings are unchanged; the official app only receives relay wake-ups when the relay's FCM service account belongs to the app's Firebase project
Dictation in the desktop app, Android app and web inbox: a mic button beside free-text answers, feedback and reply fields, text fields and email subject/body appends what you say; the text stays editable and nothing is sent until you submit, and read aloud stops before listening. The desktop app transcribes on your computer with whisper.cpp using a model you install in Settings → Dictation (tiny, base or small; default base; SHA-256 checked, works offline afterwards; macOS asks for microphone access); Android uses the phone's speech recognizer (on-device when supported, otherwise Google's speech service; Settings says which) and asks for microphone permission; the web inbox uses the browser's speech recognition where available
Optional cloud speech providers in the desktop and Android apps: dictation with OpenAI, Groq or ElevenLabs and read aloud with OpenAI or ElevenLabs. API keys entered in Settings are stored only in the OS keychain or Android Keystore, are never shown again and never go to the daemon or relay; the provider receives your audio or text and may charge for it
Desktop dictation on Linux reuses a whisper.cpp model another speech tool already downloaded, so there is nothing to install: voxtype (Omarchy's dictation), hyprwhspr, Handy, OpenWhispr, Speech Note, GNOME Speech2Text, whisper-dictation, Buzz and AUR whisper.cpp-model packages. The same size as the selected model is preferred, a model installed in handup always wins, and Settings → Dictation shows which one is used (for example "Using base.en from voxtype (English only)")
Vim keys in the Inbox and History: G (or End) jumps to the last request and g g (or Home) to the first; Ctrl+D / Ctrl+U scroll the request on screen half a screen, Ctrl+E / Ctrl+Y a line and Page Down / Page Up a screen. All but g g and Home can be remapped under keys: in the config (scroll_half_down, scroll_line_up, last, …)
handup doctor reports push delivery: which route sends notifications (self-hosted FCM or the licensed gateway), verified and unverified phones, whether the push gateway is reachable, and the last delivery result with its age (for example "refused 5m ago: rate limited"). It also checks that a configured relay answers. Network checks time out after 3 seconds and only warn
Flood control for a runaway hook or agent session (one agent + session): after notifications.burst.max (20) notifications per notifications.burst.window (1m) the rest are skipped and one summary ("N more from ") follows; a source sending requests.flood_threshold (40) requests in a minute shows an inbox banner with Mute 1h, Dismiss all (N pending) and hide, and is listed by handup flood with ready-to-run mute/clear commands and a rules snippet; handup flood clear --agent A [--session S] dismisses its pending notices and denies its other pending requests ("Cleared as a flood"); handup mute --agent/--session [--for 1h] [--dismiss-notices] silences a source until removed or a daemon restart (handup unmute ID|--all); past requests.max_per_minute (120) a source's new requests are refused with HTTP 429 code rate_limited. Each limit takes 0 to turn it off. API: /v1/floods, /v1/floods/dismiss, /v1/mutes with floods.changed and mutes.changed events; view devices can read them, changing them needs decide
Rules can dismiss info notices with action: dismiss (matching only kind: info; recorded as dismissed with decided_by: rule). Other rule actions still never touch notices
Changed
Inbox and History filters in the desktop app, Android app and web inbox: pick several type or outcome chips on one sideways-scrolling row, then narrow by agent, request type or files in Filters. Nothing picked shows everything; extra picks stay visible as removable chips, and a reset icon clears them. Unread automatic decisions open through the auto-handled · View line above the list instead of a tab
The selected request in the Inbox and History lists stands out more, with a blue bar and outline, so it no longer looks like a hovered row
Every stored file preview (Markdown, text, code, JSON, HTML, diff, plain file, as well as images, video, audio and PDF) now shows one compact row above it in the desktop app, Android app and web inbox: name · type · size with icon-only Open and Download buttons (HTML has Download only). Bundle files use the same row, and code previews no longer repeat the file name in their toolbar. Inline text sent without a file has no file actions
Fixed
Auto-handled Mark read now syncs across every device connected to the same daemon, separately for each computer, and survives daemon restarts. GET/PUT /v1/auto-read max-merges the read watermark and emits auto_read.changed only when it rises; remote and relay updates require decide scope
omp turn notices now come only from interactive omp sessions: headless runs (omp -p, scripted evals; detected through omp's ctx.hasUI) no longer send their final message as a handup notice, which flooded the inbox when tools launched many omp runs
Phone inbox (Split layout): when the request you last opened is resolved on another device while you are on the list screen, the list moves on and shows All clear after the last one, instead of an empty list