Fastmail JMAP MCP Server — email, masked email, and push notifications
Project description
Fastmail Blade MCP
The only MCP server built on Fastmail's native JMAP protocol — email, masked email, and push notifications with token-efficient output.
Wraps the Fastmail JMAP API via jmapc as an MCP server using FastMCP 2.0.
Why Fastmail Blade?
Every other email MCP uses IMAP — a 1986 protocol that was never designed for programmatic access. Fastmail Blade uses JMAP, Fastmail's native protocol:
- JMAP-native — stateless, JSON-based, supports batch operations natively. No IDLE hacks, no MIME parsing, no connection state management.
- Masked Email — full CRUD for Fastmail's privacy aliases (create, list, enable/disable). No IMAP MCP can touch this — it's a Fastmail extension that only exists in JMAP.
- Push notifications — real-time EventSource via JMAP Push. Know when mail arrives without polling.
- Incremental sync — JMAP state tokens for delta changes. Get only what's new since your last check, not the entire mailbox.
- Token-efficient — concise pipe-delimited output, null-field omission. IMAP MCPs dump raw headers and MIME multipart.
- Write-safe — env-gated writes, batch limits (50 max), credential scrubbing on all error paths.
Features
- 18 tools: email read/write/manage, masked email, push notifications, meta
- Masked Email management — no other MCP server exposes this Fastmail extension
- JMAP Push (EventSource) — real-time state change notifications
- Write-gate — all write operations disabled by default (
FASTMAIL_WRITE_ENABLED=true) - Token-efficient — concise output, capped lists, null-field omission
- Batch limits —
mail_bulkcapped at 50,mail_searchdefaults to 20 - SKILL.md — self-teaching instructions for Claude
Requirements
- macOS (tested) or Linux
- Python 3.12+
- uv
- Fastmail account with API token
Quick Start
# Clone and install
cd fastmail-blade-mcp
uv sync
# Set your API token
export FASTMAIL_API_TOKEN=fmu1-xxxxxxxx
# Run (stdio transport)
uv run fastmail-blade-mcp
Claude Code
claude mcp add fastmail-blade -- uv run --directory ~/src/fastmail-blade-mcp fastmail-blade-mcp
Claude Desktop (claude_desktop_config.json)
{
"mcpServers": {
"fastmail-blade": {
"command": "uv",
"args": ["run", "--directory", "/path/to/fastmail-blade-mcp", "fastmail-blade-mcp"],
"env": {
"FASTMAIL_API_TOKEN": "fmu1-xxxxxxxx",
"FASTMAIL_WRITE_ENABLED": "false"
}
}
}
}
Tools (18)
Email Read (5)
| Tool | Description |
|---|---|
mail_mailboxes |
Mailbox list with ID, name, total/unread, role |
mail_read |
Full email: headers + body |
mail_search |
Search with filters (sender, subject, date, mailbox, keywords) |
mail_threads |
Chronological conversation view |
mail_snippets |
Search with highlighted context excerpts |
Email State & Sync (2)
| Tool | Description |
|---|---|
mail_state |
Get JMAP state token for change tracking |
mail_changes |
Incremental changes since a previous state token |
Email Write (4, gated)
| Tool | Description |
|---|---|
mail_send |
Send new email |
mail_reply |
Reply (preserves threading) |
mail_move |
Move to mailbox |
mail_flag |
Set/clear keywords ($flagged, $seen, etc.) |
Email Manage (2, gated)
| Tool | Description |
|---|---|
mail_delete |
Move to Trash (default) or permanently destroy |
mail_bulk |
Bulk action on up to 50 emails |
Masked Email (3)
| Tool | Description |
|---|---|
masked_list |
List aliases with state, domain, description |
masked_create |
Create new masked alias (gated) |
masked_update |
Update state/description (gated) |
Push (2)
| Tool | Description |
|---|---|
push_subscribe |
Listen for state changes via EventSource |
push_status |
Check EventSource availability |
Security
| Layer | Control |
|---|---|
| Secrets | FASTMAIL_API_TOKEN from env (never logged) |
| Transport | stdio default (no network exposure) |
| Write gate | FASTMAIL_WRITE_ENABLED default false |
| Batch limits | mail_bulk capped at 50 |
| Token scrubbing | API token removed from all error output |
| HTTP auth | Optional bearer token middleware |
HTTP Transport
export FASTMAIL_MCP_TRANSPORT=http
export FASTMAIL_MCP_HOST=127.0.0.1
export FASTMAIL_MCP_PORT=8767
export FASTMAIL_MCP_API_TOKEN=your-secret-token
uv run fastmail-blade-mcp
Environment Variables
| Variable | Default | Description |
|---|---|---|
FASTMAIL_API_TOKEN |
(required) | Fastmail API token |
FASTMAIL_WRITE_ENABLED |
false |
Enable write operations |
FASTMAIL_MCP_TRANSPORT |
stdio |
Transport: stdio or http |
FASTMAIL_MCP_HOST |
127.0.0.1 |
HTTP bind host |
FASTMAIL_MCP_PORT |
8767 |
HTTP bind port |
FASTMAIL_MCP_API_TOKEN |
(none) | Bearer token for HTTP auth |
Architecture
src/fastmail_blade_mcp/
├── server.py — FastMCP 2.0 server, 18 @mcp.tool decorators
├── client.py — JMAP client via jmapc, masked email, push subscriptions
├── formatters.py — Token-efficient output (pipe-delimited, null omission)
├── models.py — Config, write-gate, batch limits
└── auth.py — Bearer token middleware for HTTP transport
Built with FastMCP 2.0 and jmapc.
Development
make install-dev # Install with dev dependencies
make test # Run unit tests (92 tests, mocked)
make test-e2e # Run E2E tests (requires live Fastmail)
make check # Lint + format + type-check
make run # Start the server
License
MIT
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file fastmail_blade_mcp-0.2.0.tar.gz.
File metadata
- Download URL: fastmail_blade_mcp-0.2.0.tar.gz
- Upload date:
- Size: 120.2 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
4349e0acba9907261c3d4fec43b3452e6913bf1a31d5c8d84ecda76a0e0a76e3
|
|
| MD5 |
e0463a3301ce5aa5fd003594f563a23e
|
|
| BLAKE2b-256 |
067b8a85d421d888ad5edc291a8bdcc649318900d700742668a8e7557b57b448
|
Provenance
The following attestation bundles were made for fastmail_blade_mcp-0.2.0.tar.gz:
Publisher:
publish.yml on Groupthink-dev/fastmail-blade-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
fastmail_blade_mcp-0.2.0.tar.gz -
Subject digest:
4349e0acba9907261c3d4fec43b3452e6913bf1a31d5c8d84ecda76a0e0a76e3 - Sigstore transparency entry: 1396159142
- Sigstore integration time:
-
Permalink:
Groupthink-dev/fastmail-blade-mcp@f8e403c9e5d3a23d4d22270247df2f79022933cf -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/Groupthink-dev
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@f8e403c9e5d3a23d4d22270247df2f79022933cf -
Trigger Event:
push
-
Statement type:
File details
Details for the file fastmail_blade_mcp-0.2.0-py3-none-any.whl.
File metadata
- Download URL: fastmail_blade_mcp-0.2.0-py3-none-any.whl
- Upload date:
- Size: 22.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a777ffa650a3d2788e662c09f930185f79e276fc3c603ff4954ebffd5cb7e514
|
|
| MD5 |
aac45eaa2c26f215049ead4d9d0068e1
|
|
| BLAKE2b-256 |
a7e1d31c6fbf3a42a26ba5fe59596aa918eccc7a772419f07464edc9604f29ef
|
Provenance
The following attestation bundles were made for fastmail_blade_mcp-0.2.0-py3-none-any.whl:
Publisher:
publish.yml on Groupthink-dev/fastmail-blade-mcp
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
fastmail_blade_mcp-0.2.0-py3-none-any.whl -
Subject digest:
a777ffa650a3d2788e662c09f930185f79e276fc3c603ff4954ebffd5cb7e514 - Sigstore transparency entry: 1396159163
- Sigstore integration time:
-
Permalink:
Groupthink-dev/fastmail-blade-mcp@f8e403c9e5d3a23d4d22270247df2f79022933cf -
Branch / Tag:
refs/tags/v0.2.0 - Owner: https://github.com/Groupthink-dev
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
publish.yml@f8e403c9e5d3a23d4d22270247df2f79022933cf -
Trigger Event:
push
-
Statement type: