uChecker

Email validation for AI agents: check addresses via SMTP/MX, detect disposable, catch-all and role emails, track tasks and export clean lists.

Hosted MCP Server

npx add-mcp 'https://api.uchecker.net/mcp'

Installs into Claude Code, Codex, Cursor and more

Documentation

UChecker MCP Server

CI

An MCP server for the UChecker email validation API. It lets an AI assistant validate email addresses, track validation tasks, read per-address results and account analytics, and export cleaned lists — without you writing any API glue.

Ten tools, three resources and two guided prompts, over either stdio (local) or Streamable HTTP (remote).

Quick start

Local (stdio)

You need a UChecker API key from app.uchecker.net.

// Claude Desktop: claude_desktop_config.json
// Claude Code:    .mcp.json
{
  "mcpServers": {
    "uchecker": {
      "command": "node",
      "args": ["/path/to/mcp/build/stdio.js"],
      "env": { "UCHECKER_API_KEY": "uk_..." }
    }
  }
}

The key can also be passed as --api-key=uk_.... Build first with npm ci && npm run build.

Remote (Streamable HTTP)

A hosted instance runs at https://api.uchecker.net/mcp. It is stateless: the API key travels on every request, and no session is kept between calls.

curl -X POST https://api.uchecker.net/mcp \
  -H 'Content-Type: application/json' \
  -H 'Accept: application/json, text/event-stream' \
  -H 'x-api-key: uk_...' \
  -d '{"jsonrpc":"2.0","id":1,"method":"tools/call",
       "params":{"name":"get_account_balance","arguments":{}}}'

Authorization: Bearer uk_... works as well. Health check: GET /mcp/health. To run your own instance, see docs/DEPLOYMENT.md.

The remote endpoint authenticates with an API key header, not OAuth, so clients that can only do OAuth or cannot set custom headers need the stdio build instead.

Configuration

VariableModeDefaultPurpose
UCHECKER_API_KEYstdio—Required. Also settable via --api-key=.
UCHECKER_API_URLbothhttps://api.uchecker.netUpstream API. Also --api-url= in stdio.
UCHECKER_PUBLIC_API_URLhttphttps://api.uchecker.netURL shown to users in download hints, when the server reaches the API over an internal network.
MCP_PORThttp3009Listen port.

In HTTP mode the key is never configured server-side — it comes from the x-api-key or Authorization: Bearer header of each request, so one instance serves many accounts.

Tools

ToolWhat it doesCosts credits
validate_emailQueue one address for validation1
validate_emailsQueue a batch (max 10 000 per call)1 per address
get_task_statusStatus and progress of a task—
wait_for_taskPoll until completed/failed, with progress notifications—
get_task_resultsPer-address results, paged and filterable—
get_task_analyticsCounts, deliverability %, rejection reasons—
export_resultsSave the full result list to a file (stdio) or return a curl command (http)—
list_tasksPaginated task history—
get_account_balanceRemaining credits—
get_account_statsAccount-wide totals and averages—

Full parameter and output reference: docs/TOOLS.md.

Resources

  • uchecker://account/balance — remaining credits
  • uchecker://tasks — 20 most recent tasks
  • uchecker://tasks/{taskId}/analytics — analytics for one task

Prompts

  • clean_email_list(source?) — end-to-end workflow: check balance, validate in chunks, wait, export cleaned good/bad lists, report deliverability
  • deliverability_report() — deliverability trend across recent tasks

How validation works

Addresses are queued, not checked synchronously. validate_email and validate_emails return a task_id immediately; the task moves through pending → processing → completed. A five-address list typically finishes in well under a minute, but larger lists take proportionally longer, so:

  • prefer wait_for_task over a manual get_task_status loop — it emits MCP progress notifications while it waits and returns timed_out: true instead of hanging forever;
  • for long lists pass webhook_url and let the API call you back;
  • use get_task_analytics when you only need aggregates — it is far cheaper than pulling every row.

Each address ends up good, bad, or unknown. unknown means the check could not reach a verdict (unreachable MX, greylisting, catch-all ambiguity) — it is not a synonym for invalid.

Development

The server runs on Node 20+; the test toolchain needs Node 22.12+.

npm ci
npm run build        # tsc -> build/
npm test             # vitest, no network

A live smoke test drives the built stdio server against a real API:

UCHECKER_API_KEY=uk_... UCHECKER_API_URL=https://api.staging.uchecker.net \
  node tests/live-staging.mjs [completedTaskId]

It spends one credit on a real validate_email call, so point it at staging unless you are deliberately verifying production.

Architecture: src/core/ holds the transport-independent server (API client, tools, resources, prompts); src/stdio.ts and src/http.ts are the two entry points. Adding a tool means touching src/core/tools.ts only.

Further reading:

License

MIT