REST API v1

Integrate HandoffRx into your EHR

The HandoffRx API lets you send and receive behavioral health referrals, browse the provider directory, and get AI-powered clinical matches — all from your existing workflows.

🔒
HIPAA Compliant
End-to-end encryption, audit logs
Real-time
Webhooks for instant event notifications
🏥
AHCCCS-Ready
Built for the Arizona Medicaid ecosystem

Authentication

All API requests must include your API key in the Authorization header as a Bearer token. API keys start with hrx_.

Generate your API key

Visit your API Keys dashboard to generate a key. Keys are shown once on creation — store them securely.

curl
curl https://handoffrx.com/api/v1/referrals \
  -H "Authorization: Bearer hrx_your_api_key_here"
javascript
const res = await fetch("https://handoffrx.com/api/v1/referrals", {
  headers: {
    "Authorization": "Bearer hrx_your_api_key_here",
    "Content-Type": "application/json",
  },
});
const { data } = await res.json();

Base URL

https://handoffrx.com/api/v1

Rate Limits

PlanRate LimitMonthly Cap
Free10 req/min100 requests
Pro100 req/minUnlimited
Enterprise500 req/minUnlimited

Errors

All errors return a JSON object with an error field describing the issue.

401
UnauthorizedMissing or invalid API key
403
ForbiddenAPI key lacks required scope for this action
404
Not FoundResource does not exist or you don't have access
422
UnprocessableMissing required fields or validation error
500
Server ErrorInternal error — contact support

Referrals

Create and manage clinical referrals. Requires referrals:read or referrals:write scope.

GET/api/v1/referrals

List all referrals sent by or to your practice. Supports pagination and status filtering.

Query Parameters

statusstringFilter by status: pending, accepted, declined, scheduled, completed
limitintegerResults per page (default: 20, max: 100)
offsetintegerPagination offset (default: 0)
curl
curl "https://handoffrx.com/api/v1/referrals?status=pending&limit=10" \
  -H "Authorization: Bearer hrx_your_key"
Response
{
  "data": [
    {
      "id": "550e8400-e29b-41d4-a716-446655440000",
      "client_first": "Maria",
      "client_last": "Hernandez",
      "client_insurance": "AHCCCS",
      "sent_to_practice": "Sonora Behavioral Health",
      "service_needed": "IOP - Substance Use",
      "status": "pending",
      "is_urgent": false,
      "created_at": "2026-04-10T14:22:00Z"
    }
  ],
  "count": 1,
  "limit": 10,
  "offset": 0
}
POST/api/v1/referrals

Create a new referral. Requires referrals:write.

⚖️ Anti-Brokering Compliance

clinical_justification is required (min 10 characters) per Arizona ARS §36-2212 and AHCCCS anti-brokering regulations. This field is audit-logged.

curl
curl -X POST https://handoffrx.com/api/v1/referrals \
  -H "Authorization: Bearer hrx_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "client_first": "Maria",
    "client_last": "Hernandez",
    "client_dob": "1985-03-15",
    "client_ahcccs_id": "AZ123456789",
    "client_insurance": "AHCCCS",
    "sent_to_practice": "Sonora Behavioral Health",
    "service_needed": "IOP - Substance Use",
    "level_of_care": "IOP",
    "diagnosis": "F10.20",
    "risk_level": "medium",
    "is_urgent": false,
    "clinical_justification": "Client meets ASAM criteria for IOP level of care. Motivated for treatment, stable housing, support system in place."
  }'
javascript
const res = await fetch("https://handoffrx.com/api/v1/referrals", {
  method: "POST",
  headers: {
    "Authorization": "Bearer hrx_your_key",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    client_first: "Maria",
    client_last: "Hernandez",
    client_insurance: "AHCCCS",
    sent_to_practice: "Sonora Behavioral Health",
    service_needed: "IOP - Substance Use",
    level_of_care: "IOP",
    clinical_justification: "Client meets ASAM criteria for IOP. Motivated for treatment.",
  }),
});
const referral = await res.json(); // status 201
GET/api/v1/referrals/:id

