Sending Emails
Send emails from your inboxes with text, HTML, and attachments.
Last updated 2026-03-29
Sending requires Tier 1 or above. Free accounts (Tier 0) can only receive email. To unlock sending, verify via X (Twitter) or add a payment method through Stripe.
Upgrading to Tier 1#
The fastest path is X verification. Post a tweet tagging @lobster_mail that includes your account ID, then submit the tweet URL:
POST /v1/verify/x
{ "tweetUrl": "https://x.com/your_handle/status/123456789" }
Alternatively, subscribe to a paid tier via POST /v1/billing/checkout.
Sending an Email#
const inbox = await lm.createInbox();
const result = await inbox.send({
to: ['recipient@example.com'],
subject: 'Hello from my agent',
body: { text: 'This email was sent by an AI agent via LobsterMail.' },
});
Send Options#
| Option | Type | Required | Description |
|---|---|---|---|
to | string[] | Yes | Recipient addresses (1-50). |
subject | string | Yes | Subject line. |
body | { text?: string; html?: string } | Yes | Email body. At least one of text or html is required. When only html is provided, a plain-text version is auto-generated. |
cc | string[] | No | CC recipients. |
inReplyTo | string | No | Message-ID of the email being replied to. Enables threading. |
threadId | string | No | Explicit thread ID to associate this email with. |
attachments | Attachment[] | No | File attachments (see below). |
Attachments#
Attachment content must be a base64-encoded string. Max 10 attachments per message.
import { readFileSync } from 'node:fs';
const pdfBytes = readFileSync('report.pdf');
await inbox.send({
to: ['recipient@example.com'],
subject: 'Report attached',
body: { text: 'Please find the report attached.' },
attachments: [
{
filename: 'report.pdf',
content: pdfBytes.toString('base64'),
contentType: 'application/pdf',
},
],
});
Replying to Emails (Threading)#
To reply within a conversation thread, include the inReplyTo field with the Message-ID of the email you're replying to. LobsterMail automatically sets In-Reply-To and References MIME headers and associates the outgoing email with the correct thread.
await inbox.send({
to: ['billing@example.com'],
subject: 'Re: Invoice #1234',
body: { text: 'Thanks, received the invoice.' },
inReplyTo: '<original-message-id@example.com>',
});
See the Threads guide for more details on conversation threading.
Asynchronous Delivery#
inbox.send() returns a response immediately. The email is queued for delivery, not sent synchronously. The response includes an id you can use to track delivery status.
const result = await inbox.send({
to: ['recipient@example.com'],
subject: 'Queued',
body: { text: 'This will be delivered shortly.' },
});
console.log(result.id); // eml_abc123
console.log(result.status); // 'queued'
Daily Sending Limits#
| Tier | Daily Limit |
|---|---|
| Free (Tier 0) | Cannot send |
| Free Verified (Tier 1) | 10 emails/day |
| Builder (Tier 2) | 500 emails/day |
| Pro (Tier 3) | 1,000 emails/day |
| Scale (Tier 4) | 10,000 emails/day |
Exceeding the limit returns a 429 Too Many Requests error. Limits reset at midnight UTC.
Best Practices#
- Including a plain text
body.textalongside HTML is recommended for compatibility, but not required — a text version is auto-generated from HTML when omitted. - Keep attachments under 10 MB total per message.