Skip to content

Authentication API Endpoints

This document contains the API contract specifications for authentication-related endpoints in the RestartiX application.

API Conventions

  • Base path: /v1/ (versioned from day one)
  • Content-Type: application/json for all request/response bodies
  • Authentication: Clerk session token in Authorization: Bearer <token> header
  • Organization context: Determined by user's current_organization_id (set via /me/switch-organization)
  • Errors: Consistent { "error": { "code": "...", "message": "..." } } format

Standard Response Formats

Single Resource

json
{
  "data": {
    "id": 1,
    "title": "Initial Consultation",
    "status": "upcoming",
    "created_at": "2025-01-15T10:30:00Z"
  }
}

Error

json
{
  "error": {
    "code": "appointment_not_found",
    "message": "Appointment not found",
    "details": null
  }
}

Validation Error

json
{
  "error": {
    "code": "validation_error",
    "message": "Validation failed",
    "details": {
      "fields": {
        "email": "must be a valid email address",
        "name": "is required"
      }
    }
  }
}

Endpoints

GET /v1/me

Returns the current authenticated user with organization context.

Authentication: Required - Clerk session token

Request: No body required

Response: 200

json
{
  "data": {
    "id": 42,
    "email": "[email protected]",
    "username": "[email protected]",
    "role": "specialist",
    "confirmed": true,
    "last_activity": "2025-01-15T14:22:00Z",
    "current_organization": {
      "id": 1,
      "name": "RestartiX",
      "slug": "restartix"
    },
    "organization_ids": [1, 3],
    "specialist_id": 2,
    "specialist_name": "Dr. Smith",
    "patient_id": null
  }
}

Notes:

  • This endpoint provides the full user context including their current organization
  • The organization_ids array shows all organizations the user belongs to
  • Role-specific IDs are included (specialist_id, patient_id) with null for non-applicable roles
  • last_activity timestamp is useful for session management

PUT /v1/me/switch-organization

Switch the user's active organization context.

Authentication: Required - Clerk session token

Request:

json
{
  "organization_id": 3
}

Response: 200

json
{
  "data": {
    "current_organization": {
      "id": 3,
      "name": "HealthCorp",
      "slug": "healthcorp"
    },
    "message": "Organization switched successfully"
  }
}

Errors:

  • 403 forbidden - User is not a member of this organization
  • 404 organization_not_found - Organization doesn't exist

Notes:

  • The user must be a member of the target organization (must exist in their organization_ids array)
  • After switching, all subsequent API requests will be scoped to the new organization context
  • This affects data visibility, RLS policies, and available resources

POST /webhooks/clerk

Clerk webhook endpoint for user sync events. Verified by Clerk signature.

Authentication: Verified by Clerk webhook signature (not user token)

Events handled:

  • user.created → Create internal user record
  • user.updated → Update email/username
  • user.deleted → Soft-delete or block user

Request: The request body follows Clerk's webhook event format. The structure varies by event type.

Response: 200

json
{
  "success": true
}

Notes:

  • This endpoint is called by Clerk's servers, not by client applications
  • Request verification is done via Clerk's webhook signature in the request headers
  • Used to keep internal user records synchronized with Clerk's authentication system
  • Handles user lifecycle events from Clerk
  • Should implement idempotency to handle duplicate webhook deliveries
  • Error responses should still return 200 to prevent Clerk from retrying valid but already-processed events

Error Code Reference

CodeHTTPDescription
validation_error400Input validation failed
unauthorized401Missing or invalid auth token
forbidden403Insufficient permissions
not_found404Resource not found
conflict409Resource already exists or state conflict
rate_limited429Too many requests
internal_error500Unexpected server error
service_unavailable502External service unavailable
organization_not_found404Organization doesn't exist