Skip to content

Repository files navigation

ZapFast

WhatsApp, native and fast. ZapFast is a WhatsApp client written in Rust with egui. It uses whatsapp-rust for the WhatsApp Web protocol. It runs on Linux, macOS, and Windows, links to your phone as a companion device, and has no browser engine. In our Linux test, it opened in under a second and used about 150 MB of idle RAM, compared with 1.13 GB for WhatsApp Web and its Chromium processes. See the measurements.

ZapFast is a sibling of Spotifast, with the same native UI for a different service.

ZapFast showing a chat with a photo, a document, a voice message, a quoted reply, and a link

See zapfast.rocks for downloads and guides.

A group chat with sender names and pictures, a photo with reactions, a reply with a mention, and a poll

The linking screen with the QR code

What it does

  • Links to your phone. Scan a QR code or link with your phone number. Recent history is copied to this computer after linking and stored here.
  • Chats. See pinned, unread, muted, and archived chats, typing indicators, and message status. Search chats, saved messages, and contacts. Pinned chats stay in pin order (most recently pinned first), regardless of new messages. Chat and contact name searches ignore accents, so Angel finds Ángel. Typing indicators show other participants, excluding your own linked devices.
  • Read state across devices. Reading a chat syncs its unread badge with your phone and other linked devices, including when read receipts are off. Replies from another device clear preceding unread messages. The read-receipt toggle also controls voice-message played receipts; account privacy is checked before sending receipts in direct chats. A hidden window does not read messages.
  • Conversations. See replies, reactions, edits, deleted messages, read receipts, sender names, and group pictures. Older messages load as you scroll up, first from the local archive and then from your phone. Group messages show two gray checks after every recipient has received them, and blue checks after every recipient has read them. The recipient list and individual receipts are saved locally; later membership changes do not change that list. If the original recipients are unknown, ZapFast waits for the phone's aggregate status instead of guessing from one reader.
  • WhatsApp formatting. Bold, italic, strikethrough, code, lists, quotes, mentions, and link previews are supported. Links are clickable. Hebrew and Arabic RTL paragraphs keep logical word order by reordering font runs; this is not a full Unicode Bidirectional Algorithm. Emoji use the desktop's color emoji font, with a bundled fallback, and emoji-only messages are larger.
  • Send attachments with captions. Paste a picture, drop files, or use the file picker. They stay in the composer until you send them or press Escape.
  • Mute chats for eight hours, one week, or indefinitely. The setting also applies on your phone and to desktop notifications. Mute changes from your phone survive history arriving later, including during initial linking. Existing installations request one settings refresh after upgrading to recover previously lost mute settings and pin order, without relinking.
  • Voice messages. Play, seek, record, reply with, and send voice messages in the chat. The app normalizes quiet recordings and handles OGG/Opus without external tools.
  • Send messages. Press Enter to send text and Shift+Enter for a new line. You can swap these keys in Settings. The composer is focused when you open or return to a conversation; invoking search keeps focus in search, and Escape clears search and returns to the composer; another Escape closes the chat and saves your text draft. Open menus, dialogs, and unfinished actions are dismissed first. Type :name to autocomplete an emoji without leaving the composer, or @ in a group to mention a member. Reply, react with any emoji, edit, forward, delete, and check when a message was sent, delivered, or read.
  • Disappearing-message timers. Outgoing messages use the chat's known timer, including replies, attachments, edits, and forwards. Forwarded copies use the destination chat's timer. Received messages remain in the local archive after they expire on the phone. A clock badge on chat avatars shows enabled timers and follows changes from the phone. Changing the default timer for new chats leaves existing chats alone.
  • View attachments. ZapFast downloads files up to 64 MB automatically or on click. Photos, stickers, GIFs, voice messages, audio, locations, contacts, polls, and link previews appear in the chat. Videos and documents open in their default desktop apps. Profile pictures and downloaded images support Windows drive paths and filenames with spaces or non-ASCII characters. If an attachment has expired, ZapFast asks your phone to upload it again.
  • Polls. Use the checklist button beside the paperclip to create a poll with 2–12 answers. Turn off Allow multiple answers for a single-choice poll. Click an answer in a poll to vote; click a selected answer again to remove it. Results and your selection are retained in the encrypted archive, including votes received through phone history. Visible polls automatically request earlier votes from your phone. If it is offline, results are labelled incomplete and the request retries with backoff; no refresh button or relinking is needed. Voting needs the original poll's key; if that key is missing, the message explains that voting is available on your phone. Creating polls in disappearing-message chats is not yet supported by the protocol library's poll API, so ZapFast blocks it instead of ignoring the timer.
  • Emoji, GIF, and sticker picker. Search emoji and GIFs, use recent emoji and stickers, and save stickers with a right-click. Emoji autocomplete and picker search select their first match; use the arrow keys and Enter to choose it. GIF search needs a free GIPHY API key unless the build includes one.
  • Sticker packs. Import a pack from a signal.art link or .wastickers file. Animated packs remain animated. Packs are stored as WebP files on your computer.
  • Consistent names. Use names from your address book or public WhatsApp profile names across chats, replies, mentions, and notifications.
  • Groups. See members, sender names, and sender pictures. Announcement groups are read-only for non-admins.
  • Presence. See online, last-seen, and typing status, and send your typing status.
  • Idle rendering. History-sync progress updates when data arrives. Animated stickers and GIFs play only while their message or picker tile is visible.
  • Sync recovery. A conflicting app-state collection is recovered through whatsapp-rust, including requesting a fresh snapshot from the paired phone when validation fails. Private read-state updates run one at a time. Failures pause the whole queue with backoff from 30 seconds to 15 minutes; pending reads remain saved and resume automatically. New messages can still arrive.
  • Runs in the background. Closing the window keeps ZapFast linked in the system tray. Reopen it from the tray or by launching it again. Quit from the tray or with Ctrl+Q, or disable this behavior in Settings.
  • Desktop notifications. Get notifications with the chat picture when you are away from the open chat. Muted chats do not notify you. Windows notifications identify ZapFast as the sender and show chat pictures as small circular icons; installed and portable builds register this identity in the current user's registry. On Linux, clicking a notification opens the chat, and reading the chat here or on another device dismisses its outstanding notifications. On macOS, notifications use the installed ZapFast application's identity without an application chooser; unregistered development builds skip notifications if that identity is unavailable.
  • Update notices. ZapFast checks GitHub once a day and shows a download link when a newer release is available. You can turn this off in Settings.
  • Themes. Light, dark, follow the system, or a local JSON palette. Native Linux packages can follow Omarchy colors without restarting the app. Zoom with Ctrl+plus and Ctrl+minus.
  • Copy text. Select part of a message or copy across messages in WhatsApp's [time, date] Name: format. Contact names and numbers are also selectable.
  • Keyboard shortcuts. Ctrl+K searches, Alt+↑/↓ switches chats and keeps the active chat visible in the list, Esc cancels the current action, Ctrl+L focuses the message input, and Ctrl+/ lists all shortcuts (use Command instead of Ctrl on macOS). The × at the left of the shortcut hints hides the bar; restore it with Show shortcut hints in Settings.
  • Local storage. Messages, contacts and sticker metadata are stored in a SQLCipher-encrypted archive, unlocked automatically through your OS keyring. Existing plaintext archives are migrated on first use. Attachments remain ordinary files in the cache directory. Unlinking deletes both and removes this device from your phone.

