> ## Documentation Index
> Fetch the complete documentation index at: https://docs.xpander.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Email

> The mail xpander sends, and the inbox an agent can have, on cloud and self-hosted installs.

| Path | xpander cloud | Hybrid and Air-Gapped |
| - | - | - |
| [Transactional email](#transactional-email): sign-in codes, run notifications, approval requests, an agent's send-email action | xpander's SendGrid and Mailgun accounts | Your SMTP relay |
| [An inbox for an agent](#an-inbox-for-an-agent): mail sent to an agent becomes a run | `<agent-name>@xpander.bot` | Your own mailboxes at `<handle>@<your reply domain>` |

## Transactional email

On a self-hosted install, set your SMTP relay once in the chart: `global.smtp.host`, `port` (587), `starttls`, `user`, `passwordSecret.name` and `.key` (a Secret you create), `adminEmail` and `senderName`. It feeds sign-in mail, invitations and notifications, rendered into `XPANDER_EMAIL_DELIVERY`. No mail leaves the cluster to xpander, and outbound mail goes only to that relay.

### Amazon SES in the sandbox

A new SES account delivers only to verified identities. Request production access before you invite members, and create the DKIM, MAIL FROM and DMARC records SES gives you. Until then, an invite to an unverified address fails with `554 Access denied ... not authorized to perform 'ses:SendRawEmail' on resource ...:identity/<recipient>`. To invite earlier, verify each recipient in SES and add its identity ARN to the `Resource` list of the SMTP IAM user's `ses:SendRawEmail` policy.

### Sign in without SMTP

Without SMTP, the email code is never sent. On an Air-Gapped install, enter the email on the login page, then get the code from the cluster:

```bash theme={"dark"}
NS="<namespace>"
EMAIL="<email>"
KEY=$(kubectl -n "$NS" get secret xpander-generated-keys -o jsonpath='{.data.SUPABASE_SERVICE_KEY}' | base64 -d)
kubectl -n "$NS" exec deploy/supabase-auth -- wget -qO- \
  --header "Authorization: Bearer $KEY" --header "Content-Type: application/json" \
  --post-data "{\"type\":\"magiclink\",\"email\":\"$EMAIL\"}" \
  http://localhost:9999/admin/generate_link | sed -n 's/.*"email_otp":"\([0-9]*\)".*/\1/p'
```

Type the printed code into the login page. Each new code replaces the previous one. Per-agent run notifications are on [Budgets and notifications](https://docs.xpander.ai/use/agents/budgets.md).

## An inbox for an agent

### On xpander cloud

The **Email** switch on an agent's Channels pane gives it `<agent-name>@xpander.bot`. Mail and forwards to it become runs, attributed to the sender. **Reply to newsletters** (off by default) decides whether mailing-list mail gets a reply. The run happens either way.

### On a self-hosted installation

Every agent gets `<handle>@<your reply domain>`. The API accepts mail at `POST /v1/inbound/email?token=<INBOUND_EMAIL_TOKEN>` in Mailgun's store-and-notify shape and checks the token and the Mailgun signature. Set on the chart:

```yaml theme={"dark"}
api:
  env:
    INBOUND_EMAIL_REPLY_DOMAIN: agents.xpander.acme.example   # the agents' address domain
  extraEnv:                          # both from a Secret you create
    - name: INBOUND_EMAIL_TOKEN
      valueFrom: { secretKeyRef: { name: xpander-inbound-mail, key: token } }
    - name: MAILGUN_SIGNING_KEY
      valueFrom: { secretKeyRef: { name: xpander-inbound-mail, key: signing-key } }
ui:
  env:
    VITE_EMAIL_DOMAIN: agents.xpander.acme.example
```

Deliver the mail with a Mailgun route to the endpoint, or with Amazon SES into an S3 bucket plus a small job that posts each object to it. Two SES facts cost time:

1. SES receives only in some regions. If the cluster's region does not, put the receiving rule and its bucket in one that does.
2. The bucket policy must grant SES with `aws:SourceAccount`, not the legacy `aws:Referer`, or SES bounces mail silently.

`mailgun.net` and `sendgrid.com` are in the egress allowlist only for xpander cloud. A self-hosted install needs neither.

## Next steps

> **[Set run notifications for an agent](https://docs.xpander.ai/use/agents/budgets.md)**
>
> On success and on error

> **[Route channels to an agent](https://docs.xpander.ai/use/agents/channels.md#what-your-administrator-controls)**
>
> Channels on a self-hosted install


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.