Checking your session…

Intake Forms

Some conversations need more than a chat can comfortably collect — full contact details, structured questionnaires, sign-up information. Intake forms solve this: during a booking, the platform can text the person a link to a hosted form; their answers come back as intake records your team can read, and are then handed on to your connected system and purged on a schedule. No third-party form builder, no copy-paste.

The two endpoints here are the read surface over those records — the list your team works from, and the detail view they read the answers from. Both are gated by view_intakes, which is its own permission (rather than riding along with booking config) because submissions can carry sensitive personal details. The baseline is Owner + Manager; it's revocable per user with -view_intakes and grantable to staff with +view_intakes.

Requires view_intakes. Returns answer-free summary rows — never the questionnaire answers. Supports a status filter and offset/limit pagination.

Query params:

  • status — filter to one lifecycle status (pending | received | transferred | purged).
  • limit — page size, default 50, capped at 200.
  • offset — default 0.

Response (200):

total is the full count after the status filter; intakes is the current page. Rows are sorted newest-first by creation time, and include every submission for the app, whether it arrived before or after the app went live.

GET/api/v1/apps/{appId}/intakesview_intakes
curl "https://api.everycallhandled.com/api/v1/apps/$APP_ID/intakes?status=received&limit=50" \
  -H 'Authorization: Bearer YOUR_TOKEN'
Sign in to run this against your account.
JSON
{
  "intakes": [
    {
      "id": "el_intake_9f2a",
      "status": "received",
      "firstName": "Priya",
      "phone": "+447700900123",
      "typeKey": "initial_consult",
      "bookingId": "bk_5521",
      "submittedAt": "2026-07-10T14:32:07.000Z",
      "transferredAt": "",
      "created": "2026-07-10T13:05:00.000Z"
    }
  ],
  "total": 1,
  "limit": 50,
  "offset": 0
}

Requires view_intakes. Returns the full record including the answers blob — the read your team uses for a confirming call, or for manual entry into a connected system. The record must belong to this app; a mismatched or unknown id returns 404 Intake not found. The form link's security token is never returned.

Response (200):

GET/api/v1/apps/{appId}/intakes/{intakeId}view_intakes
curl 'https://api.everycallhandled.com/api/v1/apps/{appId}/intakes/{intakeId}' \
  -H 'Authorization: Bearer YOUR_TOKEN'
Sign in to run this against your account.
JSON
{
  "id": "el_intake_9f2a",
  "status": "received",
  "appId": "app_9f31",
  "bookingId": "bk_5521",
  "patientId": "",  /* the matched record id in a connected system such as Semble */
  "firstName": "Priya",
  "phone": "+447700900123",
  "typeKey": "initial_consult",
  "submittedAt": "2026-07-10T14:32:07.000Z",
  "transferredAt": "",
  "purgeAfter": "",
  "formVersion": 1,
  "answers": {
    "firstName": "Priya",
    "lastName": "Sharma",
    "dob": "1990-04-12",
    "email": "priya@example.com",
    "postcode": "W1G 6BW",
    "payer": "Self-Pay"
  }
}

An intake moves through four statuses:

  • pending — the booking created the record and texted the signed link, but the person hasn't submitted yet. No answers on file.
  • received — the person submitted the form. The answers blob is populated and submittedAt is stamped. Resubmitting on an open link replaces the answers in place.
  • transferred — the platform has written the details into your connected system (for example Semble) and confirmed it. transferredAt is stamped, and purgeAfter is set to the retention deadline. Answers are still readable during the grace window.
  • purged — the grace window elapsed and the answers blob has been wiped. The row still exists (status, identity, timestamps) but answers is gone.

Intake answers can carry sensitive personal data, so they're held only as long as they're operationally needed. Retention runs in two phases:

  1. Transfer — a received intake with a matched record is written into your connected system, then marked transferred and stamped purgeAfter = now + purgeGraceDays (the app's configured grace window, default 7 days, range 1–60). A received record with no matched record or a corrupted/empty answers blob is left alone for a human to sort out — it is never silently dropped.
  2. Purge — once a transferred intake passes its purgeAfter deadline, the answers are blanked and the status becomes purged. The wipe is verified before the record is reported as purged.

Treat answers as transient: available while pendingreceivedtransferred, and gone once purged. Build any downstream capture of intake answers to happen before the grace window closes; after that, only the summary metadata survives.