OnePath Connect
OnePath Connect
OnePath Connect Documentation
WebhooksError HandlingRate LimitsHIPAA for IntegratorsMedication Refill Lifecycle
Guides

Medication Refill Lifecycle

End-to-end guide to medication orders, refill-due polling, progress check-ins, and discontinue.

The medication resource models a full order → refill lifecycle: you create an order after a patient pays and their script goes to the pharmacy, OnePath tells you when a refill is coming up, your patient fills out a progress check-in, and you tell OnePath how it resolved — refilled or discontinued. Requires the medications.read/medications.write scopes.

The flow

create order  →  Tebra sync  →  refill-due poll  →  progress check-in  →  refill or discontinue
  1. Your backend calls medications.createOrder() after payment succeeds and the script ships to the pharmacy.
  2. OnePath stores the order as a FHIR MedicationRequest and asynchronously syncs a note into the prescribing practice's Tebra chart.
  3. Some days before the medication is expected to run out, your own scheduler polls medications.getRefillsDue() — OnePath does not push refill notifications.
  4. You prompt the patient (however you want — push, in-app, email) and collect a progress check-in, then submit it with medications.submitProgressCheckin().
  5. When the refill actually happens, call createOrder() again with renewsOrderReference set to the prior order's medicationRequestId. If it doesn't happen, call discontinueOrder() instead — this is what lets a therapy leave the "still counting down" state.

Creating an order

const order = await client.medications.createOrder(
  externalId,
  {
    externalOrderReference: "wellvi_order_9182",
    medicationName: "Semaglutide",
    medicationCategory: "peptide",
    dosage: "0.25mg",
    frequency: "weekly",
    expectedSupplyDurationDays: 28,
    startDate: "2026-08-18",
    tebraPracticeConfigId: "5f2c1e3a-...",
  },
  "wellvi_order_9182" // idempotency key — safe to retry on network error
);
order = client.medications.create_order(
    external_id,
    {
        "externalOrderReference": "wellvi_order_9182",
        "medicationName": "Semaglutide",
        "medicationCategory": "peptide",
        "dosage": "0.25mg",
        "frequency": "weekly",
        "expectedSupplyDurationDays": 28,
        "startDate": "2026-08-18",
        "tebraPracticeConfigId": "5f2c1e3a-...",
    },
    idempotency_key="wellvi_order_9182",
)

tebraPracticeConfigId identifies which practice's Tebra credential to sync through — configure practices under Partner Portal → Settings → Tebra Practices first.

Polling for refills due

const due = await client.medications.getRefillsDue({ withinDays: 5 });
for (const item of due.medications) {
  // item.externalOrderReference is YOUR OWN reference from createOrder() — correlate against
  // your own records the same way you already do for that value. It is not the raw externalId;
  // OnePath tokenizes that on write and cannot reverse it, so there's nothing else to return here.
  await notifyPatientForRefill(item.externalOrderReference, item.daysUntilDue);
}

Run this on whatever cadence suits you — daily is typical. An order only appears once per refill cycle; after it's returned it won't resurface until a new order references it via renewsOrderReference.

Submitting a progress check-in

await client.medications.submitProgressCheckin(externalId, order.medicationRequestId, {
  externalCheckinReference: "wellvi_checkin_4471",
  answers: [
    { code: "72514-3", display: "Pain severity", value: "3" },
    { code: "wellvi-side-effects", display: "Side effects", value: "Mild nausea, resolved after week 1" },
  ],
});

Use a LOINC code where one exists; otherwise a free-text local code is fine — OnePath stores whatever you send as a FHIR Observation linked to the order via basedOn.

Closing the loop

// Refilled — call createOrder() again, pointing at the order being renewed:
await client.medications.createOrder(externalId, {
  ...newOrderParams,
  renewsOrderReference: order.medicationRequestId,
});

// Not refilled — tell OnePath why, so it stops counting down:
await client.medications.discontinueOrder(externalId, order.medicationRequestId, {
  reason: "patient-discontinued",
});

Without one of these two calls, an order flagged "refill due" has no way to leave that state — OnePath can't tell "refilled and we haven't heard yet" from "patient dropped off" from "physician declined."

HIPAA for Integrators

What HIPAA means for your OnePath integration, and what you need to do.

SDKs

Official client libraries for OnePath Connect.

On this page

The flowCreating an orderPolling for refills dueSubmitting a progress check-inClosing the loop