Skip to main content

Cases API

Retrieve case information by external identifier. This endpoint allows you to fetch case details including patient information, scheduling status, and retry attempt tracking.

Get Cases​

Retrieve a paginated list of cases for your organization.

GET /api/v1/cases

Purpose​

Lists all cases for your organization with pagination support and optional filtering by status and update date.

Query Parameters​

ParameterTypeRequiredDescriptionDefaultRange
case_idUUID stringNoFilter by a specific case IDAll casesValid UUID
sizeintegerNoNumber of results per page1001-500
startintegerNoStarting index (1-based)1>= 1
updated_afterISO 8601 stringNoFilter cases updated after this dateAll cases-
statusstringNoFilter by case statusAll statusesawaiting_sms, awaiting_call, cancelled, pending, success, escalation

Response​

{
"data": [
{
"id": "11111111-1111-1111-1111-111111111111",
"name": "Case 2025-10-15",
"created_at": "2025-10-15T10:00:00.000Z",
"external_id_field_name": "sample_field_name",
"external_id": "1234567",
"patient_id": "11111111-1111-1111-1111-111111111111",
"attempt_count": 0,
"max_attempts": 3,
"updated_at": "2025-10-15T10:30:00.000Z",
"success_at": "2025-10-15T10:30:00.000Z",
"intake_version": 1,
"status": "success",
"case_report": {
// **NOTE** Content varies by agent configuration
"tickets": [],
"extracted_data": {
"end_case": "case_1",
"allergies": [
{
"name": "grass",
"reaction": "rash",
"severity": "mild"
}
],
"medications": [
{
"name": "Methylphenidate",
"dosage": "20mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "verified"
}
},
{
"name": "Acetaminophen/Guaifenesin",
"dosage": "20mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "verified"
}
}
],
"pharmacy_fax": "+19053173538",
"consent_given": "yes",
"pharmacy_name": "SHOPPERS DRUG MART",
"preferred_email": "john.doe@example.com",
"identity_verified": "yes",
"ohip_version_code": "AB",
"faq_answered_from_kb": [
{
"question": "pet_policy",
"answer": "Pets are not allowed during the appointment."
},
{
"question": "service_dog_policy",
"answer": "Service dogs are welcome to accompany you during your appointment."
},
{
"question": "bring_medications_list",
"answer": "Yes, please bring a complete list of your current medications and supplements."
}
],
"appointment_confirmed": "yes",
"preferred_phone_number": "+14165551234"
},
"short_description": "Cardiology intake completed successfully; all information collected.",
"bullet_point_summary": [
"Patient identity verified and consent obtained.",
"All intake questions completed; appointment confirmed."
],
"conversation_summary": "The agent successfully contacted the patient to conduct a cardiology intake. Identity verification and consent were obtained. All required intake information was collected including medications, allergies, and pharmacy details. The appointment was confirmed and all patient questions were answered. The intake process was completed successfully."
}
},
{
"id": "22222222-2222-2222-2222-222222222222",
"name": "Case 2025-10-15",
"created_at": "2025-10-15T10:00:00.000Z",
"external_id_field_name": "sample_field_name",
"external_id": "1234567",
"patient_id": "22222222-2222-2222-2222-222222222222",
"attempt_count": 0,
"max_attempts": 3,
"updated_at": "2025-10-15T10:30:00.000Z",
"success_at": "2025-10-15T10:30:00.000Z",
"intake_version": 1,
"status": "success",
"case_report": {
// **NOTE** Content varies by agent configuration
"tickets": [],
"extracted_data": {
"end_case": "case_1",
"allergies": [],
"medications": [],
"pharmacy_fax": "",
"consent_given": "yes",
"pharmacy_name": "SHOPPERS DRUG MART",
"preferred_email": "jane.smith@email.com",
"identity_verified": "yes",
"ohip_version_code": "N/A",
"faq_answered_from_kb": [],
"appointment_confirmed": "yes",
"preferred_phone_number": "+16475559876"
},
"short_description": "Cardiology intake completed successfully; patient reported no medications or allergies.",
"bullet_point_summary": [
"Patient identity verified and consent obtained.",
"Intake questions completed; patient has no current medications or allergies.",
"Appointment confirmed; no pharmacy information needed."
],
"conversation_summary": "The agent successfully contacted the patient to conduct a cardiology intake. Identity verification and consent were obtained. During the intake process, the patient confirmed they are not currently taking any medications and have no known allergies. No pharmacy information was needed. The appointment was confirmed and all patient questions were answered. The intake process was completed successfully with no medical information to record."
}
},
{
"id": "33333333-3333-3333-3333-333333333333",
"name": "Case 2025-10-15",
"created_at": "2025-10-15T10:00:00.000Z",
"external_id_field_name": "sample_field_name",
"external_id": "1234567",
"patient_id": "33333333-3333-3333-3333-333333333333",
"attempt_count": 0,
"max_attempts": 3,
"updated_at": "2025-10-15T10:30:00.000Z",
"success_at": null,
"intake_version": 1,
"status": "pending",
"case_report": {
// **NOTE** Content varies by agent configuration
"tickets": [
{
"notes": "Patient asked a question that the agent could not answer",
"title": "FAQ Issue"
}
],
"extracted_data": {
"end_case": "case_6",
"allergies": [
{
"name": "grass",
"reaction": "rash",
"severity": "mild"
}
],
"medications": [
{
"name": "Methylphenidate",
"dosage": "40mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "changed",
"previous_fields": {
"dosage": "20mg"
},
"reason": "dose increased by cardiologist",
"change_date": "2025-09-15",
"is_approved": "yes",
"approved_doctor": "Dr. Patel"
}
},
{
"name": "Acetaminophen/Guaifenesin",
"dosage": "20mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "verified"
}
},
{
"name": "Metformin",
"dosage": "500mg",
"duration": "2 years",
"frequency": "twice daily",
"review_details": {
"state": "stopped",
"reason": "adverse reaction",
"change_date": "2025-10-01",
"is_approved": "yes",
"approved_doctor": "Dr. Patel"
}
},
{
"name": "Amlodipine",
"dosage": "5mg",
"duration": "unknown",
"frequency": "once daily",
"review_details": {
"state": "unverified"
}
},
{
"name": "Sandoz",
"dosage": "unknown",
"duration": "unknown",
"frequency": "2 times a day",
"review_details": {
"state": "flagged",
"reason": "patient mentioned a new medication but only gave the manufacturer name; exact drug and dosage unclear"
}
}
],
"pharmacy_fax": "+19053173538",
"consent_given": "yes",
"pharmacy_name": "SHOPPERS DRUG MART",
"preferred_email": "bob.jones@example.com",
"identity_verified": "yes",
"ohip_version_code": "AB",
"faq_answered_from_kb": [
{
"question": "pet_policy",
"answer": "Pets are not allowed during the appointment."
},
{
"question": "service_dog_policy",
"answer": "Service dogs are welcome to accompany you during your appointment."
},
{
"question": "bring_medications_list",
"answer": "Yes, please bring a complete list of your current medications and supplements."
}
],
"appointment_confirmed": "yes",
"preferred_phone_number": "+14165554321"
},
"short_description": "Cardiology intake partially completed; dose change, stopped med, and one med not reviewed.",
"bullet_point_summary": [
"Patient identity verified and consent obtained.",
"Methylphenidate dose increased from 20mg to 40mg (Dr. Patel approved).",
"Metformin stopped October 1 due to adverse reaction (Dr. Patel approved).",
"Amlodipine (on file) not confirmed — call ended before reaching it.",
"New medication mentioned by patient flagged for human review (Sandoz — partial info)."
],
"conversation_summary": "The agent successfully contacted the patient to conduct a cardiology intake. Identity verification and consent were obtained. The patient confirmed an updated Methylphenidate dose (20mg → 40mg) approved by Dr. Patel, and confirmed stopping Metformin October 1 due to an adverse reaction, approved by the same doctor. Acetaminophen/Guaifenesin was confirmed unchanged. Amlodipine, on file from the clinic's records, was not reached before the call ended. The patient also mentioned a new medication but only gave the manufacturer name (Sandoz) with unclear dosage, so it was flagged for human review."
}
}
],
"pagination": {
"start": 1,
"requested_size": 100,
"returned_count": 3,
"total": 150,
"hasMore": false,
"updated_after": "2025-10-01T00:00:00.000Z"
}
}

