{"openapi":"3.1.0","info":{"title":"Health Patient Portal: Delegated Agent API","version":"1.0.0","description":"API for software agents (for example a voice assistant) acting on behalf of one patient of the Health patient portal. Mirrors what the patient can do in the portal. Authentication: Bearer grant token minted by the patient under Account settings > Linked apps & agents; each grant carries scopes and a confirmation policy.\n\nConfirmation protocol for irreversible actions (booking, cancelling or rescheduling an appointment, accepting a wait-list offer, sending or replying to a message, requesting refills, paying, signing a document, submitting a questionnaire): when the grant's confirm_policy is \"confirm-irreversible\" (the default), the first call returns HTTP 202 {status:\"confirmation_required\", confirmation_token, expires_in:300, summary, action, payload_hash}. Read the summary to the patient, get their yes, then repeat the identical request with the header X-Confirmation-Token: <confirmation_token>. Tokens are single-use, expire in 5 minutes, and are bound to the exact action + payload (409 on mismatch, reuse or expiry). Grants with confirm_policy \"pre-authorized\" skip the challenge. Every call is written to the patient's access log with actor=agent, on_behalf_of=patient and the grant id, and appears under \"Who's accessed my record\".\n\nScopes: record:read appointments:read appointments:book appointments:cancel checkin:complete messages:read messages:send refills:request results:read medications:read billing:read billing:pay questionnaires:submit vitals:write profile:read.\n\nA read-only FHIR R4 (US Core 6.1-shaped) view of the same record is at https://portal.mohithgajjela.com/fhir/r4 (CapabilityStatement at /fhir/r4/metadata) using the same Bearer token with record:read."},"servers":[{"url":"https://portal.mohithgajjela.com/agent/v1"}],"components":{"securitySchemes":{"grantToken":{"type":"http","scheme":"bearer","description":"Grant token from the portal (Account settings > Linked apps & agents)."}}},"paths":{"/context":{"get":{"summary":"Compact briefing to open a conversation: patient, next appointments, eCheck-In availability, unread messages, new results, open refills, questionnaires due, preventive care due, balance due, wait-list offers, scheduling tickets, org info, server time.","description":"Required scope: profile:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/profile":{"get":{"summary":"Demographics, contact info, emergency contact, pharmacies on file, coverage.","description":"Required scope: profile:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/record/summary":{"get":{"summary":"Problems, allergies, active medications, immunizations, last 10 results with flags, latest vitals, care team.","description":"Required scope: record:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/appointments":{"get":{"summary":"List appointments.","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[{"name":"status","in":"query","required":false,"description":"upcoming (default) | past","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}},"post":{"summary":"Book a free slot.","description":"Required scope: appointments:book. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"visit_type_id":{"description":"string"},"slot_id":{"description":"string"},"reason_text":{"description":"string?"},"comments":{"description":"string?"},"scheduling_ticket_id":{"description":"string? (links a provider order)"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}":{"get":{"summary":"Appointment details.","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/appointments/{id}/instructions":{"get":{"summary":"Instructions, address, arrival guidance, cancel policy.","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/visit-types":{"get":{"summary":"Bookable visit types (duration, modality, direct vs request).","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/providers":{"get":{"summary":"Schedulable providers, care-team members first.","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[{"name":"visit_type","in":"query","required":false,"description":"filter by visit type id","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/slots":{"get":{"summary":"Free slots grouped by day with friendly labels.","description":"Required scope: appointments:read.","security":[{"grantToken":[]}],"parameters":[{"name":"visit_type","in":"query","required":true,"description":"required","schema":{"type":"string"}},{"name":"provider_id","in":"query","required":false,"description":"optional","schema":{"type":"string"}},{"name":"from","in":"query","required":false,"description":"ISO datetime","schema":{"type":"string"}},{"name":"to","in":"query","required":false,"description":"ISO datetime (default from + 14 days)","schema":{"type":"string"}},{"name":"modality","in":"query","required":false,"description":"in-person | video","schema":{"type":"string"}},{"name":"part_of_day","in":"query","required":false,"description":"morning | afternoon","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/appointments/request":{"post":{"summary":"Request an appointment for request-only visit types.","description":"Required scope: appointments:book.","security":[{"grantToken":[]}],"parameters":[],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"visit_type_id":{"description":"string"},"provider_id":{"description":"string?"},"preferred_days":{"description":"string?"},"preferred_times":{"description":"string?"},"comments":{"description":"string?"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}/cancel":{"post":{"summary":"Cancel an appointment (late cancellations are flagged).","description":"Required scope: appointments:cancel. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"reason":{"description":"string"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}/reschedule":{"post":{"summary":"Move an appointment to another free slot.","description":"Required scope: appointments:book + appointments:cancel. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"slot_id":{"description":"string"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}/waitlist":{"post":{"summary":"Join the wait list for an earlier time.","description":"Required scope: appointments:book.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/waitlist/{id}/accept":{"post":{"summary":"Accept an earlier-time offer.","description":"Required scope: appointments:book. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}/checkin":{"get":{"summary":"eCheck-In steps with the data to verify (personal, insurance, copay, documents, medications, allergies, health issues, questionnaires).","description":"Required scope: checkin:complete.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/appointments/{id}/checkin/step/{key}":{"post":{"summary":"Complete one step. Review steps: {confirmed:true, changes:[{op:add|remove|update, target_id?, payload}]} (changes become pending change requests for staff review). payment: {pay_later:true} or {method_id} (saved method; confirmation required). documents: {consent_id, signature_name} (confirmation required). questionnaires: {assignment_id, answers}.","description":"Required scope: checkin:complete. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"key","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/appointments/{id}/checkin/complete":{"post":{"summary":"Finish eCheck-In once no step is pending.","description":"Required scope: checkin:complete.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/messages":{"get":{"summary":"Conversation list.","description":"Required scope: messages:read.","security":[{"grantToken":[]}],"parameters":[{"name":"folder","in":"query","required":false,"description":"conversations (default) | appointment | automated | archived","schema":{"type":"string"}},{"name":"unread","in":"query","required":false,"description":"true","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}},"post":{"summary":"Send a new message on the patient's behalf (sender is labelled \"<patient> (via <grant>)\").","description":"Required scope: messages:send. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"kind":{"description":"medical-advice | refill | billing | customer-service | scheduling"},"recipient_practitioner_id":{"description":"string? (care team member)"},"recipient_pool":{"description":"nurse-line | billing | customer-service | scheduling (default by kind)"},"subject":{"description":"string"},"body":{"description":"string"},"about_type":{"description":"string?"},"about_id":{"description":"string?"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/messages/{thread_id}":{"get":{"summary":"Thread with all messages.","description":"Required scope: messages:read.","security":[{"grantToken":[]}],"parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/messages/{thread_id}/read":{"post":{"summary":"Mark a thread read.","description":"Required scope: messages:read.","security":[{"grantToken":[]}],"parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/messages/{thread_id}/reply":{"post":{"summary":"Reply in a conversation.","description":"Required scope: messages:send. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"thread_id","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"body":{"description":"string"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/results":{"get":{"summary":"Released test results.","description":"Required scope: results:read.","security":[{"grantToken":[]}],"parameters":[{"name":"new","in":"query","required":false,"description":"true (unviewed only)","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/results/{id}":{"get":{"summary":"Result detail with components, flags, provider comment. Does not mark the result viewed unless mark_viewed=true.","description":"Required scope: results:read.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"mark_viewed","in":"query","required":false,"description":"true","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/results/{id}/trend/{loinc}":{"get":{"summary":"All released values of one component over time.","description":"Required scope: results:read.","security":[{"grantToken":[]}],"parameters":[{"name":"id","in":"path","required":true,"schema":{"type":"string"}},{"name":"loinc","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/medications":{"get":{"summary":"Medication list with refill eligibility and renewal flags.","description":"Required scope: medications:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/pharmacies":{"get":{"summary":"Pharmacies (patient's on file first).","description":"Required scope: medications:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/refills":{"get":{"summary":"Refill requests with status history.","description":"Required scope: medications:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}},"post":{"summary":"Request refills/renewals. Controlled substances and patient-reported meds are rejected.","description":"Required scope: refills:request. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"items":{"description":"[{medication_request_id, comments?}]"},"delivery_method":{"description":"pickup | mail"},"pharmacy_id":{"description":"string"},"pickup_at":{"description":"ISO datetime?"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/billing/summary":{"get":{"summary":"Balances per account, payment plans, saved payment methods, recent payments.","description":"Required scope: billing:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/billing/statements":{"get":{"summary":"Statements.","description":"Required scope: billing:read.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/billing/pay":{"post":{"summary":"Pay toward an account using a saved payment method.","description":"Required scope: billing:pay. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"account_id":{"description":"string"},"amount":{"description":"number"},"method_id":{"description":"string (saved method)"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/questionnaires":{"get":{"summary":"Assigned questionnaires.","description":"Required scope: questionnaires:submit.","security":[{"grantToken":[]}],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/questionnaires/{assignment_id}":{"get":{"summary":"Questionnaire items and any saved answers.","description":"Required scope: questionnaires:submit.","security":[{"grantToken":[]}],"parameters":[{"name":"assignment_id","in":"path","required":true,"schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}},"post":{"summary":"Save (submit:false) or submit answers keyed by linkId.","description":"Required scope: questionnaires:submit. Irreversible: subject to the confirmation protocol.","security":[{"grantToken":[]}],"parameters":[{"name":"assignment_id","in":"path","required":true,"schema":{"type":"string"}},{"name":"X-Confirmation-Token","in":"header","required":false,"description":"Single-use token from a prior 202 response (see confirmation protocol).","schema":{"type":"string"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"answers":{"description":"{ [linkId]: value }"},"submit":{"description":"boolean (default true)"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/vitals":{"get":{"summary":"Vitals and patient-entered readings.","description":"Required scope: record:read.","security":[{"grantToken":[]}],"parameters":[{"name":"flowsheet","in":"query","required":false,"description":"blood_pressure | weight | blood_glucose | steps | heart_rate | temperature | spo2","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}},"post":{"summary":"Record a patient-entered reading (flagged pending clinician review).","description":"Required scope: vitals:write.","security":[{"grantToken":[]}],"parameters":[],"requestBody":{"required":true,"content":{"application/json":{"schema":{"type":"object","properties":{"flowsheet":{"description":"blood_pressure | weight | blood_glucose | steps | heart_rate | temperature | spo2"},"value":{"description":"number (non-BP)"},"systolic":{"description":"number (BP)"},"diastolic":{"description":"number (BP)"},"effective_at":{"description":"ISO datetime?"},"note":{"description":"string?"}}}}}},"responses":{"200":{"description":"OK"},"201":{"description":"Created"},"202":{"description":"confirmation_required (see protocol)"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"},"409":{"description":"Conflict (confirmation mismatch, slot taken, already done)"}}}},"/audit":{"get":{"summary":"This grant's own access-log entries.","description":"Required scope: profile:read.","security":[{"grantToken":[]}],"parameters":[{"name":"limit","in":"query","required":false,"description":"number (default 50)","schema":{"type":"string"}}],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/openapi.json":{"get":{"summary":"This document.","description":"Public.","security":[],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}},"/docs":{"get":{"summary":"Human-readable docs.","description":"Public.","security":[],"parameters":[],"responses":{"200":{"description":"OK"},"400":{"description":"Validation error {error, message}"},"401":{"description":"Missing/invalid grant token"},"403":{"description":"insufficient_scope {required:[...]}"},"404":{"description":"Not found"}}}}}}