No description
  • JavaScript 100%
Find a file
GyozaGuy 9f2cfd54e9
All checks were successful
Release / build (push) Successful in 42s
Add notification chime and bump version to 1.3.0
2026-06-26 14:45:36 -06:00
.claude/skills/changelog Improve changelog skill to auto-propose entry from Git 2026-06-22 22:20:45 -06:00
.forgejo/workflows Move publish disablement to electron-builder config 2026-06-22 22:41:48 -06:00
.zed Automate release tag creation in Zed task 2026-06-22 22:30:09 -06:00
build Update unread and alert tray icons 2026-06-24 23:14:44 -06:00
.gitignore Ignore environment files in Git 2026-06-26 11:08:03 -06:00
CHANGELOG.md Add notification chime and bump version to 1.3.0 2026-06-26 14:45:36 -06:00
CLAUDE.md Add CLAUDE.md with setup and architecture guide 2026-06-22 21:07:46 -06:00
main.js Add notification chime and bump version to 1.3.0 2026-06-26 14:45:36 -06:00
package-lock.json Add notification chime and bump version to 1.3.0 2026-06-26 14:45:36 -06:00
package.json Add notification chime and bump version to 1.3.0 2026-06-26 14:45:36 -06:00
README.md Initialize Fastmail Electron tray app project 2026-06-22 11:09:48 -06:00

Fastmail Tray

A minimal Electron wrapper around app.fastmail.com that does the two things the official Fastmail desktop app doesn't: stays resident in the system tray and closes to the tray instead of quitting. Desktop notifications for new mail come straight from Fastmail's own web client (JMAP push → HTML5 Notification API, which Electron bridges to native OS notifications) — this wrapper just keeps the window alive so they keep arriving.

Prerequisites

  • Node.js 18+ and npm
  • A desktop environment that hosts a system tray (see the GNOME note below)

First-time setup

cd fastmail-tray
npm install

Run (development)

npm start

Log in once; the session persists in Electron's userData dir, so you stay logged in.

Enable notifications inside Fastmail: Settings → Notifications → turn on new-mail notifications, and accept the browser permission prompt the first time. Without this, Fastmail never fires notifications and the wrapper has nothing to relay.

Build a standalone AppImage

npm run dist

The AppImage lands in dist/. Make it executable and run it:

chmod +x dist/Fastmail-*.AppImage
./dist/Fastmail-*.AppImage

Your own icon

Replace build/icon.png (the included one is a placeholder). Use 512×512 PNG; electron-builder generates the other sizes. The same file is used for the window and the tray. If the tray icon looks fuzzy, supply a separate small, simple/monochrome image and point the Tray at it in main.js.

Wayland notes

  • main.js sets --ozone-platform-hint=auto before app-ready, so the packaged AppImage picks Wayland or X11 automatically. The npm start script passes the same flag for dev runs.
  • The tray icon uses StatusNotifierItem over DBus (display-server-agnostic), but your DE must host a tray:
    • KDE Plasma — works natively.
    • GNOME — install the AppIndicator and KStatusNotifierItem Support extension, or the tray icon won't appear at all.
  • Heads-up: tray-click hide/show can be flaky on some Wayland compositors (window restoring on the wrong workspace, or not regaining focus). It's reliable on KDE Plasma. Test on your compositor early. If tray.on('click') misbehaves, drop it and use the right-click context menu's "Open Fastmail" instead.

Optional extras

  • Unread badge: already wired — main.js parses the unread count out of the page title and calls app.setBadgeCount(). This shows up on launchers that support libunity badging; behavior varies by DE.
  • Start on login: add a .desktop file in ~/.config/autostart/ pointing at the AppImage, or call app.setLoginItemSettings({ openAtLogin: true }) in init().
  • mailto: handler: uncomment app.setAsDefaultProtocolClient('mailto') in init() to register. Note that on its own this just opens the inbox when you click an email link — deep-linking into Fastmail's compose view requires handling the mailto: argv in the second-instance event and navigating to Fastmail's compose URL, whose exact format you'll want to confirm from the running web app first.

License

MIT