Response Fields​

  • id: Unique identifier for the case
  • name: Name or description of the case
  • created_at: ISO 8601 timestamp when the case was created
  • external_id_field_name: Name of the external ID field used to identify this case
  • external_id: External identifier from your system
  • patient_id: UUID of the associated patient (nullable)
  • attempt_count: Number of call attempts made for this case
  • max_attempts: Maximum number of call attempts allowed
  • updated_at: ISO 8601 timestamp when the case was last updated
  • success_at: ISO 8601 timestamp of when the case was closed as successful, for the intake it currently holds. A case is closed on a fixed 12-hour timer after the intake completes, so this timestamp is approximately 12 hours after the call or form submission rather than the moment of the intake itself. Where an intake is collected again on the same case (see intake_version), success_at moves to the later completion, so it always describes the case_report returned alongside it. It does not move for any other reason: unlike updated_at, which is bumped by every subsequent write to the case, success_at changes only when a case crosses into success. It is null for any case that has not reached success, and null for every case closed before 2026-08-05 UTC, when the field was introduced. Cases that succeeded before repeat intakes were introduced retain their first completion. Use intake_version, not success_at, to decide whether a newer intake exists: it is an integer with no clock skew or 12-hour offset.
  • intake_version: Integer, starts at 1. It is the generation of the intake the case is currently on or last completed, not a count of completed intakes. Blair increments it each time it schedules a repeat intake on the same case and the same external_id — today only for KMH, when a completed intake's appointment is pushed out far enough that the collected data would be stale. Because the increment happens when the repeat is scheduled rather than when it completes, a case can carry intake_version: 2 while its status is awaiting_sms, awaiting_call, or pending; during that window case_report still holds the previous intake. The case reappears in an updated_after poll at that point, and again when the repeat intake completes. Regenerate your downstream artifact (e.g. the chart PDF) only when status is success and intake_version is higher than the version you last regenerated for. Both conditions are required: acting on the version alone would regenerate from the stale report and then skip the new one. Record the version you last processed at the moment you regenerate, not when you first see it. When the repeat completes, success_at moves to the newer completion alongside it, so the timestamp always matches the case_report returned.
  • status: Current status of the case (awaiting_sms, awaiting_call, cancelled, pending, success, escalation)
  • case_report: JSONB field with case-specific data (nullable).
  • short_description: Brief one-line summary of the call outcome
  • bullet_point_summary: Array of key points summarizing the call interaction
  • conversation_summary: Detailed narrative summary of the entire call and its outcome
  • pagination.start: The 1-based index you requested
  • pagination.requested_size: The size you requested
  • pagination.returned_count: Actual number of records returned
  • pagination.total: Total records matching the filter
  • pagination.hasMore: Whether more pages are available

