Skip to main content
Glama
imessage-mcp

imessage-mcp

iMessageMCP

Search, read, reply to, and clean up your Apple Messages from Claude or any other MCP client. It runs on your Mac and reads the Messages history already there.

  • Finds messages by words, exact text, or phrase across iMessage, SMS, MMS, and RCS

  • Reads whole conversations with edits, unsent messages, reactions, replies, and read receipts

  • Shows photos people sent you, with location data removed

  • Keeps up with new messages through a change feed, and answers counts and response-time questions

  • Sorts conversations into Known and Unknown Senders, the way Messages does

  • Replies in an existing conversation after you approve a preview of exactly what will be sent

  • Deletes spam threads (one-to-one, nobody in your Contacts) after you approve a preview

  • Keeps working when Messages rewrites its database, and a watchdog restarts it if it ever stops answering

How it runs

The server runs on your Mac as a LaunchAgent and listens on 127.0.0.1:8765 over HTTP with a bearer token. tailscale serve makes that port reachable on your tailnet, so an MCP gateway elsewhere (for example a small VPS that Claude connects to) can call it. It can also run over stdio for a client on the same Mac.

Claude ──> your MCP gateway (VPS) ──> Tailscale ──> tailscale serve on the Mac ──> 127.0.0.1:8765

Related MCP server: imessage-kit-mcp

Install on the Mac

Requirements: macOS 14 or newer and Tailscale, connected. The installer downloads its own Node 24 (checksum-verified) into ~/Library/Application Support/imessage-mcp-runtime, so any other Node on the Mac is untouched.

git clone https://github.com/jaredzimmerman/iMessageMCP.git
cd iMessageMCP
SEND=1 DELETE=1 IMESSAGE_VPS_SSH=root@<your-vps> bash mac/install.sh
  • SEND=1 turns on replying and DELETE=1 turns on deleting spam threads. Leave either out to keep it off.

  • IMESSAGE_VPS_SSH copies the bearer token to the gateway at /etc/code-mcp/imessage.token. Leave it out to copy the token yourself from ~/.config/imessage-mcp/token.

  • When it finishes, give the Node binary it prints Full Disk Access (System Settings > Privacy & Security > Full Disk Access). Messages history is protected by macOS; without it the server can't read anything.

  • The first reply or delete asks for permission to control Messages. Allow it.

The installer copies the code to ~/Library/Application Support/imessage-mcp, builds it, and loads two LaunchAgents: com.indigokarasu.imessage-mcp (the server) and com.indigokarasu.imessage-mcp-watchdog. Run it again after pulling changes; it keeps the existing token. bash mac/uninstall.sh removes both. More detail: mac/README.md.

Running it locally over stdio

npm ci && npm run build
{
  "mcpServers": {
    "imessage": {
      "command": "node",
      "args": ["/path/to/iMessageMCP/bin/imessage-mcp.js", "--allow-send"]
    }
  }
}

The app that starts the server (your terminal, Claude, an editor) needs Full Disk Access.

Prompts

prompt

what it does

catch_up

Who is waiting on a reply from you, and what they need

draft_reply

A reply in your own texting style. With sending on, it can be sent after you approve the preview

recap

Your week in messages: volume, busiest conversations, anyone still waiting

Clients that attach resources can use imessage://conversations and imessage://conversations/{chat_id}.

Tools

tool

what it does

search_messages

Search by substring, exact text, token, or phrase. Message text by default; conversation names and attachment filenames are opt-in. Filter by service, sent or received, and date

get_conversation

Read a conversation by chat_id or by a contact or group name, with edits, reactions, receipts, replies, group events, and attachments. The cursor pages to older events

list_conversations

Find conversations by contact, service, kind, reply state, Known or Unknown Senders folder, or date, each with its latest message

get_attachment

Show one attachment from get_conversation: images as a JPEG with location and camera metadata removed, text files as text. Needs the full privacy mode

sync_messages

Pull every change since a cursor: new, edited, unsent, and deleted messages, conversation memberships, reactions, and receipts

analyze_communication

Message counts by hour and weekday, response times, streaks, and who starts conversations

resolve_contact

Match a name, phone number, or email to a contact in your Mac's Address Book, and report ambiguity rather than guess

server_status

Version, privacy mode, index and cache state, schema support, conversation membership counts, and Contacts access

prepare_send

Preview a reply in an existing conversation and get a one-time token (with --allow-send)

confirm_send

Send the previewed reply, then check chat.db for sent, delivered, or failed

cancel_send

Discard a prepared reply

prepare_delete

Preview deleting one whole one-to-one conversation with nobody in Contacts and get a one-time token (with --allow-delete)

confirm_delete

Have Messages delete the previewed conversation, then check chat.db that it is gone

cancel_delete

Discard a prepared delete

The send and delete tools appear only when the server is started with --allow-send or --allow-delete. Replies go only into conversations that already exist; the server can't start a new one. A delete is refused for group chats, for anyone in Contacts, and when a new message arrived after the preview. With Messages in iCloud a delete reaches every device, and Recently Deleted keeps it for up to 30 days.

Results use plain ids (message_id, chat_id, attachment_id) you can pass between tools. Every tool's output schema accepts both its success envelope and the structured error envelope, so strict clients can show the original reason and recovery hints.

