SendRaven

MCP server

45 tools. One line to install.

The same REST API, exposed to any MCP client. The server runs remotely and holds no database or provider credentials of its own: it can reach exactly what your key can reach and nothing more.

Get a key
Claude Codeterminal
claude mcp add --transport http sendraven https://mcp.sendraven.ai/mcp
Then, in a session
> What replies are waiting on me?

Using list_threads(awaiting_reply=true) …
Two threads. Maya at Acme asked for the
August invoice as a PDF, 40 minutes ago.

Install

Any client that speaks Streamable HTTP.

Claude Code

claude mcp add --transport http sendraven https://mcp.sendraven.ai/mcp

The first call opens a browser to sign in and pick a workspace. Nothing else to configure.

Cursor, Claude Desktop, and other clients with a JSON config

{
  "mcpServers": {
    "sendraven": {
      "url": "https://mcp.sendraven.ai/mcp"
    }
  }
}

Clients that support OAuth will prompt you to authorize on first use.

As a local process, from npm

claude mcp add sendraven -e SENDRAVEN_API_KEY=sk_live_… -- npx -y @sendraven/mcp

The same server, published as @sendraven/mcp. It speaks stdio when no port is set and takes the key from SENDRAVEN_API_KEY. Source and issues at github.com/CommonNinja/sendraven-mcp-server.

Remote server with a key instead of OAuth, for an agent running unattended

{
  "mcpServers": {
    "sendraven": {
      "url": "https://mcp.sendraven.ai/mcp",
      "headers": { "Authorization": "Bearer sk_live_…" }
    }
  }
}

Create the key in the dashboard under Developers. Give an agent’s key a daily limit, an allowlist, or an approval hold; the tools respect all three. Limits for agents.

The tools

Everything the API does, named for what an agent is trying to do.

Descriptions say which tool to reach for and what it costs to get wrong. A failed call returns the API’s own message, so “domain not verified” comes back as those words rather than a bare 403.

Send and read

  • send_email
  • send_template_email
  • reply_to_message
  • list_emails
  • get_email
  • list_scheduled_emails
  • cancel_scheduled_email

Threads

  • list_threads
  • get_thread

Approvals

  • list_pending_approvals
  • decide_approval

Sending domains

  • list_sending_domains
  • add_sending_domain
  • verify_sending_domain

Suppressions

  • list_suppressions
  • add_suppression
  • remove_suppression
  • suppress_many

Templates

  • list_templates
  • render_template

Campaigns

  • list_broadcasts
  • preview_broadcast
  • send_broadcast
  • list_broadcast_recipients

Automations

  • list_automations
  • enroll_in_automation
  • emit_event

Topics

  • list_topics
  • get_email_preferences
  • set_email_preferences

Contacts and audiences

  • list_audiences
  • add_contact
  • get_contact
  • find_contact
  • update_contact
  • delete_contact
  • remove_from_audience
  • tag_contact
  • list_tags
  • list_segments
  • count_segment

Operations

  • get_email_metrics
  • list_webhook_deliveries
  • list_api_keys
  • get_usage

Behaviour worth knowing

Three things the server does that a wrapper would not.

  • A held send is not a failure. When a key requires approval, send_email returns pending_approval with an id. The right move is to report that it awaits a person, not to retry.
  • Out of plan is 402, not 429. get_usage reports plan, usage and remaining so an agent can say “you are near your limit” before a batch rather than surfacing a payment error afterwards.
  • Two calls cannot be undone. send_broadcast mails an audience; run preview_broadcast first. remove_suppression lets us mail an address that bounced or complained. Neither should be used to fix a failed send.