Medication review_details​

Each entry in case_report.extracted_data.medications[] includes a review_details object describing what the agent learned about that medication during the call. The top-level fields on the medication (name, dosage, duration, frequency) always reflect the current values after any changes.

The state field determines which additional fields are present:

stateWhen it's usedAdditional fields
verifiedPatient confirmed they are currently taking this medication as listed — covers both previously known medications with no changes and newly reported medications captured during the callNone
changedOne or more fields were modified (e.g. dose or frequency)previous_fields, reason, change_date, is_approved, approved_doctor
stoppedMedication has been discontinuedreason, change_date, is_approved, approved_doctor
unverifiedA medication from the healthcare organization's existing records that the patient did not confirm during the call (e.g. the call ended before reviewing it)None
flaggedA new medication the patient mentioned during the call that the agent could not fully capture (partial name, unclear dosage, ambiguous frequency) and needs human reviewreason

Field reference:

  • previous_fields: Sparse object containing only the fields whose values changed, with their prior values (current values remain on the top-level medication object).
  • reason: Free-text explanation. For changed / stopped, this is the patient's reason for the change or discontinuation. For flagged, this is why the agent could not confidently record the medication.
  • change_date: ISO 8601 date (YYYY-MM-DD) when the change took effect.
  • is_approved: "yes" or "no" — whether a prescribing doctor approved the change.
  • approved_doctor: Name of the doctor who approved the change (present when is_approved is "yes").

