Skip to main content
GET
/
api
/
models
curl -X GET 'http://localhost:5079/api/models' \
  -H 'Authorization: Bearer YOUR_JWT_TOKEN'
{
  "items": [
    {
      "modelId": "model-uuid-1",
      "modelName": "llama-3.3-70b-versatile",
      "displayName": "Llama 3.3 70B Versatile",
      "providerName": "groq",
      "apiUrl": "https://api.groq.com/openai/v1/chat/completions",
      "status": "active"
    },
    {
      "modelId": "model-uuid-2",
      "modelName": "mixtral-8x7b-32768",
      "displayName": "Mixtral 8x7B",
      "providerName": "groq",
      "apiUrl": "https://api.groq.com/openai/v1/chat/completions",
      "status": "active"
    }
  ]
}

Authentication

Required: JWT Bearer token

Response

items
array
Array of active model objects
curl -X GET 'http://localhost:5079/api/models' \
  -H 'Authorization: Bearer YOUR_JWT_TOKEN'
{
  "items": [
    {
      "modelId": "model-uuid-1",
      "modelName": "llama-3.3-70b-versatile",
      "displayName": "Llama 3.3 70B Versatile",
      "providerName": "groq",
      "apiUrl": "https://api.groq.com/openai/v1/chat/completions",
      "status": "active"
    },
    {
      "modelId": "model-uuid-2",
      "modelName": "mixtral-8x7b-32768",
      "displayName": "Mixtral 8x7B",
      "providerName": "groq",
      "apiUrl": "https://api.groq.com/openai/v1/chat/completions",
      "status": "active"
    }
  ]
}

Side Effects

Database Reads (Lines 29-33):
var rows = await _supabase.SelectAsync<JObject>(
    "ai_models",
    "model_id,model_name,provider_name,api_url,description,status,created_at",
    "status=eq.active&order=created_at.desc"
);
Tables Read:
  • ai_models table
Filter Applied (Line 32):
  • WHERE status = 'active'
  • ORDER BY created_at DESC
No Database Writes: Read-only endpoint

Authorization

Authentication: Required (JWT Bearer) Who Can Read:
  • Any authenticated user
Data Visibility:
  • Global model list (not user-specific)
  • All users see same models

Permissions

No User Filtering: All authenticated users see same data No Privacy Controls: All active model data visible to authenticated users

Response Structure

Ordering (Line 32):
  • Ordered by created_at DESC (newest models first)
  • Hardcoded in query, not configurable
Filtering (Line 32):
  • Only status = 'active' models returned
  • Inactive models excluded
  • No additional filtering parameters
Pagination: Not supported
  • Returns ALL active models
  • Performance depends on number of active models

Edge Cases

  1. No active models: Returns {"items": []} (empty array, Line 35)
  2. Model missing description: displayName falls back to modelName (Line 39)
  3. Null fields: Converted to null in JSON response (Lines 37-42)
  4. Very large result set: No pagination, could be slow

Error Conditions

CodeHTTPCauseController Line
N/A401JWT missing or invalidMiddleware
MODELS_ERROR500Database query failure47-55
MODELS_ERROR500Supabase connection error47-55
Exception Handling (Lines 47-55):
catch (Exception ex) {
    return StatusCode(500, new { error = ex.Message, code = "MODELS_ERROR" });
}
  • All exceptions return 500
  • Exception message exposed to client

Field Mapping

Column → Response Mapping (Lines 35-43):
ai_models.model_id → modelId
ai_models.model_name → modelName
ai_models.description → displayName (fallback: model_name)
ai_models.provider_name → providerName
ai_models.api_url → apiUrl
ai_models.status → status
created_at: Selected from database (Line 31) but NOT included in response (Lines 37-42)

Behavioral Guarantees

Data Staleness: Not specified by API contract
  • Caching behavior not enforced by server contract
  • Real-time database query (no caching documented in controller)
Consistency: Not guaranteed
  • Models added/removed during request processing may not be reflected
Completeness: All active models returned
  • Partial results not enforced by server contract

Performance Characteristics

Query Complexity: Simple SELECT with WHERE and ORDER BY Index Requirements:
  • ai_models.status should be indexed
  • ai_models.created_at should be indexed for sorting
Response Size: Unbounded (proportional to number of active models) No Rate Limiting: Not documented in controller

Use Cases

Model Selection:
  • Populate model dropdown in UI
  • GetRandomModelAsync service queries this data
  • GetTwoRandomModelsAsync for dual-chat
Configuration:
  • Determine available providers
  • Get API endpoints for model routing
Display:
  • Show model names and descriptions to users

Status Values

Filtered Value: "active" (Line 32) Other Possible Values (not returned):
  • "inactive": Models disabled/deprecated
  • "testing": Models in beta
  • Behavior not enforced by server contract (database schema-dependent)

Provider Information

apiUrl Field (Line 41):
  • Full provider API endpoint
  • Used by chat providers for routing
  • Exposed to authenticated clients
Security: API URLs visible to all authenticated users