What it does not do yet

  • Play ordinary videos in the app (they open in your player), or reply to a message with an attachment.
  • Calls, status posts, communities, newsletters, and group administration.

Installing

On macOS with Homebrew: brew install --cask crmne/tap/zapfast.

ZapFast was previously called FastsApp. Version 0.13.0 introduces the new package and executable names. On Arch Linux:

yay -S zapfast-bin      # the released build, ready made
yay -S zapfast          # the release, built from source
yay -S zapfast-git      # built from the latest commit

Builds for every release are on the releases page:

Platform File
Linux x86_64 and arm64 zapfast-vX.Y.Z-<target>.tar.gz, with the desktop file and icon in packaging/
Windows x64 and arm64 zapfast-vX.Y.Z-<target>-setup.exe (no administrator rights needed), or the .zip
macOS, universal zapfast-vX.Y.Z-macos-universal.dmg

On macOS, the rounded Dock icon matches the app bundle. Native menus provide Settings, editing, search, view controls, and window commands. The traffic lights share the chat header, leaving more room for conversations in a normal window. Settings is also available with ⌘,.

The macOS release process signs the app with Developer ID, submits the DMG to Apple's notarization service, and staples and validates its ticket before publishing. Open the DMG and drag ZapFast to Applications. When upgrading from FastsApp on macOS, quit the old app and remove its application bundle after installing ZapFast.

Releases before 0.13.0 keep their original FastsApp filenames.

Flatpak

Flatpak packaging lives in packaging/flatpak/, following Spotifast's source manifest and release-bundle setup. Future releases will attach an x86_64 .flatpak bundle; install a downloaded bundle with flatpak install --user FILE and run flatpak run rocks.zapfast.ZapFast. Flathub publication is pending; ZapFast is not yet listed there. See PACKAGING.md for local builds and preparing a Flathub submission. File selection uses desktop portals; the sandbox has no general access to your home directory.

