Skip to main content
Glama
mpacarroll

apple-messages-mcp-remote

by mpacarroll

apple-messages-mcp-remote

A fork of @griches/apple-messages-mcp that adds an optional remote (HTTP) transport, for running this server on an always-on Mac and reaching it from a cloud AI session instead of only a session running locally on the same machine. Local stdio mode is unchanged and remains the default — this is purely additive.

An MCP server that gives AI assistants access to Apple Messages on macOS. Reads messages from the Messages database (SQLite) and sends messages via AppleScript.

Quick Start (local, stdio — same as upstream)

npx apple-messages-mcp-remote

Related MCP server: imessage-mcp

Quick Start (remote, HTTP)

Only do this if you understand what you're exposing: this gives whoever holds the token read access to your real iMessage history, and send access to your Messages app. See Remote setup below before running this on a machine reachable from outside your own network.

export MCP_TRANSPORT=http
export MCP_AUTH_TOKEN=$(openssl rand -hex 32)   # save this, you'll need it on the client side
npx apple-messages-mcp-remote

Tools

Tool

Description

list_chats

List recent chats with last message preview

get_chat_messages

Get message history for a specific chat (with optional date range filtering)

search_messages

Search messages by text content

send_message

Send an iMessage or SMS

get_chat_participants

Get participants of a chat

Configuration

Claude Code

claude mcp add apple-messages -- npx apple-messages-mcp-remote

Claude Desktop

Add to your claude_desktop_config.json:

{
  "mcpServers": {
    "apple-messages": {
      "command": "npx",
      "args": ["apple-messages-mcp-remote"]
    }
  }
}

Remote setup

