API reference
The PAD HTTP API is documented as OpenAPI 3.1 at /v1/openapi.json. Point Swagger UI, Postman, or your favorite OpenAPI codegen at it.
Authentication
Every request includes Authorization: Bearer <api_key>. Create keys at /dashboard/settings/api-keys; pick the right scope:
browser— safe to ship to the client; limited to event tracking + identifyserver— full read + write; never embed in a client appadmin— workspace admin operations (rare)
Quick start (curl)
# Identify a profile
curl -X POST https://pad.thevisualpay.com/v1/profiles \
-H "Authorization: Bearer pad_sk_..." \
-H "Content-Type: application/json" \
-d '{"externalId":"u_42","email":"ada@acme.com","traits":{"plan":"pro"}}'
# Track an event (triggers campaigns)
curl -X POST https://pad.thevisualpay.com/v1/events \
-H "Authorization: Bearer pad_sk_..." \
-H "Content-Type: application/json" \
-d '{"event":"checkout.completed","externalId":"u_42","properties":{"amount":99}}'
# Send a transactional email
curl -X POST https://pad.thevisualpay.com/v1/sends \
-H "Authorization: Bearer pad_sk_..." \
-H "Content-Type: application/json" \
-d '{"template":"welcome","to":"u_42","variables":{"firstName":"Ada"}}'
# Poll send status
curl https://pad.thevisualpay.com/v1/sends/<send_id> \
-H "Authorization: Bearer pad_sk_..."Endpoints
POST /v1/profiles— upsert a profileGET /v1/profiles/{id}— fetch by id or external idPOST /v1/events— track a single event (triggers campaigns)POST /v1/events/bulk— ingest up to 500 events (no campaign enqueue)GET /v1/events/list— cursor-paginated listPOST /v1/sends— send a transactional or marketing emailGET /v1/sends/{id}— fetch a send + timestamp ladderGET /v1/sends/list— cursor-paginated listPOST /v1/consents— record consent for (profile, channel, category)
Pagination
List endpoints return { data: [...], nextCursor }. Pass nextCursor back in the next request to fetch the next page. nextCursor: null means end-of-list.
Idempotency
Both /v1/events and /v1/sends accept an idempotencyKey. Resubmitting the same key returns the original result with idempotent: true. Keep keys unique per logical operation (e.g. checkout_42_2026-05-20).
Errors
All errors are JSON with shape { error: { message, code? } }. 401 = bad auth. 400 = bad request body. 404 = resource not in this workspace. 5xx = retry with exponential backoff.
Webhooks
PAD can also POST events to you — see webhooks for the signed outbound delivery contract.