Skip to main content

Quickstart

This public documentation can be read without credentials. Calling the API requires a credential manually issued by Hermes for an approved server-to-server integration.

1. Obtain and store a credential

Request access from info@phishinghermes.com. Keep the issued key in a backend secrets manager and expose it only to the calling process:

export HERMES_API_BASE_URL="https://api.phishinghermes.com"
export HERMES_API_KEY="<read-from-your-secret-manager>"

Windows PowerShell 5.1 or PowerShell 7:

$env:HERMES_API_BASE_URL = "https://api.phishinghermes.com"
$env:HERMES_API_KEY = "<read-from-your-secret-manager>"

2. Use the synthetic message

Download synthetic-safe.eml. It uses reserved example domains and contains no credential, active link, attachment, or customer data.

3. Create one operation key

Generate the idempotency key once and keep it with the message bytes until the operation reaches a terminal outcome:

quickstart-0b8c29c8-491a-4a8d-a832-58e5417e065f

The key must contain 8–128 safe ASCII characters. A retry of this operation reuses the same key and the exact same bytes. A different logical submission needs a new key.

4. Submit the message

Download one of the complete clients. Each client reads the EML once as bytes, generates one idempotency key, applies at most four attempts with an overall deadline, handles RFC 9457 Problems, and preserves the same key and bytes during safe retries:

Run the downloaded client beside synthetic-safe.eml:

bash curl.sh synthetic-safe.eml

The PowerShell client uses .NET HttpClient and ByteArrayContent, so its body handling is consistent in Windows PowerShell 5.1 and PowerShell 7. The Bash client snapshots the file before its first cURL call. The Python and Node.js clients retain one byte buffer in memory.

All four are executed against a local contractual mock in CI. Validation never calls production.

5. Interpret a complete result

{
"analysis_id": "00000000-0000-4000-8000-000000000001",
"status": "completed",
"verdict": "no_threat_detected",
"risk": "none",
"completeness": "complete",
"signal_codes": [],
"warnings": [],
"created_at": "2026-09-10T12:00:00Z",
"schema_version": "1.0",
"request_id": "req_quickstart_0001"
}

The verdict shown is illustrative, not a promise for the sample.

6. Interpret partial or inconclusive results

A confirmed threat remains phishing or suspicious when another applicable area is incomplete, but completeness becomes partial and a warning explains the affected category.

If no threat is confirmed and an applicable area is incomplete, Hermes returns inconclusive, unknown, and partial. Never convert that combination into “safe.” See Result model.

7. Handle errors and retries

Errors use application/problem+json. Read status, code, and request_id; do not log the EML or credential. Retry only network-unknown outcomes and 408, 429, 500, or 503, with bounded exponential backoff and jitter. Preserve the same idempotency key and bytes. Do not retry permanent 4xx errors automatically.

Respect Retry-After when present. It is not present on every retryable response. If bounded retries fail, stop and provide the latest request_id, status, code, and approximate UTC time to support.