Practices and connections
Your organization is a partner on Thea. A partner works with one or more practices (clinics). Each practice connects to your organization once, and a Thea practice admin approves it, because the practice admin controls which clinicians have Thea seats and what the practice pays.
Connecting gives you a practice key for that practice. Every request about the practice’s data uses it, together with your partner key. See Authentication.
Connect a practice
Section titled “Connect a practice”-
Send the admin to Thea. From your product (for example, a “Connect Thea” button in practice settings), redirect the practice admin to:
https://app.theahealth.com/connect/{partner_slug}?redirect_uri={redirect_uri}&state={state}partner_slugis your organization’s identifier, which Thea gives you with your partner key.redirect_urimust exactly match one you’ve registered with Thea.stateis an opaque value you generate per attempt. Check it when the admin comes back, to block forged callbacks.
Use
https://dev.theahealth.com/connect/…in the sandbox. -
The admin approves. They sign in to Thea (or sign the practice up, including a payment method), review the scopes your organization agreed with Thea, and approve the connection.
-
Thea redirects back to
{redirect_uri}?code={code}&state={state}. Codes are single-use and expire after 10 minutes. -
Exchange the code from your server, with your partner key:
Terminal window curl -X POST "$THEA_API/connect/token" \-H "Authorization: Bearer $THEA_PARTNER_KEY" \-H "Content-Type: application/json" \-d '{ "grant_type": "authorization_code", "code": "cc_9Hd2kQ7xLm", "redirect_uri": "https://app.acme-ehr.example/integrations/thea/callback" }'Response {"practice_id": "152","practice_name": "Riverbend Family Medicine","practice_key": "thea_pk_test_7Rk2pQ9vXa3mLc8tYb4nWe6s","scopes": ["patients:read", "patients:write", "cases:read", "cases:write","messages:read", "messages:write", "files:write","providers:read", "providers:write"],"connected_at": "2026-11-04T15:04:05Z"}Store
practice_keysecurely now: it’s returned only once.
A code that’s expired, already used, or issued for a different redirect_uri
returns 400 invalid-grant. Send the admin
through the flow again.
Mapping your practices and locations to Thea practices is up to you. One of your multi-location organizations may be one Thea practice, or several.
What a practice key can reach
Section titled “What a practice key can reach”A practice key only reaches its own practice:
- Lists (
GET /patients,GET /cases) return that practice’s records. Make one call per practice key. - Retrieving a patient or case from another practice returns
404 not-found, the same as one that doesn’t exist, so IDs from other practices reveal nothing. practice_idis optional in request bodies. If you send it, it must match the key’s practice, or the request fails with403 practice-mismatch. The same applies topractice_idin paths such as/practices/{practice_id}/providers.
Keeping track of practices
Section titled “Keeping track of practices”Store each practice’s practice_id together with its practice key when you
exchange the code. Practice IDs don’t change.
Disconnect
Section titled “Disconnect”A connection can end three ways:
- The practice admin disconnects your organization in Thea.
- Your server calls
DELETE /practices/{practice_id}/connection. - Thea disconnects it, for example at the practice’s request.
Either way the practice key stops working immediately, and Thea sends a
practice.disconnected webhook. Then:
- Open cases carry on in Thea, and clinicians finish them there. Cases closed after the disconnect don’t reach you.
- Stop offering eConsults for that practice, and clear its roster mapping.
- Records you created stay in Thea.
Requests with a disconnected practice’s key return
403 practice-not-connected.
Webhooks and practices
Section titled “Webhooks and practices”Webhook endpoints belong to your organization, not to one practice. An endpoint
receives events from every connected practice; each event includes its
practice_id, so you can pick the right practice key when you fetch details.