Fetch a single referral by ID. Returns 404 if the referral doesn't exist or you don't have access.

curl
curl "https://handoffrx.com/api/v1/referrals/550e8400-e29b-41d4-a716-446655440000" \
  -H "Authorization: Bearer hrx_your_key"
PATCH/api/v1/referrals/:id

Update a referral status or notes. Fires a webhook when status changes. Requires referrals:write.

curl
curl -X PATCH "https://handoffrx.com/api/v1/referrals/550e8400-..." \
  -H "Authorization: Bearer hrx_your_key" \
  -H "Content-Type: application/json" \
  -d '{"status": "accepted", "outcome_notes": "Client scheduled for intake assessment."}'

Providers

Browse the HandoffRx provider directory. Requires providers:read scope.

GET/api/v1/providers

List providers currently accepting clients. Filter by county, facility type, and availability.

curl
curl "https://handoffrx.com/api/v1/providers?county=Maricopa&facility_type=IOP&has_availability=true" \
  -H "Authorization: Bearer hrx_your_key"
Response
{
  "data": [
    {
      "id": "...",
      "practice": "Desert Sky IOP",
      "county": "Maricopa",
      "facility_type": "IOP",
      "available_iop_slots": 3,
      "insurance_accepted": ["AHCCCS", "Banner"],
      "accepting_clients": true
    }
  ],
  "count": 8,
  "limit": 20,
  "offset": 0
}

Clinical Matching

Get AI-powered provider recommendations based on clinical criteria. Scoring is based exclusively on clinical factors — no financial relationships influence results.

POST/api/v1/match

Returns the top 5 clinically-matched providers. Scoring: facility type match (30pts), insurance match (25pts), availability (20pts), specialties (15pts), provider rating (10pts).

curl
curl -X POST https://handoffrx.com/api/v1/match \
  -H "Authorization: Bearer hrx_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "level_of_care": "IOP",
    "insurance": "AHCCCS",
    "diagnosis": "F10.20",
    "risk_level": "medium"
  }'
Response
{
  "matches": [
    {
      "provider_id": "...",
      "practice": "Desert Sky IOP",
      "score": 90,
      "reasons": ["Facility type (IOP) matches IOP", "Accepts AHCCCS", "3 IOP slots available"],
      "available_iop_slots": 3,
      "county": "Maricopa",
      "facility_type": "IOP"
    }
  ]
}

Webhooks

Configure webhook endpoints to receive real-time notifications when referral events occur. Set up webhooks in your API Keys dashboard.

Event Types

referral.createdA new referral was sent to your practice
referral.acceptedA referral was accepted by the receiving provider
referral.declinedA referral was declined
referral.scheduledAn appointment was scheduled
referral.completedThe referral was marked as completed

Webhook Payload

JSON
{
  "event": "referral.accepted",
  "data": {
    "referral_id": "550e8400-e29b-41d4-a716-446655440000",
    "status": "accepted",
    "updated_at": "2026-04-10T15:30:00Z"
  },
  "timestamp": "2026-04-10T15:30:00.123Z"
}

Verifying Signatures

Every webhook includes an X-HandoffRx-Signature header. Verify it using your webhook secret to ensure the request came from HandoffRx.

javascript
import { createHash } from "crypto";

function verifyWebhook(rawBody: string, secret: string, signatureHeader: string): boolean {
  const expected = "sha256=" + createHash("sha256").update(secret + rawBody).digest("hex");
  return expected === signatureHeader;
}

// In your Next.js route handler:
export async function POST(req: Request) {
  const rawBody = await req.text();
  const sig = req.headers.get("x-handoffrx-signature") || "";
  const webhookSecret = process.env.HANDOFFRX_WEBHOOK_SECRET!;

  if (!verifyWebhook(rawBody, webhookSecret, sig)) {
    return new Response("Unauthorized", { status: 401 });
  }

  const { event, data } = JSON.parse(rawBody);
  // Handle event...
  return new Response("OK");
}

Ready to integrate?

Generate your API key →

Have questions? support@handoffrx.com