Skip to main content

Glossary & Reference

This page is the canonical reference for terms, identifiers, statuses, and webhook events used across every Stealth Health partner integration. Each tier guide links here rather than duplicating these tables.

ID Prefixes

All partner-facing identifiers carry a stable prefix so you can route them in your own systems without parsing.

PrefixObjectIssued by
ptr_PartnerStealth Health (at onboarding)
sk_live_ / sk_test_API key (production / sandbox)Stealth Health
whsec_Webhook signing secretStealth Health
ref_ReferralStealth Health (POST /partner/referrals)
partner_intake_Patient profile (created via POST /partner/appointments)Stealth Health — deterministic: partner_intake_{partner_id}_{sanitized_email}
partner_inline_Patient profile (created via POST /partner/prescriptions with inline_patient)Stealth Health — deterministic: partner_inline_{partner_id}_{sanitized_email}
pres_Prescriber (clinical-tier registry)Stealth Health (POST /partner/prescribers)
appt_AppointmentStealth Health
appt_partner_Partner-submitted appointmentStealth Health (POST /partner/prescriptions)
PRX-Partner-submitted prescription (rx_id)Stealth Health
lab_Lab orderStealth Health (clinician-placed)
psc_apt_Patient Service Center appointmentStealth Health (booked via our lab partner's PSC network)
evt_Webhook eventStealth Health

Partners are encouraged to set their own partner_reference on every create call. We treat it as the idempotency key and echo it back on every webhook so your downstream joins are stable.

:::note Patient ID stability The patient_id returned from POST /partner/appointments (and POST /partner/prescriptions) is deterministic and canonical: it is derived from (partner_id, lowercased patient email), so the same patient always resolves to the same patient_id. It is safe to persist and anchor refills on. For follow-up/refill cases, pass it back as patient_id rather than re-sending inline_patient — re-sending inline_patient reuses the same patient profile but opens a new referral and appointment. Some older examples in the tier guides show a pat_… placeholder; the real format is partner_intake_… / partner_inline_… as shown above. :::

Authentication headers

HeaderPurposeRequired on
X-Partner-IDIdentifies the partner (public, safe to log).All /partner/* calls.
X-Api-KeyAuthenticates the request (secret). Compared in constant time against a stored SHA-256 hash of the key.All /partner/* calls.
X-Access-TierMust be clinical for clinical-tier endpoints. Referral-tier keys hitting clinical endpoints are rejected with 403 CLINICAL_ACCESS_REQUIRED.Clinical-tier endpoints.

Key rotation supports a dual-hash window: the old key remains valid until previous_key_expires_at (default 7 days) so partners can deploy the new key with zero downtime.

Webhook signature header

Every outbound webhook delivery includes:

X-Stealth-Signature: sha256=<hex-digest>

The digest is HMAC-SHA256(webhook_secret, raw_request_body). Verify on every request, against the raw body bytes, using a constant-time comparison. A reference implementation lives in Clinical Tier § 17.2.

Delivery contract:

  • Stealth Health expects a 2xx response within 10 seconds.
  • Failed deliveries are retried with backoff [30s, 5m, 30m, 2h, 12h] (max 6 attempts) and persisted in our internal event store for replay.
  • Each event has a unique event_id; treat it as the idempotency key.

Webhook event catalog

Referral-tier events

Available on all tiers. Delivered to the webhook URL configured on your partner account.

EventTriggerPayload extension
referral.enrolledPatient completes intake formproduct_category
referral.pending_reviewIntake submitted for doctor review
referral.approvedDoctor approves prescription
referral.deniedDoctor denies prescriptiondenial_category (medical_contraindication, incomplete_information, not_a_candidate, ...)
referral.payment_duePayment required from patientamount_cents, currency
referral.payment_completePatient payment receivedamount_cents, currency
referral.awaiting_shipmentPrescription sent to pharmacy
referral.shippedOrder shipped by pharmacycarrier, estimated_delivery
referral.in_transitCarrier scancarrier
referral.out_for_deliveryShipment out for deliverycarrier
referral.deliveredShipment deliveredcarrier, delivered_at
referral.delivery_exceptionDelivery issue (failed attempt etc.)carrier, exception_type
referral.cancelledReferral cancelledcancelled_by (partner or patient)
referral.expiredEnrollment URL expired without completion

Clinical-tier events

Sent only to clinical-tier partners. PHI-bearing payloads.

EventTriggerPayload extension
patient.createdPatient profile created after enrollmentpatient (full profile)
patient.updatedPatient updates their profilepatient (changed fields)
appointment.intake_completedIntake questionnaire submittedappointment_id, intake_summary
appointment.prescription_signedA Stealth or partner physician signed an Rx for a partner-owned appointment. Emitted from all sign paths (doctor portal, standalone, JotForm, POST /partner/prescriptions)appointment_id, prescription: { rx_id, medications[] } (slim shape — see Clinical Tier § 13.2.1)
transaction.succeededPayment successfully processedtransaction (full detail)
transaction.refundedPayment refundedtransaction, refund_amount_cents, reason
prescription.receivedPartner-submitted Rx accepted by POST /partner/prescriptionsappointment_id, prescription_id, rx_id, prescriber_id, medications[]
prescription.rejectedEither (a) partner-submitted Rx rejected after async re-validation, or (b) Stealth physician declined to sign for a partner-owned appointment. Paired with referral.denied in case (b).appointment_id?, prescription_id?, error_code, error_message (see Clinical Tier § 13.2.2 for the enum)
messageThread.updatedNew message landed in a partner-visible thread; body is not included — re-fetch via GET /partner/patients/:id/messagesthread_id, appointment_id, patient_id, last_message_at, sender_type, sender_role
lab_order.createdClinician placed a lab order on a partner-owned appointmentlab_order_id, appointment_id, patient_id, collection_method, provider, tests[] (summary)
lab_order.requisition_readyLab published the requisition PDFlab_order_id, requisition_pdf_url_expires_at
lab_order.sample_collectedSample collected (walk-in, at-home phleb, or testkit registration)lab_order_id, collected_at, collection_method
lab_order.results_updatedLab released results (partial or final); biomarker values NOT included — re-fetch via GET /partner/lab-orders/:id/resultslab_order_id, result_status, resulted_at
lab_order.completedAll ordered markers finallab_order_id, resulted_at
lab_order.cancelledOrder cancelled before sample collectionlab_order_id, cancellation_reason
lab_order.exceptionLab rejected the sample or order entered unrecoverable error statelab_order_id, detailed_status, exception_note

Prescriber-Partner events

EventTriggerPayload extension
appointment.submittedAppointment created and queued for reviewappointment_id, patient_id, status, estimated_review_hours
appointment.in_reviewPhysician has opened the caseappointment_id
appointment.prescription_signedPhysician approved and signed a prescriptionappointment_id, prescription, prescriber
appointment.deniedPhysician denied the caseappointment_id, denial_category, denial_reason
prescription.routedPrescription sent to pharmacy (when we route)appointment_id, pharmacy_name, pharmacy_npi
prescription.filledPharmacy confirmed fill and shippedappointment_id, tracking

Status lifecycles

Referral status

Appointment status (clinical / prescriber-partner)

doctor_reviewed is also the entry state for partner-submitted prescriptions (the appointment is created already in this state by POST /partner/prescriptions).

Common error codes

The complete per-endpoint error catalog lives in each tier guide. The codes below appear across multiple endpoints.

CodeHTTPMeaning
MISSING_CREDENTIALS401X-Partner-ID or X-Api-Key header missing.
INVALID_CREDENTIALS401Partner not found, inactive, or key hash mismatch.
CLINICAL_ACCESS_REQUIRED403Endpoint requires clinical-tier access but a referral-tier key was used.
RATE_LIMIT_EXCEEDED429Per-minute rate limit hit. Honor Retry-After.
INVALID_BODY400Request body failed schema validation. details contains specifics.
INTERNAL_ERROR500Unexpected server error. Safe to retry with exponential backoff.

Rate limits

EnvironmentLimit (per partner, per minute)
Production (api.stealth.health)300
Sandbox (sandbox.stealth.health)60

429 responses include standard Retry-After, X-RateLimit-Remaining, and X-RateLimit-Reset headers.

Environments

EnvironmentBase URLNotes
Productionhttps://api.stealth.healthReal PHI. Requires production API key (sk_live_*).
Sandboxhttps://sandbox.stealth.healthSynthetic data only. Requires sandbox key (sk_test_*). Functionally identical surface.