Archive encryption

The archive key is a random 256-bit secret in Secret Service on Linux, Keychain on macOS, or Windows Credential Manager. Linux needs a working Secret Service provider (for example GNOME Keyring or KeePassXC with Secret Service enabled). If the keyring is locked or unavailable, unlock it and click Retry; ZapFast keeps its archive intact and waits before connecting. It never saves a replacement plaintext archive. Back up both the archive and its OS keyring key: copying only archive.db to another computer is insufficient.

Only archive.db and its SQLite journal/WAL are encrypted. Device credentials in session.db, downloaded media, profile pictures, saved sticker files and settings remain ordinary files. Use full-disk encryption for those files, swap, backups and remnants of the old plaintext archive. Migration removes the original only after verifying its encrypted copy; deletion cannot guarantee erasure from SSDs or snapshots. Keyring unlocking also does not protect against software running as you while your login is unlocked.

From source

ZapFast needs Rust, a C/C++ toolchain, CMake and Perl (for bundled OpenSSL). rust-toolchain.toml pins the exact version. On Linux, it also needs GUI development packages:

# Debian and Ubuntu
sudo apt install libxkbcommon-dev libwayland-dev libgl1-mesa-dev libasound2-dev cmake perl
# Arch
sudo pacman -S libxkbcommon wayland mesa alsa-lib cmake perl

Then:

cargo install --path .
zapfast

The desktop file and icon are in packaging/.

whatsapp-rust is pinned to a Git commit because version 0.7.0 on crates.io enables a simd feature that needs nightly Rust. The pinned commit builds on stable Rust and includes the upstream fixes for missing app-state snapshots and conflicts that make no progress. ZapFast does not reset your session to recover a collection.

Using it

On first start, scan the QR code from WhatsApp under Linked devices, Link a device. To link without the camera, click Link with phone number instead, enter your number with its country code, then enter the shown code on your phone.

WhatsApp then sends your recent history. This can take a few minutes. A banner shows the progress. New messages arrive live, and your phone does not need to stay on the same network.

Right-click a chat or message to open its menu. Open Settings from the gear or with Ctrl+,. Use the pencil to message a new number or save a contact. You can also open a group member's contact card. Saved names sync through WhatsApp to your phone and linked devices.

Files

What Linux Notes
Settings ~/.config/zapfast/settings.json JSON, safe to edit
Device keys ~/.local/state/zapfast/session.db Owned by whatsapp-rust; deleting it unlinks
Messages ~/.local/state/zapfast/archive.db SQLCipher-encrypted SQLite, unlocked by the OS keyring; raw messages retain attachment keys
Attachments, avatars ~/.cache/zapfast/ Safe to delete
Saved stickers and packs ~/.local/state/zapfast/stickers/ Plain WebP files; each pack is a folder
Log of the last run ~/.local/state/zapfast/zapfast.log --verbose for more

macOS and Windows use the standard platform directories selected by the directories crate. On first start, ZapFast moves settings, the linked session, message archive, saved stickers, caches, and window state from fastsapp (or the earlier fastwhatsapp) paths. Existing ZapFast directories take precedence and are never overwritten. Quit FastsApp before starting ZapFast; if an older copy is still running, the new launch brings its window forward. Your phone may keep showing the old linked-device name until you link again.

On Linux and macOS, ZapFast restricts its configuration, state, and cache directories to the current user (0700), including existing installations. Startup stops if those directories cannot be created or secured, before opening logs or databases. Windows uses the permissions inherited from your user profile.

Local themes

Settings → Appearance → Theme uses the same picker as Spotifast, with Follow system, Light, Dark, and its Catppuccin, Catppuccin Latte, Nord, Ristretto, and Tokyo Night palettes. Choose Open themes folder below the picker to add JSON palettes beside settings.json. A local file with a bundled palette's name overrides it. For example:

{"base":"dark","colors":{"accent":"#89b4fa","bubble_out":"#293954"}}

Unspecified colors inherit the light or dark base. Spotifast palettes also work: chat backgrounds, bubbles, and links derive from their interface colors when not specified. Color names match Palette in src/theme.rs; use #RRGGBB or #RRGGBBAA. The last accepted palette is cached in settings, so a missing or damaged theme file does not reset your appearance. Linux watches the themes folder for changes without periodic repaints. On other platforms, use zapfast reload-themes after editing. The command also works while the window is closed and never launches a stopped app.