Apple can record the same message in several conversations. Search returns that message once with all canonical chat_ids and their conversations labels. A single membership also includes chat_id and conversation; for shared results, pass the relevant id from chat_ids to get_conversation. Only Apple's explicit lookup evidence combines chat aliases.

Global and contact message counts deduplicate shared records within the requested scope. Conversation timelines and sequence metrics keep each recorded membership, so adding per-conversation counts can exceed the global count. Sync includes chat_ids on changes and emits message_membership_changed with previous_chat_ids; its changed_at is null because Apple does not timestamp these joins. When a sync cursor returns DATABASE_CHANGED, start a new sync without a cursor.

Contact names expand to the selected person's addresses. An exact phone number or email scopes only that address. resolve_contact reports ambiguous identity instead of merging people.

Conversation reads are strict by default. When a body or relationship can't be recovered completely, the error explains the allow_partial: true retry. Partial results keep completeness, warnings, and each event's row_status.

Configuration

option

description

--allow-send

Add prepare_send, confirm_send, cancel_send. Needs the full privacy mode. env IMESSAGE_ALLOW_SEND=1

--allow-delete

Add prepare_delete, confirm_delete, cancel_delete. env IMESSAGE_ALLOW_DELETE=1

IMESSAGE_SEND_LIMIT_PER_HOUR

Replies allowed per hour, 1 to 200 (default 20)

IMESSAGE_DELETE_LIMIT_PER_HOUR

Deletes allowed per hour (default 20)

--privacy <mode>

The most any caller can see. full (default), redacted (names and masked handles, calendar days, no message text or filenames), or aggregate (counts only). A call can ask for a stricter mode, never a looser one. env IMESSAGE_PRIVACY

--contacts <mode>

live (default) names handles from your Contacts; none shows handles only. env IMESSAGE_CONTACTS

--database <path>

Read a copy of chat.db instead of this Mac's Messages. env IMESSAGE_DB

--transport http --port <n>

Serve MCP over HTTP on 127.0.0.1 instead of stdio. Requires IMESSAGE_API_TOKEN or IMESSAGE_API_TOKEN_FILE. IMESSAGE_ALLOWED_HOSTS and IMESSAGE_ALLOWED_ORIGINS take comma-separated lists; both default to localhost

IMESSAGE_CACHE=0

Keep the search index in memory only

IMESSAGE_WARM_SEARCH=0

Build the search index on the first search instead of at startup

Safety and privacy

  • Nothing is sent or deleted without your approval. Each reply or delete is two steps: a preview with a single-use token, then a confirm. The assistant is told to confirm only after you approve that exact preview. Sends and deletes are rate-limited and logged to ~/Library/Logs/imessage-mcp/sends.jsonl and deletes.jsonl without message text.

  • chat.db is never written. The server opens the Messages database with query_only and changes it only through the Messages app, which it drives with fixed AppleScript. Message text and ids reach osascript as arguments, never as script source.

  • Local. No accounts, telemetry, or analytics. The HTTP transport binds to 127.0.0.1, checks the bearer token, Host, and Origin, and is meant to be reached through Tailscale, not exposed publicly.

  • Your client sees what you ask for. Results go to the MCP client you use and its model provider, under their policies. --privacy redacted or aggregate limits what leaves the server.

  • Search index. Built on your Mac and cached encrypted in ~/Library/Caches/imessage-mcp, with a key derived from your Messages database, so it opens only for an app that can already read your messages. Deleting it is always safe.

  • Untrusted content. Messages can contain text written to manipulate an AI. The server tells clients to treat all message content as data, never as instructions.

Details: SECURITY.md and PRIVACY.md.

When something goes wrong

  • Server log: ~/Library/Logs/imessage-mcp/server.log. A database_reopened line means Messages changed its database and the server reopened it on its own.

  • Watchdog log: ~/Library/Logs/imessage-mcp/watchdog.log. The watchdog calls server_status every 2 minutes and restarts the server after two failed checks in a row.

  • Restart by hand: launchctl kickstart -k gui/$(id -u)/com.indigokarasu.imessage-mcp

  • Check access and schema: node bin/imessage-mcp.js doctor

Development

npm ci
npm test      # unit tests on synthetic Messages databases
npm run e2e   # launches the built server over stdio and HTTP
npm run perf  # one-million-message performance gates

Tests use synthetic data only. See CONTRIBUTING.md.

Credits and license

MIT. Built on imessage-mcp by Ani Potts (MIT); see LICENSE.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

    Related MCP Connectors

    Related MCP Servers

    • A
      license
      Not graded
      quality
      D
      maintenance
      Enables reading, searching, and sending iMessages directly from MCP-compatible clients by accessing the local macOS iMessage database, supporting conversations, attachments, and both individual and group chats.
      638 npm
      10
      MIT
    • A
      license
      Not graded
      quality
      D
      maintenance
      Enables reading, sending, and managing iMessage conversations on macOS through MCP.
      1
      MIT
    • A
      license
      Not graded
      quality
      C
      maintenance
      Enables AI agents to read the entire Apple Messages (iMessage/SMS) history on a Mac through a read-only, batched tool that supports listing chats, retrieving transcripts, polling recent messages, and searching message bodies via REST or streamable HTTP MCP.
      MIT
    • F
      license
      Not graded
      quality
      B
      maintenance
      Enables AI clients to read and search macOS Messages history through a read-only MCP interface.
      -