A command-line interface for Fastmail by Marc Köhlbrugge.
Disclaimer: This is an unofficial tool, not affiliated with Fastmail. Use at your own risk.
Fastmail has a great web interface, but sometimes you want to:
- Quickly triage your inbox without leaving the terminal
- Let AI agents manage your email with structured JSON output
- Script email workflows for automation
- Search across your mailbox with powerful JMAP queries
fm gives you all of this through a clean, intuitive CLI inspired by GitHub CLI.
# Authenticate (stores token in system keychain)
fm auth login
# Check your inbox
fm inbox
# Read an email
fm email read M1234567890
# Search for emails
fm search "from:alice subject:meeting"
# Create and send a draft
fm draft new --to bob@example.com --subject "Hello" --body "Hi Bob!"
fm draft send M9876543210brew install marckohlbrugge/tap/fmgit clone https://github.com/marckohlbrugge/fastmail-cli.git
cd fastmail-cli
go build -o fm ./cmd/fmThen move fm to somewhere in your PATH, or add the directory to your PATH.
brew update && brew upgrade fmcd fastmail-cli
git pull
go build -o fm ./cmd/fm| Command | Description |
|---|---|
fm inbox |
List recent emails in your inbox |
fm search <query> |
Search emails with JMAP query syntax |
fm folders |
List all mailboxes |
| Command | Description |
|---|---|
fm email read <id> |
Display full email content |
fm email thread <id> |
View entire conversation thread |
fm email archive <id> |
Archive email(s) |
fm email move <id> <folder> |
Move email to a folder |
fm email delete <id> |
Move email to trash |
| Command | Description |
|---|---|
fm draft new |
Create a new draft |
fm draft reply <id> |
Reply to an email |
fm draft forward <id> |
Forward an email |
fm draft edit <id> |
Edit an existing draft |
fm draft send <id> |
Send a draft |
fm draft delete <id> |
Delete a draft |
| Command | Description |
|---|---|
fm folder list |
List all folders |
fm folder create <name> |
Create a new folder |
fm folder rename <id> <name> |
Rename a folder |
Every command supports --json for machine-readable output, making fm perfect for AI agents and automation:
# Get inbox as JSON
fm inbox --json
# AI agent can parse and act on emails
fm inbox --json | jq '.[0].id' | xargs fm email read --jsonExample JSON output:
[
{
"id": "M1234567890",
"threadId": "T9876543210",
"subject": "Meeting tomorrow",
"from": [{"name": "Alice", "email": "alice@example.com"}],
"receivedAt": "2024-01-15T10:30:00Z",
"isUnread": true,
"preview": "Hi, just wanted to confirm..."
}
]If you use Claude Code, you can add the included skill to let Claude manage your email.
If installed via Homebrew:
mkdir -p ~/.claude/commands
ln -sf $(brew --prefix)/share/fm/fastmail.md ~/.claude/commands/fastmail.mdIf installed manually:
mkdir -p ~/.claude/commands
ln -sf /path/to/fastmail-cli/skills/fastmail.md ~/.claude/commands/fastmail.mdThen ask Claude things like:
- "Check my inbox for unread emails"
- "Search for emails from Alice about the project"
- "Draft a reply to the last email from Bob"
See skills/fastmail.md for the full command reference.
fm stores your API token securely in your system's credential store (macOS Keychain, Windows Credential Manager, or Linux Secret Service).
- Go to Fastmail Settings > Privacy & Security > Integrations
- Click "New API Token"
- Give it a name (e.g., "fm-cli") and select permissions
- Run
fm auth loginand paste your token
# Interactive login
fm auth login
# Check authentication status
fm auth status
# Log out (removes token from keychain)
fm auth logoutAlternatively, set the FASTMAIL_TOKEN environment variable:
export FASTMAIL_TOKEN="fmu1-..."
fm inboxfm includes safety measures to prevent accidental data loss:
When running non-interactively (piped input, AI agents, scripts), destructive commands are blocked by default:
# This will fail in safe mode
echo "" | fm draft send M123
# Error: 'fm draft send' is disabled in safe mode.
# Override with --unsafe flag
echo "" | fm draft send M123 --unsafe --yes
# Or via environment variable
FM_UNSAFE=1 fm draft send M123 --yesDestructive actions require confirmation:
fm email delete M123
# Delete email M123? [y/N]
# Skip with --yes flag
fm email delete M123 --yesGenerate completions for your shell:
# Zsh
fm completion zsh > "${fpath[1]}/_fm"
# Bash
fm completion bash > /etc/bash_completion.d/fm
# Fish
fm completion fish > ~/.config/fish/completions/fm.fishmake build # Build binary
make test # Run testsTo release a new version:
git tag v1.x.x
git push origin v1.x.xThis triggers GitHub Actions to build binaries for macOS (Intel/ARM) and Linux (amd64/arm64) and create a GitHub release.
Then update the Homebrew formula manually:
# Get checksums from the release
gh release download v1.x.x --pattern 'checksums.txt' --output -
# Update Formula/fm.rb in marckohlbrugge/homebrew-tap with new version and checksumsI'm not accepting pull requests at this time—reviewing external code for security in a tool that handles email requires more time than I can commit to. Feel free to open an issue for bug reports or feature requests.
MIT