Skip to main content

Submit Encounter

Submit a clinical letter for evaluation and physician review. Returns an evaluation against 11 criteria, then either a checkout URL or — for authenticated subscribers with a verified patient — an immediate submitted state with no website round-trip.

POST/api/v1/agent/query

Authentication is optional. See Authentication for the three caller modes (anonymous, API key, Clerk JWT) and what each one unlocks.

Request body

ParameterTypeRequiredDescription
querystringRequiredThe clinical letter in Markdown format. 500-10,000 characters.
session_tokenstringOptionalToken from a previous response to continue the same encounter. Omit for a new encounter.
patient_idstringOptionalUUID of the person this encounter is for. Authenticated calls only — must belong to your account. Retrieve via GET /api/v1/patients. Once bound, cannot be re-targeted at a different patient.
imagesarrayOptionalUp to 3 images to attach (e.g., photos of a rash, wound, or test result).

Image object

ParameterTypeRequiredDescription
images[].urlstringOptionalURL pointing to an image. Provide either url or base64.
images[].base64stringOptionalBase64-encoded image data. Provide either url or base64.
images[].namestringOptionalOptional filename for the image.

Request example

Request body
{
  "query": "# Chief Complaint\nCough x 2 weeks\n\n# Age and Sex\n35-year-old male\n\n# History of Present Illness\nProductive cough with yellow-green sputum for 2 weeks. Worse in the morning.\n\n# Review of Systems\nNo fever, no weight loss, no night sweats.\n\n# Past Medical History\nNo chronic conditions.\n\n# Allergies\nNKDA\n\n# Family History\nFather with asthma.\n\n# Social History\nNon-smoker, office worker.\n\n# What I Think It Might Be\nAcute bronchitis.\n\n# What I Am Hoping For\nBenzonatate for cough suppression.",
  "session_token": "abc123-def456"
}

Response (more info needed)

When the letter is missing required information, the API returns final_decision_ready: false with a list of missing items.

{
  "session_token": "abc123-def456",
  "evaluation": {
    "chief_complaint_present": true,
    "age_and_sex_present": false,
    "history_of_present_illness_present": true,
    "review_of_systems_present": false,
    "past_medical_history_present": false,
    "allergies_present": false,
    "family_history_present": false,
    "social_history_present": false,
    "diagnosis_present": false,
    "treatment_plan_present": false,
    "request_within_scope": false
  },
  "final_decision_ready": false,
  "commentary": "Missing age and sex, review of systems, past medical history...",
  "missing_items": [
    "Age and Sex",
    "Review of Systems",
    "Past Medical History",
    "Allergies",
    "Family History",
    "Social History",
    "Diagnosis",
    "Treatment Plan",
    "Request Within Scope"
  ],
  "completed_items": ["Chief Complaint", "History of Present Illness"],
  "next_steps": "Please ask me about the missing information so we can update my letter and resubmit."
}

Response (ready for checkout)

When all 11 criteria are met, the API returns final_decision_ready: true with a checkout URL.

{
  "session_token": "abc123-def456",
  "evaluation": {
    "chief_complaint_present": true,
    "age_and_sex_present": true,
    "history_of_present_illness_present": true,
    "review_of_systems_present": true,
    "past_medical_history_present": true,
    "allergies_present": true,
    "family_history_present": true,
    "social_history_present": true,
    "diagnosis_present": true,
    "treatment_plan_present": true,
    "request_within_scope": true
  },
  "final_decision_ready": true,
  "commentary": "All required information present.",
  "missing_items": [],
  "completed_items": [
    "Chief Complaint",
    "Age and Sex",
    "History of Present Illness",
    "Review of Systems",
    "Past Medical History",
    "Allergies",
    "Family History",
    "Social History",
    "Diagnosis",
    "Treatment Plan",
    "Request Within Scope"
  ],
  "encounter_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "encounter_token": "7f3e...<64-char hex>",
  "checkout_url": "https://appendix.com/checkout/a1b2c3d4-e5f6-7890-abcd-ef1234567890?token=xyz...",
  "encounter_expires_at": "2026-02-29T12:00:00.000Z",
  "pricing": {
    "amount": "$99",
    "base_amount": "$99",
    "seat_amount": "$29",
    "includes": [
      "Our doctors on retainer, accessible through any AI agent",
      "Personal response from our in-house physicians with every submission",
      "Prescriptions included as clinically appropriate",
      "E-prescription sent to any U.S. pharmacy",
      "Add family members for $29/mo each — adults and kids as young as 6 months",
      "Cancel anytime"
    ],
    "refund_policy": "You may cancel your subscription at any time. Upon cancellation, you will receive a prorated refund for the unused portion of the current billing period. If a prescription has been issued during the current billing period, that period is paid in full and non-refundable; cancellation stops all future charges but does not refund the current period. Refunds are processed to the original payment method within 5–10 business days.",
    "fair_use_policy": "Subject to our fair use policy. Appendix reserves the right to limit usage at its discretion."
  },
  "next_steps": "My letter is complete. Please show me the checkout URL so I can verify my identity, pay, and choose my pharmacy."
}