This adds an HTTP transport (Streamable HTTP, the current MCP spec's remote transport) alongside the original stdio one. Stdio is still the default — you only get the HTTP server if you set MCP_TRANSPORT=http.

Threat model this was actually designed for: one person, one Mac, one client at a time, connecting from that same person's own cloud AI session. It is not designed to be a multi-tenant hosted service — every deployment only ever has one real Messages database behind it, so there's no "different users, different permissions" problem to solve, which is why this uses a single bearer token instead of OAuth. If you want to offer this to other people against their own Macs, each of them runs their own instance with their own token; you're not meant to run one instance for many people.

Environment variables:

Variable

Required

Purpose

MCP_TRANSPORT

no (default stdio)

Set to http to enable the remote server.

MCP_AUTH_TOKEN

yes, in http mode

Bearer token every request must present. Generate with openssl rand -hex 32. Must be at least 32 characters — the server refuses to start otherwise. Never commit this.

MCP_PORT

no (default 8443)

Port to listen on.

MCP_HOST

no (default 127.0.0.1)

Bind address. Leave this on loopback and reach it through a tunnel (see below) rather than binding 0.0.0.0 and exposing a raw port.

Do not expose a raw open port on the public internet. Put a private tunnel in front of this instead — Tailscale or a Cloudflare Tunnel both work well and mean the port is never directly internet-routable, the bearer token is a second layer rather than your only layer, and you get to revoke access by removing a device/tunnel rather than by hoping nobody guessed the token.

Connecting a client, once the tunnel is up:

{
  "mcpServers": {
    "apple-messages-remote": {
      "url": "https://your-tunnel-hostname/",
      "headers": {
        "Authorization": "Bearer <your MCP_AUTH_TOKEN>"
      }
    }
  }
}

What this does not do: encrypt anything beyond what your tunnel provides, rate-limit requests, expire or rotate the token automatically, or provide per-tool permission scoping (a valid token can call every tool, including send_message). If any of that matters for your setup, treat this as a starting point, not a finished security product — patches welcome.

Requirements

  • macOS (uses AppleScript and macOS Messages database)

  • Node.js 22+ (uses built-in node:sqlite)

  • Full Disk Access granted to your terminal app (System Settings > Privacy & Security > Full Disk Access) — required for reading the Messages database

Permissions

  • Reading messages: Requires Full Disk Access for your terminal app to read ~/Library/Messages/chat.db

  • Sending messages: macOS will prompt you to allow your terminal app to control the Messages app via AppleScript

Credit

The stdio server, database reader, and AppleScript send logic are almost entirely the original work of @griches/apple-messages-mcp — this fork's own contribution is the remote HTTP transport and the auth/tunnel setup around it.

License

MIT.

Available Tools

5 tools
get_chat_messagesB

Get message history for a specific chat

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMaximum number of messages to return (default 100)
chat_idYesChat identifier (e.g. iMessage;-;+1234567890)
to_dateNoFilter messages up to this date (e.g. '2025-12-31')
from_dateNoFilter messages from this date (e.g. '2025-01-01' or '2025-03-15T14:00:00')

TDQS

B3.4/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden of behavioral disclosure. It only states the action and does not mention ordering, pagination, date-filter inclusivity, output format, or any permissions/rate limits.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single short sentence that front-loads the core action and scope. It is economical, though it sacrifices behavioral and usage detail that other dimensions require.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a simple read operation, the description plus the fully described schema is enough to construct a basic call with chat_id and optional filters. However, with no output schema and no guidance differentiating it from search_messages, the agent still faces moderate uncertainty.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, and each parameter already has a meaningful description, including default limit, chat_id format, and from/to date filters. The description adds no parameter-specific meaning beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The verb 'Get' and resource 'message history' precisely define the operation, and 'for a specific chat' constrains scope. This clearly distinguishes it from siblings like list_chats and send_message.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies a use case—fetching message history for one chat—but gives no explicit guidance on when to prefer it over search_messages, nor any exclusions or alternative routing. The agent must infer selection from tool names and schema.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

get_chat_participantsC

Get participants of a chat

ParametersJSON Schema
NameRequiredDescriptionDefault
chat_idYesChat identifier (e.g. iMessage;-;+1234567890)

TDQS

C2.9/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations provided, the description carries the full burden of behavioral disclosure. 'Get' implies a read-only operation, but the description does not mention authentication needs, return format, pagination, or any other behavioral traits beyond the trivial verb.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single concise sentence with no redundant words or filler. It is front-loaded and appropriately sized for a tool with one parameter, though it lacks richer context.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with no output schema and no annotations, the description does not explain what the participants data looks like, whether it returns names, IDs, or objects, or any edge cases. The description is enough for a trivial call but leaves important operational details unexplained.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the single chat_id parameter is fully documented in the schema, including an example format. The description itself adds no parameter-specific meaning, but the schema already covers what is needed, justifying the baseline score of 3.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the verb 'Get' and the resource 'participants of a chat', making the tool's primary purpose obvious. However, it does not differentiate itself from sibling tools such as list_chats or get_chat_messages.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

No guidance is provided about when to use this tool versus alternatives like list_chats or search_messages. The description gives no context, prerequisites, or exclusions, so the agent must infer usage entirely from the tool name and schema.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

list_chatsA

List recent chats with last message preview and participant info

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMaximum number of chats to return (default 50)

TDQS

A3.6/5.0
Behavior3/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden. It conveys that the operation is a non-mutating list and describes what is returned, but it does not disclose ordering, pagination, result limits, or whether only the current user's chats are included. It does not contradict any annotations.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single front-loaded sentence with no wasted words. It efficiently conveys the action, resource, and key return fields, making it easy for an agent to parse quickly.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a low-complexity tool with one optional parameter and no output schema, the description is reasonably complete: it names the result categories (recent chats, last message preview, participant info). It could add explicit ordering or pagination notes, but the essential information for invoking the tool and understanding its result is present.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

The input schema documents the only parameter, 'limit', with its default value and purpose, so schema coverage is complete at 100%. The description adds no additional parameter semantics, so the baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly identifies the action ('List') and the resource ('recent chats'), and specifies the included data: last message preview and participant info. It is distinguishable from message-level siblings like get_chat_messages and search_messages, though it does not explicitly name an alternative.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The use case is implied: use this when you need an overview of recent chats with message previews and participant details. However, there is no explicit guidance about when to prefer list_chats over get_chat_messages, search_messages, or get_chat_participants, and no exclusions are stated.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

search_messagesC

Search messages by text content

ParametersJSON Schema
NameRequiredDescriptionDefault
limitNoMaximum number of results (default 50)
queryYesText to search for in messages
chat_idNoLimit search to a specific chat

TDQS

C2.9/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description carries the full burden of behavioral disclosure. It only states the core function and offers no information about read-only behavior, result ordering, pagination, authentication requirements, or what happens when no matches are found.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, focused sentence with no filler or redundancy. It front-loads the core action and resource, making it easy to parse quickly.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness2/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

The tool has no output schema and no annotations, so the description should provide more operational context. It does not explain whether chat_id is optional for global search, what the response looks like, or how this differs from get_chat_messages. These gaps make the description only minimally viable.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema fully documents all three parameters: query, limit, and chat_id. The description itself adds no parameter-level meaning beyond what the schema already provides, warranting the baseline score.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the action ('Search') and the resource ('messages'), with a specific qualifier ('by text content'). It is unambiguous about what the tool does, but it does not explicitly distinguish itself from the sibling tool get_chat_messages, which also involves retrieving messages.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines2/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description gives no guidance on when to use this tool versus alternatives like get_chat_messages or list_chats. It does not mention search scope, such as whether it searches across all chats or within a single chat, nor does it state any exclusions.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

send_messageA

Send an iMessage or SMS to a phone number or email address

ParametersJSON Schema
NameRequiredDescriptionDefault
toYesPhone number or email address of the recipient
textYesMessage text to send
serviceNoService to use (default iMessage)

TDQS

A3.5/5.0
Behavior2/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations are provided, so the description bears the full burden of behavioral disclosure. It mentions that the tool can send to phone numbers or email addresses, but does not explain delivery behavior, error handling, message limits, or whether iMessage automatically falls back to SMS. This leaves significant behavioral ambiguity for a send operation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The description is a single, front-loaded sentence with no filler. Every word contributes to explaining the tool's core function, making it highly efficient.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness3/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For a tool with 3 fully documented parameters and no output schema, the description covers the essential function but omits practical details like return behavior, error cases, or whether SMS can truly be sent to an email address. The potential ambiguity about iMessage/SMS delivery to email prevents a higher score.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters3/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 100%, so the schema already documents all parameters (to, text, service) clearly. The description adds no new parameter meaning beyond restating that recipients are phone numbers or email addresses, which is already in the schema. Baseline of 3 applies.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the verb 'send' and the resource 'iMessage or SMS' with recipient types. It is immediately distinguishable from all sibling tools (list_chats, get_chat_messages, search_messages, get_chat_participants), which are read-oriented.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines3/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

The description implies the tool's purpose through the verb 'send', so an agent can infer that it is for sending messages rather than listing or searching. However, it does not explicitly state when to use this tool versus alternatives, nor does it offer any exclusions or fallback guidance.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections. Dates show when Glama detected each change.

  1. 5 tool updatesv0.1.0
    • First observedget_chat_messages
    • First observedget_chat_participants
    • First observedlist_chats
    • First observedsearch_messages
    • First observedsend_message

TDQS

A3.5/5.0
Disambiguation3/5

list_chats includes participant info and last message preview, which overlaps with get_chat_participants. Similarly, get_chat_messages and search_messages both retrieve messages, though one is chat-scoped and the other is global. Descriptions help but boundaries are not fully crisp.

Naming Consistency5/5

All tool names follow a consistent verb_noun snake_case pattern: list_chats, get_chat_messages, search_messages, send_message, get_chat_participants. No deviations or mixed conventions.

Tool Count5/5

Five tools is well-scoped for an iMessage server, covering the core messaging actions without unnecessary bloat. Each tool has a clear place in the workflow.

Completeness4/5

The surface covers listing chats, reading message history, searching, sending, and fetching participants. Minor gaps exist such as deleting messages or retrieving a single chat's full metadata, but the essential workflows are complete.

Maintenance

ActivityMaintained
ResponsivenessNo issues

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Connectors

Related MCP Servers

  • A
    license
    A
    quality
    D
    maintenance
    Enables AI assistants to read iMessage history and send messages on macOS. Supports conversation listing, message search with keyword and semantic modes, contact lookup, and sending messages to existing conversations.
    13
    11
    MIT
  • A
    license
    Not graded
    quality
    D
    maintenance
    Enables reading and sending iMessages on macOS through MCP, with tools for managing chats, messages, and attachments via AI agents.
    MIT
  • A
    license
    Not graded
    quality
    B
    maintenance
    Enables AI assistants to read, search, and send iMessages, manage contacts, and access attachments on macOS.
    16
    MIT
  • -
    license
    Not graded
    quality
    Not graded
    maintenance
    Read, search, and send iMessages locally from your terminal or through MCP clients like Claude, Cursor, and VS Code.
    -

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/mpacarroll/apple-messages-mcp-remote'

If you have feedback or need assistance with the MCP directory API, please join our Discord server