# Verification codes and magic links

Source: https://agentboxd.com/docs/verification-codes

> Let an agent sign up for a service with its own address and read the code or link it receives.

Agents that sign up for things need to read a login code or click a magic link. Agentboxd pulls both out of every inbound message and gives you a long-poll endpoint that waits for them.

## The flow

- Create (or reuse) an inbox for the agent.
- Record the time, **before** triggering the email.
- Have the agent submit the sign-up form with the inbox address.
- Call `waitForVerification` with that time as `since`. It returns as soon as a matching email arrives.

signup.ts:

```ts
const inbox = await mr.inboxes.create({ client_id: 'signup-agent' });
const since = new Date().toISOString(); // record the time before you trigger the email

await signUp({ email: inbox.address }); // your agent fills in the form

const v = await mr.messages.waitForVerification(inbox.id, {
  since,
  from: 'github.com',
  timeout: 60,
});
if (!v) throw new Error('no verification email within 60 s');

console.log(v.code ?? v.link, v.confidence); // "48213907" 1

```

signup.py:

```python
from datetime import datetime, timezone

inbox = mr.inboxes.create(client_id="signup-agent")
since = datetime.now(timezone.utc).isoformat()

sign_up(email=inbox["address"])  # your agent fills in the form

v = mr.messages.wait_for_verification(inbox["id"], since=since, from_="github.com", timeout=60)
if v is None:
    raise RuntimeError("no verification email within 60 s")
print(v["code"] or v["link"], v["confidence"])

```

> **Note:** Pass `since`. The wait calls only count mail that arrives after the request starts, so an email that lands between the form submit and your call would otherwise be missed.

## What comes back

GET /v1/inboxes/:id/verification:

```json
{
  "data": {
    "code": "48213907",
    "link": null,
    "confidence": 1,
    "jev_probability": 0.99,
    "auth_failed": false,
    "message_id": "a0000000-…",
    "from": "GitHub <noreply@github.com>",
    "subject": "Your GitHub launch code",
    "received_at": "2026-09-24T12:00:04.000Z"
  }
}
```

## How detection works

Detection is deterministic first. A number or code only counts when it sits close to a word like “code”, “verification” or “one-time”, and anything that looks like a phone number, date, price, year or order number is dropped. Regex results are capped at confidence 0.7.

Then JEV, a fast decision model, answers “is this a login, one-time-code or confirm-your-email message?”. If its probability is 0.8 or more, confidence rises to at least 0.95; under 0.2, it drops to at most 0.2. In our tests, a login-code email was classified as verification with confidence 1.00.

Every message also carries `ai.verification`, so you can read codes from `messages.list` or a webhook too.

## Safety

Only use a code or link for a sign-up your agent started. A code in an unexpected email is a phishing signal, not an instruction. The MCP server tells models the same thing.

Mail whose sender failed authentication may be spoofed: DMARC failed (label `dmarc-fail`), or SPF failed (`spf-fail`) and no passing DKIM signature matches the From domain. Its code or link carries `auth_failed: true`, and `GET /v1/inboxes/:id/verification` skips it, so a spoofer can’t hand your agent a code. If you just asked for a code and nothing else comes, pass `include_unauthenticated=true` (MCP: `include_unauthenticated: true`) to get it anyway, flagged. The dashboard shows such a code as a warning, without a Copy button.