Examples for each state:

verified — patient confirmed they are currently taking the medication as listed. This applies both to previously known medications that remain unchanged and to newly reported medications captured during the call.

Previously known medication, unchanged:

{
"name": "Acetaminophen/Guaifenesin",
"dosage": "20mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "verified"
}
}

New medication reported during the call:

{
"name": "Atorvastatin",
"dosage": "10mg",
"duration": "3 months",
"frequency": "once daily",
"review_details": {
"state": "verified"
}
}

changed — a dose increase from 20mg to 40mg:

{
"name": "Methylphenidate",
"dosage": "40mg",
"duration": "1 year",
"frequency": "1 time a day",
"review_details": {
"state": "changed",
"previous_fields": { "dosage": "20mg" },
"reason": "dose increased by cardiologist",
"change_date": "2025-09-15",
"is_approved": "yes",
"approved_doctor": "Dr. Patel"
}
}

stopped — medication discontinued due to an adverse reaction:

{
"name": "Metformin",
"dosage": "500mg",
"duration": "2 years",
"frequency": "twice daily",
"review_details": {
"state": "stopped",
"reason": "adverse reaction",
"change_date": "2025-10-01",
"is_approved": "yes",
"approved_doctor": "Dr. Patel"
}
}

unverified — existing medication on the healthcare organization's records; the patient did not confirm it on this call (e.g. the call ended before reviewing it):

{
"name": "Amlodipine",
"dosage": "5mg",
"duration": "unknown",
"frequency": "once daily",
"review_details": {
"state": "unverified"
}
}

flagged — a new medication the patient mentioned on the call, but the agent could not capture it confidently (partial name, unclear dosage, etc.) — needs human review:

{
"name": "Sandoz",
"dosage": "unknown",
"duration": "unknown",
"frequency": "2 times a day",
"review_details": {
"state": "flagged",
"reason": "patient mentioned a new medication but only gave the manufacturer name; exact drug and dosage unclear"
}
}

Example​

# Get first page with default size
curl -X GET "https://orchestrator.helloblair.com/api/v1/cases" \
-H "X-API-Key: YOUR_API_KEY"

# Get second page with custom size
curl -X GET "https://orchestrator.helloblair.com/api/v1/cases?size=50&start=51" \
-H "X-API-Key: YOUR_API_KEY"

# Filter by status
curl -X GET "https://orchestrator.helloblair.com/api/v1/cases?status=pending" \
-H "X-API-Key: YOUR_API_KEY"

# Filter by update date and status
curl -X GET "https://orchestrator.helloblair.com/api/v1/cases?updated_after=2025-10-01T00:00:00.000Z&status=success" \
-H "X-API-Key: YOUR_API_KEY"

# Get a specific case by ID
curl -X GET "https://orchestrator.helloblair.com/api/v1/cases?case_id=11111111-1111-1111-1111-111111111111" \
-H "X-API-Key: YOUR_API_KEY"

Case Lifecycle​

After a case is created in the system and calls are scheduled, the status will progress through the following statuses:

  • awaiting_sms: We have not had an interaction with the patient yet
  • awaiting_call: We have sent an SMS to the patient informing that they will be called
  • cancelled: Case was cancelled before making any contact with the patient
  • pending: Contact has been made with the patient. We are waiting to make sure there are no missing information
  • success: Intake is fully complete, no more actions remaining for this case
  • escalation: Case is in a state where we can no longer handle. Requires clinic admin intervention

Best Practices​

  1. Use pagination when retrieving large lists of cases
  2. Filter by status to focus on cases requiring attention (e.g., escalation, success)
  3. Use updated_after to sync only recently changed cases
  4. Monitor case_report for agent-specific data and insights
  5. Use 1-based pagination - start index begins at 1, not 0

Use Cases​

Monitoring Case Progress​

Use the cases endpoint to:

  • Track cases by status (awaiting_sms, awaiting_call, pending, success, etc.)
  • Retrieve cases updated after a specific date for syncing
  • Monitor case reports for completed intakes
  • Identify cases requiring escalation or admin intervention