Skip to main content

HIPAA readiness checklist — pre-go-live runbook

The HIPAA/BAA readiness checklist is a free, browser-side self-assessment on the developer tools hub. Mark the five tenant-owned steps you have covered and the panel scores your readiness, linking each open item to the page that configures it — no account required. This runbook takes that checklist from a score to a go/no-go decision: it maps each step to the exact control that sets it, walks the five steps in order against a live workspace, and ends with a test PHI send that proves the send-time gate passes. The BAA flow remains the authoritative reference for the state-machine vocabulary; this page is the operator sequence.
Every step is tenant-owned: you decide whether Protected Health Information (PHI) is in scope and configure the controls on your own workspace. Orbit supplies the e-sign pipeline and the enforcement point — the send-time gate that rejects PHI traffic with HIPAA_BAA_REQUIRED until a BAA is executed — but the legal determination that PHI is in scope is yours to make with counsel. The checklist reports the coverage you self-attest; it does not enforce it. This tool is not legal advice.

Where each step runs

One deep destination per step — the checklist item and the table above both point to the same page, so a visitor and an operator land on the same control.

Walk the five steps

Run these in order on the workspace you intend to take live. Steps 1–2 are owner-level acts; steps 3–5 are operator verifications.

Step 1 — Attest that PHI is in scope

  1. Open Settings → Compliance → BAA in the dashboard.
  2. Confirm the current state: for a fresh organization it reads not_required (no PHI declared).
  3. Click “Start handling PHI” (or call POST /api/v1/compliance/baa/require with an optional recorded reason).
  4. The state moves to pending and the execute form opens — the attestation is the event that raises hipaa_required, and it appends a compliance.baa.hipaa_required audit entry.
Checklist signal: mark step 1 covered when GET /api/v1/compliance/baa reads hipaa_required: true and baa_status: pending. Full endpoint detail in the BAA flow.

Step 2 — Execute the BAA

  1. While the state is pending, an owner opens the execute form on the same page (POST /api/v1/compliance/baa/execute).
  2. Preview the rendered template (organization legal name filled in), then type the signer’s legal name into typed_attestation — the server requires it to match signer_name exactly and rejects a mismatch with 400.
  3. On success the API returns baa_status: executed with the stored document reference, expires_at one year out, and days_until_expiry: 365.
Checklist signal: mark step 2 covered when GET /api/v1/compliance/baa reads executed. Only executed satisfies the gates; the roles matrix (owner/admin read, owner execute) is in the BAA flow.

Step 3 — Enable HIPAA mode

  1. With the BAA executed, enable HIPAA mode from Settings → Compliance → HIPAA controls (PUT /api/v1/settings/hipaa).
  2. The call refuses with 403 while the BAA is any state other than executed; disabling later requires re-authentication.
  3. Flipping it on engages the PHI control set: PHI access logging, enforced retention, residency pinning for voice recordings, and the PHI-adjacent audience registry for campaign prechecks.
Checklist signal: mark step 3 covered when the toggle is on and PUT /api/v1/settings/hipaa no longer returns 403. The full control set is on HIPAA controls.

Step 4 — Restrict PHI access to the right roles

  1. Map the people in your workspace to dashboard surfaces: message-content reads and the PHI access log are restricted to owners and admins; developers and viewers do not read the PHI access log; billing roles read neither.
  2. Trim roles in Settings → Members before go-live so the first PHI read lands in an allowed role.
Checklist signal: mark step 4 covered when each PHI-bearing surface (Messages, Contacts, the PHI access log) reads under an owner/admin role only. The roles-versus-surface matrix is on HIPAA controls.

Step 5 — Prove the minimum-necessary audit row

  1. Make one PHI read (open a PHI-bearing message or contact).
  2. Page through GET /api/v1/settings/hipaa/phi-access-log and confirm a row exists with the actor, the resource, and the reason code — that entry is your minimum-necessary evidence.
  3. Queue an export of the audit trail and confirm the export lines up with the live log.
Checklist signal: mark step 5 covered when the PHI access log shows reason-coded reads and the export path works. Export mechanics are on Audit log export.

The go/no-go sequence: self-check → production send

Run this end to end before the first production PHI-bearing send:
  1. Run the free checklist on the tools hub — it scores the five items and links each open one to its deep guide. Close the open items before you proceed.
  2. Walk steps 1–2 above — attest PHI in scope and execute the BAA.
  3. Walk steps 3–4 — enable HIPAA mode and trim roles; the toggle now accepts instead of returning 403.
  4. Read the gate inputs — GET /api/v1/compliance/baa returns baa_status: executed, hipaa_required: true, days_until_expiry counting down from 365.
  5. Send a test PHI-bearing message. A blocked gate returns 422 before wallet hold or provider dispatch, so the test send is free to run: if it passes, the gate verdict is clean and the workspace is live; if it returns 422 HIPAA_BAA_REQUIRED, stop and re-read the failed reason (below).
  6. Mark step 5 — the send itself wrote a PHI access-log row; verify it carries a reason code.
Re-run the checklist after a BAA renewal reminder, a role change, or a new channel launch; a fresh self-check takes under a minute.

The four BAA states and the gate predicate

The checklist mirrors the BAA state machine; the deep vocabulary lives on the BAA flow page. For the go/no-go read, the gate predicate is: Additionally: an executed row with a missing, future-dated, or malformed execution timestamp, and an executed row whose term has lapsed before the daily check flips the status, both fail as not_signed/expired — the term re-derives from the timestamp on every enforced call. See the BAA flow for the verdict table and transitions.

Worked example: the HIPAA_BAA_REQUIRED 422 verdict

A send on a PHI-scope workspace that has not executed the BAA returns:
The reason is one of pending, expired, or not_signed, and the block lands before wallet hold, quota, or dispatch — a blocked send never burns balance. If the status cannot be verified at all (a read failure), the response is 500 HIPAA_BAA_GATE_DB_FAIL and sends stay blocked: the gate fails closed. Treat a verification_unavailable reason as a verification outage — retry shortly — not a missing BAA. Safe-failure sequence before the first PHI send:
  1. Attempt the send deliberately on a draft/staging recipient.
  2. If 422 with reason: pending → execute the BAA (step 2), then re-attempt.
  3. If 422 with reason: expired → re-execute (the window opens 60 days before expires_at), then re-attempt.
  4. If 422 with reason: not_signed → check the executed row’s timestamp; decline (no PHI) or re-run execute to clear it.
  5. If 500 HIPAA_BAA_GATE_DB_FAIL → wait and retry; do not treat it as a posture defect.
  6. Only when the send passes unblocked is the workspace go-live ready.

See also