Skip to content
API Documentation

Build on AMES Platform

REST API for your operational and marketing data — members, classes, schedule, bookings, contacts, campaigns and real-time webhooks — secured with scoped API keys.

API Key Authentication

Scoped API keys (Authorization: Bearer amk_…) with per-key permissions like members:read and bookings:read, per-key rate limits and instant revocation.

RESTful Endpoints

Clean REST API over your operational and marketing data: members, classes, schedule, bookings, contacts, campaigns, segments and tags.

Webhooks

Subscribe to real-time marketing and booking events with HMAC-signed deliveries and automatic retries.

Tenant-Scoped

Every key is bound to your organisation. Responses only ever contain your tenant's data.

Available Endpoints

Authorization: Bearer amk_your_api_key

Read endpoints return { data, next_cursor } — pass next_cursor back as ?cursor= until it is null. Member medical and consent fields additionally require the members:sensitive scope and are otherwise omitted.

Operations

GET/api/v1/membersmembers:read
GET/api/v1/members/{id}members:read
GET/api/v1/classesclasses:read
GET/api/v1/scheduleclasses:read
GET/api/v1/bookingsbookings:read

Marketing

GET/api/v1/contactscontacts:read
POST/api/v1/contactscontacts:write
GET/api/v1/contacts/{id}contacts:read
POST/api/v1/contacts/unsubscribecontacts:unsubscribe
GET/api/v1/campaignscampaigns:read
GET/api/v1/campaigns/{id}/statscampaigns:read
GET/api/v1/segmentssegments:read
GET/api/v1/tagstags:read
POST/api/v1/webhooks/subscribewebhooks:manage

Webhook Events

Deliveries are signed (HMAC-SHA256, Stripe-style timestamped header), retried with backoff and deduplicated by event id. Subscribing to booking.* events requires the bookings:read scope; contact.* events require contacts:read. Booking events cover server-side flows (Connect bookings and cancellations, register and admin attendance marks).

booking.created
booking.cancelled
booking.attended
contact.created
contact.updated
contact.unsubscribed
campaign.sent
form.submitted

Sample payload (booking.created)

{
  "id": "5f1c9a4e-…",                // unique event id — dedupe on this
  "type": "booking.created",
  "version": "1",                    // payload schema version
  "tenant_id": "9d2b4c1a-…",
  "created_at": "2026-07-13T09:30:00.000Z",
  "data": {
    "booking": {
      "id": "b2a7e310-…",
      "booking_type": "drop_in",     // "drop_in" | "class"
      "class_id": "c4d8f221-…",
      "member_id": "a1b2c3d4-…",
      "class_date": "2026-07-15",
      "status": "booked",
      "amount_paid_pence": 1200,
      "authorization_source": "payg"
    },
    "class": { "id": "c4d8f221-…", "name": "Adult Swim Fitness" },
    "context": { "source": "connect" }
  }
}

Verifying signatures

// Verify X-AMES-Signature (Node.js)
// Header format: t=<unix seconds>,v1=<hex hmac-sha256>
// Signed message: `${t}.${rawBody}` with your verification secret
// (shown once when the webhook was created). Reject stale timestamps.
import { createHmac, timingSafeEqual } from "crypto";

function verify(rawBody, header, secret, toleranceSec = 60) {
  const { t, v1 } = Object.fromEntries(
    header.split(",").map((kv) => kv.split("=").map((s) => s.trim())),
  );
  if (!t || !v1) return false;
  if (Math.abs(Date.now() / 1000 - Number(t)) > toleranceSec) return false;
  const expected = createHmac("sha256", secret)
    .update(`${t}.${rawBody}`)
    .digest("hex");
  const a = Buffer.from(expected);
  const b = Buffer.from(v1);
  return a.length === b.length && timingSafeEqual(a, b);
}

Coming soon

Not yet available

On the roadmap — these are not part of the API today:

  • Payments and invoices endpoints
  • Write access for members and bookings
  • OAuth 2.0 authorisation flows
  • Official SDKs (JavaScript, Python, PHP)

API access is available on Professional and Enterprise plans.

Request API Access