Mandrill / Mailchimp Bridge

Drop-in replacement for the Mandrill (Mailchimp Transactional) API — keep the key-in-body convention and your existing request structure, swap in your wemail API key.

The Mandrill bridge lets you migrate from Mandrill (Mailchimp Transactional) to wemail without changing your integration code. Point your base URL to https://api.wemail.io/bridge/mandrill, put your wemail API key in the same key field of each request body, and keep the same request and response shapes — sends, template sends, message search, and reject listings all work the same way.

Authentication

Exactly like Mandrill, every endpoint is a POST with the API key in the JSON body's key field. Use your wemail API key (afn_live_… or afn_test_…) where your Mandrill key (md-…) used to be. Test-environment keys route through the sandbox: messages are accepted, simulated, and never delivered.

jsonAuthentication (request body)
{ "key": "afn_live_YOUR_WEMAIL_KEY", "message": { … } }

Supported Endpoints

POST /bridge/mandrill/api/1.0/messages/send.json

Send a message.

POST /bridge/mandrill/api/1.0/messages/send-template.json

Send using a stored template.

POST /bridge/mandrill/api/1.0/messages/search.json

Search sent messages.

POST /bridge/mandrill/api/1.0/messages/info.json

Get a single message's details.

POST /bridge/mandrill/api/1.0/rejects/list.json

List the rejection (suppression) list.

POST /bridge/mandrill/api/1.0/users/ping.json

Health check — returns "PONG!".

POST /bridge/mandrill/api/1.0/users/info.json

Account info + sending stats envelope.

Field-Level Compatibility

POST /messages/send.json — message fields

message.* fields
ParameterTypeRequiredDescription
from_email / from_namestringRequiredSender — must use a domain verified in your wemail workspace.
toarrayRequired[{ email, name?, type?: "to"|"cc"|"bcc" }] recipients.
subjectstringRequiredMessage subject.
html / textstringOptionalBody parts — at least one is required.
headersobjectOptionalCustom SMTP headers.
tagsarrayOptionalUp to 10 tags, echoed on events and webhooks.
metadataobjectOptionalCustom metadata, echoed on webhooks.
global_merge_vars / merge_varsarrayOptionalMerge variables, substituted like Mandrill merge tags.
track_opens / track_clicksbooleanOptionalTracking controls, mapped to wemail tracking.
send_atstringOptionalScheduled delivery (via the top-level send_at field).

Response

A successful send returns 200 with the Mandrill array — one entry per recipient: [{ _id, email, status: "sent", reject_reason: null }]. Errors return the Mandrill error object { status: "error", code, name, message } (ValidationError, InvalidKeyError, …).

POST /rejects/list.json

Returns the Mandrill rejects array: [{ email, reason, detail, created_at, last_event_at, expires_at, expired, subaccount }] with wemail suppressions mapped to Mandrill reasons (hard-bounce, spam, unsub).

Webhooks

When the Mandrill bridge is active, webhook deliveries are formatted exactly like Mandrill webhooks: an application/x-www-form-urlencoded POST with the event batch JSON in the mandrill_events field, signed with the X-Mandrill-Signature header (base64 HMAC-SHA1 over the webhook URL + sorted POST params, Mandrill's exact scheme). Event names use Mandrill vocabulary (send, hard_bounce, soft_bounce, open, click, spam, unsub, reject).

Known Deviations from Mandrill API

Deviations
ParameterTypeRequiredDescription
template_namebehaviorOptionalMandrill template slugs are not resolvable; use the wemail tpl_… id of the migrated template in template_name.
subaccounts / ip_poolbehaviorOptionalAccepted and ignored — use wemail workspaces and IP pools instead.
attachments / imagesunsupportedOptionalNot yet supported through the bridge; use the native wemail /v3/send for attachments.
async / batch splittingbehaviorOptionalThe async flag is accepted and ignored — wemail always queues asynchronously.

Code examples

cURL
curl -X POST https://api.wemail.io/bridge/mandrill/api/1.0/messages/send.json \
  -H "Content-Type: application/json" \
  -d '{
    "key": "afn_live_YOUR_KEY",
    "message": {
      "from_email": "sender@yourdomain.com",
      "to": [{ "email": "user@example.com" }],
      "subject": "Hello from the Mandrill bridge",
      "html": "<p>It works — zero code changes.</p>"
    }
  }'
Node.js
// Mailchimp Transactional SDK — point the client at the wemail bridge
const mailchimp = require('@mailchimp/mailchimp_transactional')('afn_live_YOUR_KEY');
mailchimp.setDefaultOutputFormat('json');
// The official SDK pins mandrillapp.com; for the bridge use plain fetch:
const res = await fetch('https://api.wemail.io/bridge/mandrill/api/1.0/messages/send.json', {
  method: 'POST',
  headers: { 'Content-Type': 'application/json' },
  body: JSON.stringify({
    key: 'afn_live_YOUR_KEY',
    message: {
      from_email: 'sender@yourdomain.com',
      to: [{ email: 'user@example.com' }],
      subject: 'Hello from the Mandrill bridge',
      html: '<p>It works — zero code changes.</p>',
    },
  }),
});
console.log(await res.json()); // [{ _id, email, status: 'sent', … }]
Python
import requests

resp = requests.post(
    "https://api.wemail.io/bridge/mandrill/api/1.0/messages/send.json",
    json={
        "key": "afn_live_YOUR_KEY",
        "message": {
            "from_email": "sender@yourdomain.com",
            "to": [{"email": "user@example.com"}],
            "subject": "Hello from the Mandrill bridge",
            "html": "<p>It works — zero code changes.</p>",
        },
    },
)
print(resp.status_code, resp.json())  # 200 [{'_id': 'msg_…', 'status': 'sent', ...}]