On Omarchy, Follow system and Omarchy read the active desktop palette and follow its changes in native, portable, and source builds, even without installed hooks. Other desktops keep their normal light/dark system preference. Native packages additionally register a missing per-user template and theme hook on first launch; existing user files are preserved. Flatpak uses the desktop's light/dark preference and does not read host theme files or install desktop hooks.

Updating ZapFast

ZapFast checks GitHub once a day when Check for updates is enabled. Click Update in the banner to download and verify a newer release, then Restart to update when convenient. Download updates automatically is optional and off by default; it downloads in the background and still waits for you to restart. Downloads contact GitHub's API and release-asset hosts and are checked against the release's SHA-256 checksums. The updater keeps a backup and restores it if the updated app cannot start.

The in-app updater supports marked portable downloads, the Windows installer, and the macOS app in Applications. Keep zapfast-portable.txt beside a portable executable. AUR, DEB, RPM, Flatpak, Cargo and Homebrew installations use their package manager. Older portable downloads without the marker need one manual upgrade. No account or additional service is needed.

Developing

cargo run --features demo -- --demo            # sample chats, no connection
cargo run --features demo -- --demo-page login # or settings, pair, info, light, …
cargo run --features demo -- --demo-shot shot.png --demo-page chat,light
cargo run --features demo -- --demo-tour      # Space starts/replays a 41-second tour
cargo test --all-features                      # includes a headless layout of every screen
cargo clippy --all-targets --all-features -- -D warnings

To include a default GIPHY key for GIF search, set it at build time. A key in Settings overrides it:

ZAPFAST_GIPHY_KEY=your-key cargo build --release

The earlier FASTSAPP_GIPHY_KEY build variable remains supported as a fallback.

AGENTS.md describes the architecture and the rules for changes.

Recording a demo

The demo feature uses offline sample chats in a fresh temporary directory. It does not open your linked account, read your message archive, connect to WhatsApp, or register a tray icon. You can run it alongside your regular app.

cargo build --locked --features demo
./target/debug/zapfast --demo-tour --demo-size 1280x800

The ZapFast Demo window waits for Space. The 41-second tour starts with search, switches chats with keyboard shortcuts, scrolls, right-clicks a message and selects Reply, types quickly, completes emoji and mentions, searches the GIF picker and sends a still sticker, opens group information and the shortcut list, and changes themes through Settings. It uses the normal mouse and keyboard handlers; a local responder handles outgoing messages with no WhatsApp connection. The GIF-search thumbnails and still stickers are rendered from the bundled Noto emoji font; demo GIF search uses these local fixtures. The tour makes no sound and holds its final frame. Space rebuilds the sample and replays. For an automatic start, add --demo-tour-delay 5000 (milliseconds). Use --demo instead of --demo-tour to explore the sample chats yourself. For deterministic theme screenshots, --demo-page settings,omarchy and --demo-page settings,omarchy-light preview following dark and light Omarchy palettes without changing the desktop theme.

On Omarchy, run omarchy screenrecord, select the demo window, then press Space in ZapFast. Recording has no audio unless you explicitly enable desktop or microphone audio. Stop with omarchy screenrecord --stop-recording after the tour finishes. The default capture records a fixed rectangle, so keep the demo window visible and stationary until recording stops.

To annotate the video with a visible pointer, click rings, and outlined shortcut labels, add --demo-tour-events tour.json when launching the tour. After recording, run:

python3 scripts/render-demo.py recording.mp4 tour.json launch.mp4 --start 0.8

Set --start to the recording time (in seconds) when you pressed Space. The export trims the setup footage, adds a caption band below the app, and produces a silent H.264 MP4. It requires ffmpeg with libass support and ffprobe. These annotations are added during video export, not drawn by the app. The trace contains only pointer coordinates and shortcut labels, not typed text.

Disclaimer

ZapFast is an unofficial client and is not affiliated with WhatsApp or Meta. Using an unofficial client may be against WhatsApp's terms of service and could get an account suspended. Use it at your own risk.

Packaging maintenance

Release packaging uses the native-packages gem. macOS release builds automatically sign and notarize when the Apple CI credentials are configured. native-packages.yaml declares packages and downstream repositories; native recipes and installation assets live in packaging/; see PACKAGING.md for local commands and CI behavior.

License

MIT. Inter and Noto Color Emoji are under the SIL Open Font License; the icons are from Lucide (ISC).

About

ZapFast: a fast, native WhatsApp client in Rust and egui

Topics

Resources

Stars

347 stars

Watchers

4 watching

Forks

Releases

Packages

Used by

Contributors

Languages