Response (auto-submitted)

Returned to authenticated subscribers when patient_id is bound, the patient has consented and verified ID, and the subscription is active and within the fair-use cap. The encounter advances directly to submitted; the user does not need to visit the checkout URL.

{
  "session_token": "abc123-def456",
  "encounter_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
  "encounter_token": "7f3e...<64-char hex>",
  "encounter_expires_at": "2026-02-29T12:00:00.000Z",
  "evaluation": { /* 11 criteria, all true */ },
  "final_decision_ready": true,
  "commentary": "All required information present.",
  "missing_items": [],
  "completed_items": [ /* 11 labels */ ],
  "checkout_url": "https://appendix.com/checkout/a1b2c3d4-...?token=xyz",
  "pricing": { /* same shape as the ready-for-checkout response */ },
  "auto_submit": {
    "status": "submitted",
    "submission_id": "f0e9d8c7-b6a5-4321-fedc-ba9876543210",
    "new_state": "submitted"
  },
  "submission_id": "f0e9d8c7-b6a5-4321-fedc-ba9876543210",
  "new_state": "submitted",
  "next_steps": "Submission accepted. A physician will review it and reply via the agent chat endpoints. The patient does not need to visit the checkout URL."
}

When at least one precondition is missing, the same call returns auto_submit.status: "blocked" with a pending_reasons array (patient_required, patient_not_owned, telehealth_consent_required, patient_not_id_verified, subscription_required, rate_limit_reached). The checkout_url is still included so the agent can hand it off if the user prefers to finish on the web.

Response fields

ParameterTypeRequiredDescription
session_tokenstringRequiredToken to use when resubmitting to continue the same encounter.
evaluationobjectRequiredObject with 11 boolean fields indicating which criteria are met.
final_decision_readybooleanRequiredTrue when all criteria are met and the encounter is ready for checkout.
commentarystringRequiredHuman-readable summary of the evaluation.
missing_itemsstring[]RequiredLabels of criteria that are not yet met.
completed_itemsstring[]RequiredLabels of criteria that are met.
encounter_idstringRequiredUUID of the encounter. Pair with encounter_token to poll chat or reply via the agent chat endpoints.
encounter_tokenstringRequired64-char hex token scoped to this encounter. Valid for 72h from creation. Rotates on each resubmission — always use the most recent value. Authenticates checkout and agent chat endpoints.
encounter_expires_atstringRequiredISO 8601 timestamp when the encounter expires (72h after creation).
checkout_urlstringOptionalURL for the patient to verify identity and pay. Only present when final_decision_ready is true.
pricingobjectOptionalPricing details. Only present when final_decision_ready is true.
already_claimedbooleanOptionalTrue if the encounter is owned by an account (either authenticated caller or prior claim). The checkout URL remains valid.
auto_submitobjectOptionalAuthenticated calls only. status is "submitted" (encounter advanced past readyForCheckout) or "blocked" (with pending_reasons[] explaining what to fix).
submission_idstringOptionalUUID of the created submission. Present only when auto_submit.status is "submitted".
new_statestringOptionalEncounter state after auto-submit, typically "submitted". Present only when auto_submit.status is "submitted".

Errors

CodeMeaning
400Missing query, too short (<500 chars), too long (>10,000 chars), not medical content, patient_id does not belong to the caller, or the encounter is already bound to a different patient
401Authorization header was provided but the token is invalid, or patient_id was provided without authentication
404session_token resolves to an encounter owned by another account
410Encounter expired (older than 72 hours). Start a new encounter.
429Rate limit exceeded. Wait and try again.
500Internal server error. Retry or contact support.