How it works
$ agentowl tenant create acme \
--webhook https://api.acme.ai/inbound
Provision a tenant with one CLI command. Set a webhook URL where payloads will be delivered.
To: support@acme.agentowl.dev
From: customer@example.com
Subject: Order #1234 issue
Hi, I need help with my order...
Emails sent to *@acme.agentowl.dev are captured automatically.
{
"channel": "email",
"from": "customer@example.com",
"to": "support@acme.agentowl.dev",
"subject": "Order #1234 issue",
"body": "Hi, I need help..."
}
Your agent receives a normalized JSON payload via webhook. Same format for email, SMS, and voice.
Features
Full SMTP server with SPF, DKIM, and DMARC validation. Receive email at any address on your tenant subdomain.
Telnyx-powered SMS and voice ingress. Provision phone numbers per tenant and receive transcribed calls.
Each tenant gets its own subdomain and webhook endpoint. Route inbound traffic to separate agent stacks.
Guaranteed delivery with exponential backoff retries. HMAC-signed payloads for verification.
Browse messages at {tenant}.agentowl.dev. Inspect payloads, delivery status, and retry history.
Manage tenants, inspect messages, and tail logs from the terminal. Scriptable and CI/CD-friendly.
Normalized payloads
Email, SMS, and voice all arrive at your webhook in the same normalized JSON structure. No channel-specific parsing required.
{
"id": "msg_01HZ3...",
"tenant": "acme",
"channel": "email",
"timestamp": "2026-03-25T14:30:00Z",
"from": {
"address": "customer@example.com",
"name": "Jane Doe"
},
"to": "support@acme.agentowl.dev",
"subject": "Order #1234 issue",
"body": {
"text": "Hi, I need help with my recent order...",
"html": "<p>Hi, I need help...</p>"
},
"attachments": [],
"headers": {
"spf": "pass",
"dkim": "pass",
"dmarc": "pass"
}
}