# Command line interface

> The EmailVerify Pro CLI exposes all 152 API endpoints as shell commands. Install with pipx or npm, verify addresses, clean CSV files, script it in CI.

Source: https://emailverifypro.com/docs/cli

A command for every one of the 152 API endpoints, generated from the OpenAPI spec — so
the moment an endpoint ships, it has a command. The common operations also get short
aliases.

## Install

```bash
pipx install emailverify
```

```bash
npm install -g @emailverifypro/mcp
```

Both packages install the same `emailverify` command with the same behaviour. Pick
whichever matches your stack. The Python build has **no runtime dependencies**; the Node
build needs Node 18 or newer.

Run it without installing anything:

```bash
uvx --from emailverify emailverify verify someone@example.com
```

```bash
npx -y @emailverifypro/mcp emailverify verify someone@example.com
```

## Authenticate once

```bash
emailverify login
```

Prompts for your key and writes `~/.config/emailverify/config.json` with mode `600`.
Precedence, highest first:

1. `--api-key` on the command line
2. `EMAILVERIFY_API_KEY` in the environment
3. the config file

```bash
emailverify config     # show which key and base URL are in effect
emailverify logout     # forget the stored key
```

## Verify

```bash
emailverify verify someone@example.com
```

```
VALID  someone@example.com  (mailbox_verified)  score=96 A+  can_send=yes
```

The summary line is colourised by status: green `VALID`, red `INVALID`, amber
`ACCEPT_ALL`, grey `UNKNOWN`. Add `--json` for the full response:

```bash
emailverify verify someone@example.com --json
```

Pipe it straight into `jq`:

```bash
emailverify verify someone@example.com --json | jq -r '.deliverability_score.can_send'
```

Turn signals on and off:

```bash
emailverify verify someone@example.com --smtp false --breach true --enrich true
```

## Verify a file

```bash
emailverify bulk --file leads.csv --out results.json
```

`--file` accepts:

- one address per line
- a JSON array — `["a@x.com", "b@y.com"]`
- a CSV — it picks the column containing an `@`
- `-` to read standard input

```bash
cut -d, -f3 crm-export.csv | emailverify bulk --file - --out results.json
```

Bulk calls take as long as their slowest address, so raise the timeout for big batches:

```bash
emailverify bulk --file big-list.txt --timeout 600 --out results.json
```

## Discover commands

```bash
emailverify list                      # everything, grouped by category
emailverify list --tag Verification   # one category
emailverify list --search catchall    # search paths, names and descriptions
emailverify describe validate:bulk    # parameters for one command
```

`describe` prints the method, path, every parameter with its type and default, and
whether the command is destructive.

## Call anything

Named commands cover every endpoint, but `raw` bypasses them entirely:

```bash
emailverify raw GET /db/stats
emailverify raw GET /validate --query email=a@b.com --query smtp=false
emailverify raw POST /bounce --body '{"email":"a@b.com","bounce_type":"hard"}'
```

## Aliases

| Command | Endpoint | What it does |
|---|---|---|
| `emailverify verify` | `GET /validate` | Validate Get |
| `emailverify bulk` | `POST /validate/bulk` | Validate Bulk |
| `emailverify bulk-async` | `POST /validate/bulk/async` | Validate Bulk Async |
| `emailverify quick` | `GET /validate/quick` | Validate Quick |
| `emailverify syntax` | `GET /validate/syntax` | Validate Syntax Only |
| `emailverify score` | `GET /score` | Get Deliverability Score |
| `emailverify find-email` | `POST /find-email` | Find Email Endpoint |
| `emailverify domain` | `GET /domain-intel/{domain}` | Get Domain Intel |
| `emailverify usage` | `GET /me/usage` | Me Usage |
| `emailverify stats` | `GET /me/stats` | Me Stats |
| `emailverify recent` | `GET /me/recent-verifications` | Me Recent Verifications |
| `emailverify keys` | `GET /keys` | List Keys |
| `emailverify create-key` | `POST /keys` | Create Key |
| `emailverify health` | `GET /health` | Health |
| `emailverify plans` | `GET /plans` | Get Plans |
| `emailverify suppress` | `POST /suppression/add` | Suppression Add |
| `emailverify suppressed` | `GET /suppression/check` | Suppression Check |
| `emailverify dedup` | `POST /utils/dedup` | Dedup Emails |
| `emailverify catchall` | `POST /resolve-catchall` | Resolve Catchall Endpoint |
| `emailverify job` | `GET /jobs/{job_id}` | Get Job |

Everything else follows the endpoint path — `/validate/bulk/async` becomes
`validate:bulk:async`, `/jobs/{job_id}` becomes `jobs:job-id`.

## Destructive commands

Deletes and admin operations prompt before running, and refuse outright when not attached
to a terminal:

```bash
emailverify gdpr:erase someone@example.com
```

```
About to call DELETE /gdpr/erase — this is destructive.
Type 'yes' to continue:
```

Pass `--yes` in scripts. Without a terminal and without `--yes`, the command exits `2`
rather than guessing.

## Scripting

Exit codes are stable, so you can branch on them:

| Code | Meaning |
|---|---|
| `0` | Success |
| `1` | Unknown command, or the user declined a confirmation |
| `2` | Bad arguments — a required parameter is missing |
| `3` | Authentication failed |
| `4` | API or transport error |

```bash
#!/usr/bin/env bash
set -euo pipefail

if emailverify verify "$1" --json | jq -e '.deliverability_score.can_send' >/dev/null; then
  echo "safe to send"
else
  echo "do not send"; exit 1
fi
```

Verify a list and keep only the good ones:

```bash
emailverify bulk --file leads.txt --json \
  | jq -r '.results[] | select(.status=="valid") | .email' \
  > clean.txt
```

Set `NO_COLOR=1` to strip ANSI codes when writing to a log.

## Global flags

| Flag | Purpose |
|---|---|
| `--json` | Full JSON instead of the summary line |
| `--out PATH` | Write the JSON response to a file |
| `--file PATH` | Read a list argument from a file (`-` for stdin) |
| `--yes`, `-y` | Skip the confirmation on destructive commands |
| `--api-key KEY` | Override the stored key |
| `--base-url URL` | Point at staging or a self-hosted instance |
| `--timeout SECONDS` | Per-request timeout, default 60 |
| `--verbose`, `-v` | Log the request line to stderr |

## Environment

| Variable | Purpose |
|---|---|
| `EMAILVERIFY_API_KEY` | Your key; overrides the config file |
| `EMAILVERIFY_BASE_URL` | Staging or self-hosted instance |
| `EMAILVERIFY_CONFIG` | Alternative config file path |
| `EMAILVERIFY_CA_BUNDLE` | CA bundle, if your Python has none |
| `NO_COLOR` | Disable colour |

## Troubleshooting

**`CERTIFICATE_VERIFY_FAILED`** — your Python has no CA bundle, common on python.org
macOS builds. Run *Install Certificates.command*, or `pip install certifi`, or set
`EMAILVERIFY_CA_BUNDLE=/etc/ssl/cert.pem`.

**`error: unknown command 'verifyy'`** — the CLI suggests the nearest matches. Run
`emailverify list` to see everything.

**A command hangs** — some verifications take 30 seconds or more. Raise `--timeout`, or
use `emailverify bulk-async` and poll with `emailverify job <job_id>`.

**`401` on a key you just created** — keys take up to 2 minutes to replicate to every
verification worker. Wait and retry.
