Skip to main content
EchoZero uses three distinct signing schemes depending on direction and transport. Using the wrong algorithm is the most common integration mistake.

Inbound agent HTTP signals

Endpoint: POST https://mcp.echozero.app/api/public/agent-signals/{agentId} No developer API key. Authenticate with the per-agent signing secret (ezw_...) revealed once at provision or rotation.
Always send a stable idempotencyKey on every inbound signal, including natural-language text and legacy payloads. Without it, a captured or retried signed request can execute the trade again. See Signal envelope.

Headers

Signing algorithm

  1. Serialize the request body as canonical JSON - keys sorted alphabetically at every object level, undefined fields omitted.
  2. Build: payloadString = "${unixSeconds}.${canonicalJson}"
  3. Sign: HMAC_SHA256(signingSecret, payloadString) → lowercase hex

SDK helpers

The echozero-sdk provides signInboundWebhook / sign_inbound_webhook in TypeScript, Python, Go, and Rust with canonical JSON built in.

Replay protection

  • Requests with timestamp skew beyond ±5 minutes are rejected with 401.
  • Use a unique idempotencyKey per signal so retries are safe no-ops.

Verify inbound (Python)

Golden vectors: Signature test vectors.

Outbound execution webhooks

When your agent has a webhookUrl, EchoZero POSTs execution results after trade attempts.

Signing secret

Use the agent webhook signing secret configured on the agent (webhookUrl + secret pair). Rotate by updating the agent record in Dev Portal or PATCH /api/v1/agents/{id}.

Delivery contract

Event catalog

Verify on your server

Headers:
Reject requests outside a 5-minute timestamp window and treat duplicate signalId deliveries as idempotent.

Provider webhooks (Telegram, Discord)

When EchoZero hosts signal ingestion for Telegram or Discord bots, provider-specific secrets apply. These routes do not use developer API keys.

Telegram

Endpoint: POST /api/webhooks/telegram/signal-bot When the server has SIGNAL_TELEGRAM_WEBHOOK_SECRET configured, every request must include:
Configure this when registering your bot webhook via Telegram’s setWebhook API.

Discord

Endpoint: POST /api/webhooks/discord/signal-bot When SIGNAL_DISCORD_WEBHOOK_SECRET is set:
Used when Discord Gateway ingest is off or for webhook-based testing.

REST API HMAC (developer routes)

For authenticated developer API calls (/api/v1/*), HMAC uses your API secret with millisecond timestamps and method+path signing. See API keys and HMAC.
Do not use REST API HMAC headers (x-signature / x-timestamp) on inbound agent signal POSTs. Agent ingress requires X-EZ-Signature / X-EZ-Timestamp with the per-agent ezw_ secret.

Security checklist

  • Store signing secrets in a secrets manager - they are shown only once at creation/rotation.
  • Use HTTPS for all webhook URLs.
  • Enforce timestamp windows on every inbound webhook you receive.
  • Deduplicate by idempotencyKey (inbound) or signalId (outbound).
  • Rotate compromised secrets via rotateInboundWebhookSigningSecret or API key revocation in the Dev Portal.