Surfil

Public API

The public edge API lives at api.surfil.com- stateless Cloudflare Workers that authenticate, meter, and sign. You rarely call it directly: the on-device runtime and the Hub are its normal clients. It's documented here so you can see exactly what crosses the wire.

Conventions

  • Versioned REST over HTTPS - every endpoint is under a version prefix (/v1/…); breaking changes mean a new version, not a mutated old one.
  • Idempotency keys - every state-mutating request carries one. Retries are safe by contract; a duplicated consume never double-charges.
  • Signed batches - device-to-edge telemetry arrives as signed batches over mTLS, and it is metadata only. Source code has no endpoint to arrive at.
  • Signed responses - value-outputs are Ed25519-signed and verifiable offline; the server's word is checkable after the fact.

Endpoints

  • /v1/auth/device/* - Device flow (RFC 8628) - request and poll for a device token.
  • /v1/devices - Register and manage devices tied to an account.
  • /v1/entitlement - Read current plan, allowances, and Credit balance.
  • /v1/meter/consume - Atomically, idempotently decrement a Credit for a signed output.
  • /v1/sign - Produce an Ed25519-signed output for a consumed operation.
  • /v1/verify - Verify a signed output's signature.
  • /v1/receipt - Fetch a signed savings receipt.
  • /v1/ingest/batch - Accept a signed batch of metadata-only telemetry from the device runtime.
  • /v1/billing/webhook - Receives billing provider webhooks.

Auth models

The API accepts three credential types depending on the caller:

  • Device token - an Ed25519 device token issued via the device flow, used by the on-device runtime.
  • Supabase session - used by the Hub (this dashboard) for account-scoped requests.
  • Stripe signature - used to verify inbound /v1/billing/webhook calls come from Stripe.

What's documented - and what isn't yet

The list above is the shape of the API: real endpoints, real conventions. Full request/response schemas, error codes, and rate limits are maintained in the OpenAPI specification and are not yet published publicly.

We publish what's verified rather than inventing detail. If a field, flag, or error shape isn't on this page, treat it as undocumented - this page will grow as the public OpenAPI document is released, not ahead of it.
  • Credits - the semantics behind /v1/meter/consume.
  • Signed outputs - the semantics behind /v1/sign and /v1/verify.
  • Zero-trace - why /v1/ingest/batch only ever sees metadata.