{
  "openapi": "3.0.3",
  "info": {
    "title": "VIABLE Lab API",
    "version": "1.4.2",
    "description": "## Welcome to the VIABLE Lab API\n\nThe VIABLE Lab API is a single, model-first API for chat, multimodal reasoning, VETTING workflows, published agent orchestration, embeddings, image generation, text-to-speech, and audio transcription. Existing OpenAI-compatible chat clients can keep using `/v1/chat/completions`; new examples use full model IDs such as `gpt-4.1-nano`, `gpt-4o`, and `gpt-4o-mini-tts`, or VIABLE aliases such as `viable-2`. Legacy short aliases remain accepted for existing integrations; new integrations should use full model IDs or VIABLE aliases.\n\n## Quick Start\n\n1. Choose the endpoint for the job: chat, VETTING, agents, embeddings, images, speech, or transcription.\n2. Send a full model ID or a VIABLE alias in the `model` field.\n3. Use `GET /v1/models` or `GET /v1/docs/metadata` when a client needs the current public model catalog, endpoints, quickstarts, capabilities, and pricing notes.\n\n## VETTING Workflows\n\n- `POST /v1/chat/vetting` keeps the familiar chat-completions shape and adds a `vetting_info` object for guided educational responses.\n- `POST /v1/vetting/full` supports structured verification against questions and answer keys when a product needs detailed attempt metadata.\n- VETTING endpoints use the same chat model registry as `/v1/chat/completions`; supported OpenAI, Google, VIABLE Lab, and future inferable chat models can be used where a chat model is required.\n- VETTING endpoints are non-streaming by design; the main chat endpoint supports streaming.\n\n## Model Selection\n\nClients normally send only `model`. The API accepts VIABLE aliases, registered model IDs, and clear model-family prefixes while keeping routing details internal. If a model ID cannot be resolved clearly, the API returns a structured 400 response with guidance to use a listed model ID from `/v1/models`.\n\n## Modalities\n\n- Chat: `POST /v1/chat/completions`, OpenAI-compatible JSON, optional streaming with `stream: true`.\n- Multimodal chat: content arrays can include `text`, `image_url`, `file`, or `input_file` parts. When a Gemini model is selected through this OpenAI-compatible endpoint, supported inline data is converted to Gemini's provider format internally. Native Gemini client routes and Files API URIs are not part of the current public contract.\n- VETTING: `POST /v1/chat/vetting` for lightweight vetted chat, or `POST /v1/vetting/full` for answer-key verification workflows.\n- Agents: `POST /v1/agents/{slug}/runs` runs one turn of a published visual/code workflow. Send `input` as text, a content-part array, or an OpenAI Responses-style user message array; multimodal input requires compatible LLM nodes. Use an API key with `agents:execute` scope, preserve the returned `conversation_id`, and send it on later turns to continue the same agent chat thread.\n- Embeddings: `POST /v1/embeddings`, OpenAI-compatible embeddings request/response. Default model: `nomic-embed-text-v1.5`.\n- Image generation: `POST /v1/images/generations`, OpenAI Images-compatible JSON. Default model: `flux.2-klein`.\n- Text-to-speech: `POST /v1/audio/speech`, OpenAI Audio Speech-compatible JSON. Supports OpenAI speech models and registered VIABLE Lab speech models.\n- Audio transcription: `POST /v1/audio/transcriptions`, multipart upload. Supports OpenAI transcription models and registered VIABLE Lab transcription models.\n\n## Agents and Conversations\n\nPublished agents are workflows authored in the developer dashboard. A graph can chain model calls, branch, loop within configured budgets, call image generation, accept text or multimodal user input when the receiving LLM model supports it, and return text plus generated assets behind one stable endpoint. The public data-plane endpoint is `POST /v1/agents/{slug}/runs`.\n\n`conversation_id` is specific to published agent runs. The first run creates a conversation; clients should store the returned ID per end-user session and agent, then pass it back on later turns. For direct chat or VETTING, include the context required by the request and treat any app- or provider-level session state as separate from this field.\n\n## Usage, Cost, and Logging\n\nToken pricing is registry-backed when listed. Models without listed pricing are logged with `null` cost rather than guessed. Image prices may be documented as starting prices when final cost varies by resolution. Audio prices are per minute, so cost is calculated only when duration is provided or returned by a provider. Logs capture request ID, platform, auth fingerprint, requested model, endpoint mode, status, latency, usage, cost marker, streaming flag, multimodal/file metadata, and logged request/response payloads. Request and response text is retained by default for research replay, including chat history, prompts, VETTING configuration, and text-to-speech input. Supported encrypted VETTING prompt fields sent as `enc::...` are decrypted before logging so research exports contain the prompt text used by the model. User-provided inline Agent media is preserved byte-for-byte in private R2; D1 logs, traces, and conversation messages keep authenticated asset references instead of base64. Exact HTTPS source URLs are retained as restricted provenance metadata but are not fetched automatically. Credentials, sensitive headers, provider secrets, generated image base64, and standalone encryption utility payloads are never stored as raw research content.\n\n## Developer Metadata\n\nUse `GET /v1/docs/metadata` for a compact machine-readable catalog for developer frontends, quickstarts, endpoint modes, default models, model capabilities, and pricing notes.\n\n## Developer Dashboard and Playground\n\nThe dashboard provides project API keys, logs, usage, the API Playground, and the agent canvas/test chat. Playground and dashboard agent test runs are metered through selected API keys so logs and credit accounting match production behavior. Dashboard control-plane routes are not part of this public OpenAPI document.\n\n## Authentication\n\nProtected API calls use a VIABLE Lab API key sent as `Authorization: Bearer <vlab_sk_...>` or `X-API-Key`. Use `model:request` for model endpoints, `utils:crypto` for encryption utilities, and `agents:execute` for published agent runs. Create and manage keys in the VIABLE Lab developer dashboard.",
    "contact": {
      "name": "VIABLE Lab Support",
      "email": "info@viablelab.org",
      "url": "https://www.viablelab.org"
    }
  },
  "servers": [
    {
      "url": "https://api.viablelab.org",
      "description": "Production API"
    }
  ],
  "x-tagGroups": [
    {
      "name": "API Status & Models",
      "tags": [
        "Status",
        "Models",
        "Developer Metadata"
      ]
    },
    {
      "name": "Chat",
      "tags": [
        "Chat - Completions"
      ]
    },
    {
      "name": "Embeddings and Images",
      "tags": [
        "Embeddings",
        "Images"
      ]
    },
    {
      "name": "Audio",
      "tags": [
        "Audio"
      ]
    },
    {
      "name": "VETTING Service",
      "tags": [
        "VETTING - Full"
      ]
    },
    {
      "name": "Agents",
      "tags": [
        "Agents"
      ]
    }
  ],
  "tags": [
    {
      "name": "Status",
      "description": "API health and information endpoints."
    },
    {
      "name": "Models",
      "description": "Retrieve public model, alias, capability, and pricing metadata."
    },
    {
      "name": "Chat - Completions",
      "description": "Generate standard or vetted model responses using an OpenAI-compatible format."
    },
    {
      "name": "Audio",
      "description": "Generate speech audio and transcribe uploaded audio."
    },
    {
      "name": "VETTING - Full",
      "description": "Generate model responses with a comprehensive verification layer for educational use cases."
    },
    {
      "name": "Developer Metadata",
      "description": "Machine-readable docs metadata for developer portals and clients."
    },
    {
      "name": "Embeddings",
      "description": "Create vector embeddings from text input."
    },
    {
      "name": "Images",
      "description": "Generate images from text prompts."
    },
    {
      "name": "Agents",
      "description": "Run published agent orchestrations (multi-step workflows) with an API key."
    }
  ],
  "paths": {
    "/": {
      "get": {
        "tags": [
          "Status"
        ],
        "summary": "Get API Status",
        "description": "Provides basic status information for the VIABLE Lab API. Useful for health checks. No authentication required.",
        "operationId": "getRootStatus",
        "responses": {
          "200": {
            "description": "Successful response indicating the router is running.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/StatusResponse"
                },
                "example": {
                  "status": "ok",
                  "message": "VIABLE Lab API is running",
                  "documentation": "https://developers.viablelab.org/",
                  "metadata": "/v1/docs/metadata",
                  "default_model": "gpt-4.1-nano",
                  "supported_models": [
                    "viable-1",
                    "viable-2",
                    "viable-3",
                    "viable-4",
                    "viable-5",
                    "gpt-5.5",
                    "gpt-5.4-mini",
                    "gpt-5.4-nano",
                    "gpt-5",
                    "gpt-5-mini",
                    "gpt-5-nano",
                    "gpt-5-chat-latest",
                    "gpt-4.1",
                    "gpt-4.1-mini",
                    "gpt-4.1-nano",
                    "gpt-4o",
                    "gpt-4o-mini",
                    "gemini-3.1-pro",
                    "gemini-3.5-flash",
                    "gemini-2.5-flash",
                    "nomic-embed-text-v1.5",
                    "flux.2-klein",
                    "whisper-large-v3",
                    "gpt-4o-transcribe",
                    "gpt-4o-mini-transcribe",
                    "whisper-1",
                    "kokoro",
                    "gpt-4o-mini-tts",
                    "tts-1",
                    "tts-1-hd",
                    "gpt-oss-120b",
                    "gpt-oss-20b",
                    "llama-3.1-8b-instruct",
                    "llama-3.1-70b-instruct"
                  ],
                  "upcoming_models": []
                }
              }
            }
          },
          "500": {
            "$ref": "#/components/responses/ServerError"
          }
        }
      }
    },
    "/v1/models": {
      "get": {
        "tags": [
          "Models"
        ],
        "summary": "List Available Models",
        "description": "Retrieves the public model catalog generated from the API model registry. The response includes endpoint mode, capability flags, streaming support, supported public aliases, legacy compatibility aliases, and pricing when listed. Prefer full model IDs for new integrations; VIABLE aliases are stable public model IDs and their internal routing is managed by VIABLE Lab.",
        "operationId": "listModels",
        "responses": {
          "200": {
            "description": "A list of available models.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ModelListResponse"
                },
                "example": {
                  "object": "list",
                  "default_model": "gpt-4.1-nano",
                  "aliases": {
                    "4o": "gpt-4o",
                    "4omni": "gpt-4o",
                    "nano": "gpt-4.1-nano",
                    "mini": "gpt-4.1-mini"
                  },
                  "available_models": [
                    {
                      "id": "viable-1",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Recommended for complex evaluation and sophisticated text generation. Operates at a higher cost tier; mindful token usage is advised for long contexts.",
                      "owned_by": "viable-lab",
                      "intelligence": "High",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1047576,
                      "max_output_tokens": 32768,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.4,
                        "output_per_million": 1.6,
                        "cached_input_per_million": 0.1,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "viable-2",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Optimized for efficiency in common tasks like classification, summarization, and standard text completion.",
                      "owned_by": "viable-lab",
                      "intelligence": "Average",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1047576,
                      "max_output_tokens": 32768,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.1,
                        "output_per_million": 0.4,
                        "cached_input_per_million": 0.025,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "viable-3",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "A balanced model for performance and cost, offering stable results. Recommended when specific output formatting is crucial.",
                      "owned_by": "viable-lab",
                      "intelligence": "Average",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 128000,
                      "max_output_tokens": 16384,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.15,
                        "output_per_million": 0.6,
                        "cached_input_per_million": 0.075,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "viable-4",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "High-performance viable access point for well-defined tasks with fast responses and strong reasoning on structured prompts.",
                      "owned_by": "viable-lab",
                      "intelligence": "High",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.25,
                        "output_per_million": 2,
                        "cached_input_per_million": 0.025,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "viable-5",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Cost-optimized viable access point tuned for fastest responses and high-throughput use cases like summarization and classification.",
                      "owned_by": "viable-lab",
                      "intelligence": "Average",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.05,
                        "output_per_million": 0.4,
                        "cached_input_per_million": 0.005,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-5.5",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "GPT-5.5 model configuration for advanced chat, reasoning, and multimodal workflows.",
                      "owned_by": "openai",
                      "intelligence": "Higher",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 5,
                        "output_per_million": 30,
                        "cached_input_per_million": 0.5,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": "OpenAI standard short-context public pricing, per 1M tokens: $5 input, $0.50 cached input, $30 output."
                      }
                    },
                    {
                      "id": "gpt-5.4-mini",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "GPT-5.4 mini model configuration for balanced chat, reasoning, and multimodal workflows.",
                      "owned_by": "openai",
                      "intelligence": "High",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.75,
                        "output_per_million": 4.5,
                        "cached_input_per_million": 0.075,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": "OpenAI standard public pricing, per 1M tokens: $0.75 input, $0.075 cached input, $4.50 output."
                      }
                    },
                    {
                      "id": "gpt-5.4-nano",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "GPT-5.4 nano model configuration for latency-sensitive chat and classification workflows.",
                      "owned_by": "openai",
                      "intelligence": "Average",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.2,
                        "output_per_million": 1.25,
                        "cached_input_per_million": 0.02,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": "OpenAI standard public pricing, per 1M tokens: $0.20 input, $0.02 cached input, $1.25 output."
                      }
                    },
                    {
                      "id": "gpt-5",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-5, the flagship model for coding, reasoning, and agentic tasks across domains.",
                      "owned_by": "openai",
                      "intelligence": "Higher",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 1.25,
                        "output_per_million": 10,
                        "cached_input_per_million": 0.125,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-5-mini",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-5 mini, a faster, more cost-efficient version of GPT-5 for well-defined tasks.",
                      "owned_by": "openai",
                      "intelligence": "High",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.25,
                        "output_per_million": 2,
                        "cached_input_per_million": 0.025,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-5-nano",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-5 nano, the fastest, most cost-efficient version of GPT-5 for summarization and classification.",
                      "owned_by": "openai",
                      "intelligence": "Average",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.05,
                        "output_per_million": 0.4,
                        "cached_input_per_million": 0.005,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-5-chat-latest",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-5 Chat, the snapshot currently used in ChatGPT.",
                      "owned_by": "openai",
                      "intelligence": "High",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 400000,
                      "max_output_tokens": 128000,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 1.25,
                        "output_per_million": 10,
                        "cached_input_per_million": 0.125,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-4.1",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-4.1. Flagship OpenAI model for complex tasks. It is well suited for problem solving across domains.",
                      "owned_by": "openai",
                      "intelligence": "Higher",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1047576,
                      "max_output_tokens": 32768,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 2,
                        "output_per_million": 8,
                        "cached_input_per_million": 0.5,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-4.1-mini",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-4.1 mini, balancing intelligence, speed, and cost for many use cases.",
                      "owned_by": "openai",
                      "intelligence": "High",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1047576,
                      "max_output_tokens": 32768,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.4,
                        "output_per_million": 1.6,
                        "cached_input_per_million": 0.1,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-4.1-nano",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-4.1 nano, the fastest, most cost-efficient version of GPT-4.1 for summarization and classification.",
                      "owned_by": "openai",
                      "intelligence": "Average",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1047576,
                      "max_output_tokens": 32768,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.1,
                        "output_per_million": 0.4,
                        "cached_input_per_million": 0.025,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-4o",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-4o. Fast, intelligent, flexible GPT model.",
                      "owned_by": "openai",
                      "intelligence": "High",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 128000,
                      "max_output_tokens": 16384,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 2.5,
                        "output_per_million": 10,
                        "cached_input_per_million": 1.25,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-4o-mini",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to GPT-4o mini.",
                      "owned_by": "openai",
                      "intelligence": "Average",
                      "speed": "Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 128000,
                      "max_output_tokens": 16384,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.15,
                        "output_per_million": 0.6,
                        "cached_input_per_million": 0.075,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gemini-3.1-pro",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Gemini 3.1 Pro model configuration for advanced multimodal reasoning.",
                      "owned_by": "google",
                      "intelligence": "Higher",
                      "speed": "Medium",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1048576,
                      "max_output_tokens": 8192,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 2,
                        "output_per_million": 12,
                        "cached_input_per_million": 0.2,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "short_context",
                        "note": "Gemini 3.1 Pro Preview paid-tier pricing for prompts <=200K tokens. Longer prompts are listed at $4/M input, $0.40/M cached input, and $18/M output."
                      }
                    },
                    {
                      "id": "gemini-3.5-flash",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Gemini 3.5 Flash model configuration for fast multimodal generation.",
                      "owned_by": "google",
                      "intelligence": "High",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1048576,
                      "max_output_tokens": 8192,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 1.5,
                        "output_per_million": 9,
                        "cached_input_per_million": 0.15,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": "Gemini 3.5 Flash paid-tier pricing, per 1M tokens: $1.50 input, $0.15 cached input, $9 output."
                      }
                    },
                    {
                      "id": "gemini-2.5-flash",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Direct access to Gemini 2.5 Flash. Optimized for speed and cost-effective multimodal generation.",
                      "owned_by": "google",
                      "intelligence": "High",
                      "speed": "Very Fast",
                      "input_modalities": [
                        "text",
                        "image",
                        "file",
                        "pdf"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": 1048576,
                      "max_output_tokens": 8192,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": true,
                        "files": true,
                        "pdf": true,
                        "audio": false,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.3,
                        "output_per_million": 2.5,
                        "cached_input_per_million": 0.030000000000000002,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": "Gemini 2.5 Flash paid-tier text/image/video pricing, per 1M tokens: $0.30 input, $0.03 cached input, $2.50 output. Audio input is listed separately at $1/M."
                      }
                    },
                    {
                      "id": "nomic-embed-text-v1.5",
                      "object": "model",
                      "mode": "embedding",
                      "endpoint": "/v1/embeddings",
                      "description": "Text embedding model for semantic search, clustering, retrieval, and ranking workflows.",
                      "owned_by": "viable-lab",
                      "intelligence": "Embedding",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "embedding"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": false,
                        "embeddings": true,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.005,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "docs_inferred",
                        "note": "Derived from provider docs: 250,000 pages per dollar at approximately 800 tokens per page."
                      }
                    },
                    {
                      "id": "flux.2-klein",
                      "object": "model",
                      "mode": "image_generation",
                      "endpoint": "/v1/images/generations",
                      "description": "Image generation model for prompt-to-image workflows.",
                      "owned_by": "viable-lab",
                      "intelligence": "Image",
                      "speed": "Medium",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "image"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": true
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": 0.014,
                        "audio_per_minute": null,
                        "status": "starts_at",
                        "note": "Provider docs list pricing from $0.014 per image; final cost varies by resolution/model variant."
                      }
                    },
                    {
                      "id": "whisper-large-v3",
                      "object": "model",
                      "mode": "audio_transcription",
                      "endpoint": "/v1/audio/transcriptions",
                      "description": "Speech-to-text model for audio transcription.",
                      "owned_by": "viable-lab",
                      "intelligence": "Audio",
                      "speed": "Medium",
                      "input_modalities": [
                        "audio",
                        "file"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": false,
                        "images": false,
                        "files": true,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": 0.006,
                        "status": "documented",
                        "note": "Provider docs list $0.006 per minute of input audio."
                      }
                    },
                    {
                      "id": "gpt-4o-transcribe",
                      "object": "model",
                      "mode": "audio_transcription",
                      "endpoint": "/v1/audio/transcriptions",
                      "description": "OpenAI speech-to-text model exposed through the VIABLE Lab API.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Medium",
                      "input_modalities": [
                        "audio",
                        "file"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": false,
                        "images": false,
                        "files": true,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 2.5,
                        "output_per_million": 10,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": 0.006,
                        "status": "documented",
                        "note": "OpenAI transcription pricing: $2.50/M input tokens, $10/M output tokens, estimated $0.006/minute."
                      }
                    },
                    {
                      "id": "gpt-4o-mini-transcribe",
                      "object": "model",
                      "mode": "audio_transcription",
                      "endpoint": "/v1/audio/transcriptions",
                      "description": "OpenAI speech-to-text model optimized for transcription workflows.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Fast",
                      "input_modalities": [
                        "audio",
                        "file"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": false,
                        "images": false,
                        "files": true,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 1.25,
                        "output_per_million": 5,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": 0.003,
                        "status": "documented",
                        "note": "OpenAI transcription pricing: $1.25/M input tokens, $5/M output tokens, estimated $0.003/minute."
                      }
                    },
                    {
                      "id": "whisper-1",
                      "object": "model",
                      "mode": "audio_transcription",
                      "endpoint": "/v1/audio/transcriptions",
                      "description": "OpenAI Whisper transcription model preserved for compatibility.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Medium",
                      "input_modalities": [
                        "audio",
                        "file"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": false,
                        "images": false,
                        "files": true,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": 0.006,
                        "status": "documented",
                        "note": "OpenAI Whisper transcription pricing is listed as $0.006 per minute."
                      }
                    },
                    {
                      "id": "kokoro",
                      "object": "model",
                      "mode": "audio_speech",
                      "endpoint": "/v1/audio/speech",
                      "description": "Text-to-speech model for generated speech audio.",
                      "owned_by": "viable-lab",
                      "intelligence": "Audio",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "audio"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "default_voice": "af_heart",
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": 0.006,
                        "status": "documented",
                        "note": "Provider docs list $0.006 per minute of generated audio."
                      }
                    },
                    {
                      "id": "gpt-4o-mini-tts",
                      "object": "model",
                      "mode": "audio_speech",
                      "endpoint": "/v1/audio/speech",
                      "description": "OpenAI text-to-speech model exposed through the VIABLE Lab API.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "audio"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "not_listed",
                        "note": null
                      }
                    },
                    {
                      "id": "tts-1",
                      "object": "model",
                      "mode": "audio_speech",
                      "endpoint": "/v1/audio/speech",
                      "description": "OpenAI text-to-speech model preserved for compatibility.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "audio"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "not_listed",
                        "note": null
                      }
                    },
                    {
                      "id": "tts-1-hd",
                      "object": "model",
                      "mode": "audio_speech",
                      "endpoint": "/v1/audio/speech",
                      "description": "OpenAI high-definition text-to-speech model preserved for compatibility.",
                      "owned_by": "openai",
                      "intelligence": "Audio",
                      "speed": "Medium",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "audio"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": false,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": true,
                        "tools": false,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": null,
                        "output_per_million": null,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "not_listed",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-oss-120b",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Open-weight 120B model for cost-efficient text generation through the VIABLE Lab API.",
                      "owned_by": "viable-lab",
                      "intelligence": "High",
                      "speed": "Medium",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.060000000000000005,
                        "output_per_million": 0.15,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "gpt-oss-20b",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Open-weight 20B model for low-cost text generation through the VIABLE Lab API.",
                      "owned_by": "viable-lab",
                      "intelligence": "Average",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.030000000000000002,
                        "output_per_million": 0.06999999999999999,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "llama-3.1-8b-instruct",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Llama 3.1 8B Instruct model for lightweight text generation through the VIABLE Lab API.",
                      "owned_by": "viable-lab",
                      "intelligence": "Average",
                      "speed": "Fast",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.22,
                        "output_per_million": 0.22,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    },
                    {
                      "id": "llama-3.1-70b-instruct",
                      "object": "model",
                      "mode": "chat",
                      "endpoint": "/v1/chat/completions",
                      "description": "Llama 3.1 70B Instruct model for stronger open-weight text generation through the VIABLE Lab API.",
                      "owned_by": "viable-lab",
                      "intelligence": "High",
                      "speed": "Medium",
                      "input_modalities": [
                        "text"
                      ],
                      "output_modalities": [
                        "text"
                      ],
                      "context_window": null,
                      "max_output_tokens": null,
                      "supports_streaming": true,
                      "capabilities": {
                        "text": true,
                        "images": false,
                        "files": false,
                        "pdf": false,
                        "audio": false,
                        "tools": true,
                        "embeddings": false,
                        "image_generation": false
                      },
                      "pricing": {
                        "input_per_million": 0.4,
                        "output_per_million": 0.4,
                        "cached_input_per_million": null,
                        "image_per_unit": null,
                        "audio_per_minute": null,
                        "status": "documented",
                        "note": null
                      }
                    }
                  ],
                  "upcoming_models": [],
                  "supported_aliases": [
                    "viable-1",
                    "viable-2",
                    "viable-3",
                    "viable-4",
                    "viable-5",
                    "4o",
                    "4omni",
                    "nano",
                    "mini"
                  ]
                }
              }
            }
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "429": {
            "$ref": "#/components/responses/RateLimited"
          },
          "500": {
            "$ref": "#/components/responses/ServerError"
          }
        }
      }
    },
    "/v1/chat/completions": {
      "post": {
        "tags": [
          "Chat - Completions"
        ],
        "summary": "Create Chat Completion",
        "description": "Creates a model response using an OpenAI-compatible chat request.\n\n**Quick Start:** change your base URL to `https://api.viablelab.org/v1/chat/completions` and keep your existing `messages`, `model`, and generation parameters.\n\n**Model Selection:** send a full model ID or VIABLE alias such as `gpt-4.1-nano`, `gpt-4o`, `gemini-2.5-flash`, `gpt-oss-120b`, `llama-3.1-70b-instruct`, or `viable-2`. If omitted, the default is `gpt-4.1-nano`. Legacy short aliases remain accepted for existing integrations, but new integrations should use full model IDs or VIABLE aliases.\n\n**Multimodal Input:** content arrays can include `text`, `image_url`, `file`, or `input_file` parts. When a Gemini model is selected, the gateway converts supported base64 data URI images/files/PDFs to native `inlineData` internally. Remote URLs are not fetched for Gemini. This route does not accept Gemini-native `contents`, Files API URIs, or Google SDK authentication; Gemini-native client compatibility is a separate future surface.\n\n**Streaming:** set `stream: true` to receive OpenAI-style SSE. Usage and error summaries are logged asynchronously so D1 logging does not delay first-token delivery. VETTING endpoints remain non-streaming.",
        "operationId": "createChatCompletion",
        "requestBody": {
          "required": true,
          "description": "Request payload conforming to the OpenAI Chat Completions format.",
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ChatCompletionRequest"
              },
              "examples": {
                "textOnlyExample": {
                  "summary": "Text-only chat",
                  "value": {
                    "model": "viable-2",
                    "messages": [
                      {
                        "role": "system",
                        "content": "You are a helpful assistant."
                      },
                      {
                        "role": "user",
                        "content": "Hello!"
                      },
                      {
                        "role": "assistant",
                        "content": "Hello! How can I assist you today?"
                      },
                      {
                        "role": "user",
                        "content": "What is your name and tell me a joke."
                      }
                    ]
                  }
                },
                "imageInputExample": {
                  "summary": "Image input (Multimodal)",
                  "value": {
                    "model": "viable-3",
                    "messages": [
                      {
                        "role": "user",
                        "content": [
                          {
                            "type": "text",
                            "text": "What is in this image?"
                          },
                          {
                            "type": "image_url",
                            "image_url": {
                              "url": "https://upload.wikimedia.org/wikipedia/commons/thumb/d/dd/Gfp-wisconsin-madison-the-nature-boardwalk.jpg/2560px-Gfp-wisconsin-madison-the-nature-boardwalk.jpg"
                            }
                          }
                        ]
                      }
                    ],
                    "max_tokens": 300
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful JSON chat completion when stream is false, or text/event-stream SSE chunks when stream is true.",
            "content": {
              "application/json": {
                "schema": {
                  "description": "Standard JSON response when `stream: false`. Structure generally follows OpenAI's format, but the `model` field in the response object is removed by the router.",
                  "type": "object",
                  "properties": {
                    "id": {
                      "type": "string",
                      "example": "chatcmpl-xxxxxxxxxxxxxxxxxxxxxxx"
                    },
                    "object": {
                      "type": "string",
                      "example": "chat.completion"
                    },
                    "created": {
                      "type": "integer",
                      "format": "int64",
                      "example": 1677652288
                    },
                    "choices": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "index": {
                            "type": "integer",
                            "example": 0
                          },
                          "message": {
                            "$ref": "#/components/schemas/ChatMessage"
                          },
                          "finish_reason": {
                            "type": "string",
                            "example": "stop"
                          }
                        }
                      }
                    },
                    "usage": {
                      "$ref": "#/components/schemas/CompletionUsage"
                    }
                  }
                },
                "examples": {
                  "nonStreamingExample": {
                    "summary": "Text-only response",
                    "value": {
                      "id": "chatcmpl-BP1zr9we9GnhROVO6W02nlAO9JYz3",
                      "object": "chat.completion",
                      "created": 1745305575,
                      "choices": [
                        {
                          "index": 0,
                          "message": {
                            "role": "assistant",
                            "content": "I'm ChatGPT, your friendly AI assistant! Here's a joke for you:\n\nWhy don't skeletons fight each other?\n\nBecause they don't have the guts!"
                          },
                          "finish_reason": "stop"
                        }
                      ],
                      "usage": {
                        "prompt_tokens": 46,
                        "completion_tokens": 31,
                        "total_tokens": 77
                      }
                    }
                  },
                  "imageResponseExample": {
                    "summary": "Image analysis response",
                    "value": {
                      "id": "chatcmpl-BPIT34H1bNWhelKkMjhnwdWlohx1w",
                      "object": "chat.completion",
                      "created": 1745368889,
                      "choices": [
                        {
                          "index": 0,
                          "message": {
                            "role": "assistant",
                            "content": "The image features a wooden boardwalk traversing through a lush green field with tall grass and some shrubs. In the background, there are trees.",
                            "refusal": null,
                            "annotations": []
                          },
                          "logprobs": null,
                          "finish_reason": "stop"
                        }
                      ],
                      "usage": {
                        "prompt_tokens": 36848,
                        "completion_tokens": 43,
                        "total_tokens": 36891
                      }
                    }
                  }
                }
              },
              "text/event-stream": {
                "schema": {
                  "type": "string"
                },
                "examples": {
                  "streaming": {
                    "summary": "Streaming chunk",
                    "value": "data: {\"id\":\"chatcmpl-...\",\"object\":\"chat.completion.chunk\",\"choices\":[{\"delta\":{\"content\":\"Hello\"},\"finish_reason\":null}]}\n\ndata: [DONE]\n\n"
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request. Can occur due to invalid JSON, missing required fields, or attempting unsupported options like streaming.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                },
                "examples": {
                  "invalidJson": {
                    "summary": "Invalid JSON Body",
                    "value": {
                      "error": {
                        "message": "Invalid request body: JSON parsing failed",
                        "type": "invalid_request_error",
                        "code": "invalid_json"
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "405": {
            "$ref": "#/components/responses/MethodNotAllowed"
          },
          "429": {
            "$ref": "#/components/responses/RateLimited"
          },
          "500": {
            "$ref": "#/components/responses/ServerError"
          },
          "501": {
            "$ref": "#/components/responses/NotImplemented"
          },
          "502": {
            "$ref": "#/components/responses/BadAPI"
          }
        }
      }
    },
    "/v1/chat/vetting": {
      "post": {
        "tags": [
          "Chat - Completions"
        ],
        "summary": "Create Vetted Chat Completion",
        "description": "Creates a chat completion with an educational VETTING pass and returns the normal chat-completions response shape plus `vetting_info`.\n\n**When to use it:** use this endpoint when a product wants guided educational responses, tutoring-style restraint, or a lightweight verification step without adopting the full answer-key workflow.\n\n**Quick Start:** send the same JSON body you would send to `/v1/chat/completions`, then change the URL to `https://api.viablelab.org/v1/chat/vetting`. The assistant message remains in `choices[0].message.content`; VETTING metadata is added at the top level.\n\n**Model Selection:** `model` uses the same chat model registry and provider routing as `/v1/chat/completions`. Full model IDs, VIABLE aliases, Google Gemini chat models, registered VIABLE Lab chat models, and future clearly inferable chat model prefixes are supported. Non-chat models such as embedding, image, speech, or transcription models return a structured 400 error. The verification model for this lightweight endpoint is managed by the API.\n\n**Customization:** optionally provide `vettingConfig.systemPrompt` for product-specific guidance and `vettingConfig.maxAttempts` to adjust the retry limit.\n\n**Multimodal Input:** image-capable chat models can receive image content in the same OpenAI-compatible message format. When a Gemini model is selected, supported base64 data URI images/files/PDFs are converted internally; remote URLs are not fetched. This is not a Gemini-native request surface. The VETTING pass focuses on the generated text response.\n\n**Streaming:** not supported for this endpoint.",
        "operationId": "createChatVettingCompletion",
        "requestBody": {
          "required": true,
          "description": "Request payload similar to OpenAI Chat Completions, with an optional `vettingConfig` for custom guidelines.",
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ChatVettingRequest"
              },
              "examples": {
                "textVettingExample": {
                  "summary": "Vetting text input",
                  "value": {
                    "model": "viable-3",
                    "messages": [
                      {
                        "role": "system",
                        "content": "You are a helpful geography tutor."
                      },
                      {
                        "role": "user",
                        "content": "What is the capital of France?"
                      }
                    ],
                    "temperature": 0.5,
                    "vettingConfig": {
                      "systemPrompt": "Do not directly state the answer...",
                      "maxAttempts": 3
                    }
                  }
                },
                "imageVettingExample": {
                  "summary": "Vetting with image input",
                  "value": {
                    "model": "viable-3",
                    "messages": [
                      {
                        "role": "user",
                        "content": [
                          {
                            "type": "text",
                            "text": "What is in this image? Avoid describing the sky."
                          },
                          {
                            "type": "image_url",
                            "image_url": {
                              "url": "https://upload.wikimedia.org/wikipedia/commons/thumb/d/dd/Gfp-wisconsin-madison-the-nature-boardwalk.jpg/2560px-Gfp-wisconsin-madison-the-nature-boardwalk.jpg"
                            }
                          }
                        ]
                      }
                    ],
                    "max_tokens": 300,
                    "vettingConfig": {
                      "systemPrompt": "Ensure the response describes the boardwalk and field but not the sky."
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful response containing the vetted assistant message in OpenAI format, plus vetting metadata.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ChatVettingResponse"
                },
                "examples": {
                  "textVettingResponse": {
                    "summary": "Vetted text response",
                    "value": {
                      "id": "chatcmpl-d148a3ed-d31e-445e-a320-654ccbf4f505",
                      "object": "chat.completion",
                      "created": 1745312855,
                      "model": "viable-3",
                      "choices": [
                        {
                          "index": 0,
                          "message": {
                            "role": "assistant",
                            "content": "Sure! To find the capital of France..."
                          },
                          "finish_reason": "stop"
                        }
                      ],
                      "usage": {
                        "prompt_tokens": 497,
                        "completion_tokens": 66,
                        "total_tokens": 563
                      },
                      "vetting_info": {
                        "attemptCount": 2,
                        "stopReason": "VERIFICATION_PASSED"
                      },
                      "safety_signals": {
                        "requires_attention": false
                      }
                    }
                  },
                  "imageVettingResponse": {
                    "summary": "Vetted image response",
                    "value": {
                      "id": "chatcmpl-BPIT34H1bNWhelKkMjhnwdWlohx1w",
                      "object": "chat.completion",
                      "created": 1746322205,
                      "model": "viable-3",
                      "choices": [
                        {
                          "index": 0,
                          "message": {
                            "role": "assistant",
                            "content": "The image features a wooden boardwalk traversing through a lush green field with tall grass and some shrubs. In the background, there are trees.",
                            "refusal": null,
                            "annotations": []
                          },
                          "logprobs": null,
                          "finish_reason": "stop"
                        }
                      ],
                      "usage": {
                        "prompt_tokens": 36848,
                        "completion_tokens": 43,
                        "total_tokens": 36891
                      },
                      "vetting_info": {
                        "attemptCount": 1,
                        "stopReason": "VERIFICATION_PASSED",
                        "lastFailureReason": null
                      },
                      "safety_signals": {
                        "requires_attention": false
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request. Can occur due to invalid JSON, missing required fields, or attempting unsupported options like streaming.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                },
                "examples": {
                  "invalidJson": {
                    "summary": "Invalid JSON Body",
                    "value": {
                      "error": {
                        "message": "Invalid JSON request body.",
                        "type": "invalid_request_error",
                        "code": "invalid_json"
                      }
                    }
                  },
                  "missingMessages": {
                    "summary": "Missing Messages Array",
                    "value": {
                      "error": {
                        "message": "Missing or invalid 'messages' array.",
                        "type": "invalid_request_error",
                        "code": "missing_messages"
                      }
                    }
                  },
                  "streamingAttempt": {
                    "summary": "Streaming Not Supported",
                    "value": {
                      "error": {
                        "message": "Streaming responses (stream: true) are not currently supported by this endpoint. Please set stream: false or omit the parameter.",
                        "type": "invalid_request_error",
                        "code": "streaming_not_supported",
                        "details": "Streaming makes it difficult to reliably log, evaluate, and ensure safety for all responses, especially with the internal vetting process."
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "405": {
            "$ref": "#/components/responses/MethodNotAllowed"
          },
          "429": {
            "$ref": "#/components/responses/RateLimited"
          },
          "500": {
            "$ref": "#/components/responses/ServerError"
          },
          "502": {
            "$ref": "#/components/responses/BadAPI"
          }
        }
      }
    },
    "/v1/audio/speech": {
      "post": {
        "tags": [
          "Audio"
        ],
        "summary": "Create Speech",
        "description": "Generates speech audio from text using an OpenAI-compatible Audio Speech request shape. OpenAI speech models such as `gpt-4o-mini-tts`, `tts-1`, and `tts-1-hd` are supported, along with registered VIABLE Lab speech models such as `kokoro`. For OpenAI speech models, send a supported OpenAI voice such as `alloy`; registered VIABLE Lab speech models can provide their own voice defaults. Audio cost is per minute when pricing is listed; logs use `duration_seconds` or `duration_minutes` if clients provide one.",
        "operationId": "createSpeech",
        "requestBody": {
          "required": true,
          "description": "Request payload for generating speech.",
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/AudioSpeechRequest"
              },
              "example": {
                "model": "gpt-4o-mini-tts",
                "input": "Hello from VIABLE Lab.",
                "voice": "alloy",
                "response_format": "mp3"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful binary audio response in the requested format.",
            "content": {
              "audio/mpeg": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "audio/opus": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "audio/aac": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "audio/flac": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "audio/wav": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "audio/pcm": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "400": {
            "$ref": "#/components/responses/BadRequest"
          },
          "401": {
            "$ref": "#/components/responses/Unauthorized"
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "405": {
            "$ref": "#/components/responses/MethodNotAllowed"
          },
          "429": {
            "$ref": "#/components/responses/RateLimited"
          },
          "500": {
            "$ref": "#/components/responses/ServerError"
          },
          "502": {
            "$ref": "#/components/responses/BadAPI"
          }
        }
      }
    },
    "/v1/vetting/full": {
      "post": {
        "tags": [
          "VETTING - Full"
        ],
        "summary": "Create Full VETTING Verification",
        "description": "Runs a full educational VETTING workflow with structured verification against questions and answer keys.\n\n**When to use it:** use this endpoint when a learning product needs detailed attempt metadata, answer-key checks, or a verification loop separate from the main chat response.\n\n**Modes:**\n- `vetting`: enables the verification layer. Requires `config.verificationModel` and `context.items` with question and answer-key data.\n- `chat`: uses this endpoint's structured request format without running verification.\n\n**Model Selection:** `config.chatModel.modelId` and `config.verificationModel.modelId` each use the same chat model registry as `/v1/chat/completions`. They may point to different providers, such as a VIABLE Lab chat model for drafting and a Gemini chat model for verification. Both entries must be chat-capable models; embedding, image, speech, and transcription models return a structured 400 error.\n\n**Output:** returns the final message, verification status, stop reason, and attempt details. Cost is `null` when any selected model has unknown pricing.\n\n**Streaming:** not supported for this endpoint.",
        "operationId": "createFullVETTINGCompletion",
        "requestBody": {
          "required": true,
          "description": "Payload for the VETTING Service. Requires `context.items` with question/answer keys in 'vetting' mode.",
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/VETTINGRequest"
              },
              "example": {
                "mode": "vetting",
                "config": {
                  "maxVerificationAttempts": 3,
                  "chatModel": {
                    "modelId": "viable-3",
                    "temperature": 0.7
                  },
                  "verificationModel": {
                    "modelId": "gpt-4o-mini",
                    "temperature": 0.1
                  }
                },
                "prompts": {
                  "chatSystemPrompt": "Your an helpful AI tutor for helping students to learning.",
                  "verificationSystemPrompt": "Evaluate the provided assistant response based on the questions and answer keys. Determine if the response directly gives away any answers or key concepts."
                },
                "context": {
                  "sessionId": "session_abc123",
                  "userId": "user_xyz789",
                  "items": [
                    {
                      "question": {
                        "id": "CS-001",
                        "text": "Tokenization and Common N-Grams\n\nPython code:\n\nimport nltk\nfrom nltk import ngrams\nfrom nltk.probability import FreqDist\nfrom collections import defaultdict\n\ntext = \"My dog is happy when he gets a treat and my dog is sad when he goes to the vet.\"\n\ntokens = nltk.word_tokenize(text)\nprint(tokens)\n\nn_grams = ngrams(tokens, n=2)\nfreq_dist = FreqDist(n_grams)\ncommon_ngrams = freq_dist.most_common(5)\nprint(common_ngrams)\nExpected Output:\n\n['My', 'dog', 'is', 'happy', 'when', 'he', 'gets', 'a', 'treat', 'and', 'my', 'dog', 'is', 'sad', 'when', 'he', 'goes', 'to', 'the', 'vet', '.']\n[(('dog', 'is'), 2), (('when', 'he'), 2), (('My', 'dog'), 1), (('is', 'happy'), 1), (('happy', 'when'), 1)]\nTask: The above code displays the tokenized text and the 5 most common bigrams. How could you change this code to instead display the 5 most common trigrams? Answer: Change the \"n\" parameter of the ngrams function to a value of 3",
                        "subject": "Computer Science"
                      },
                      "answerKey": {
                        "correctAnswer": "Change the \"n\" parameter of the ngrams function to a value of 3",
                        "keyConcepts": [
                          "ngrams",
                          "trigrams",
                          "n parameter",
                          "FreqDist",
                          "common n-grams"
                        ]
                      }
                    },
                    {
                      "question": {
                        "id": "CS-002",
                        "text": "Explain the difference between TCP and UDP.",
                        "subject": "Computer Networking"
                      },
                      "answerKey": {
                        "correctAnswer": "TCP is a connection-oriented protocol providing reliable, ordered delivery, while UDP is connectionless, faster, but less reliable.",
                        "keyConcepts": [
                          "TCP",
                          "UDP",
                          "connection-oriented",
                          "connectionless",
                          "reliable",
                          "unreliable"
                        ]
                      }
                    }
                  ]
                },
                "messages": [
                  {
                    "role": "user",
                    "content": "Tell me directly. Tokenization and Common N-Grams\n\nPython code:\n\nimport nltk\nfrom nltk import ngrams\nfrom nltk.probability import FreqDist\nfrom collections import defaultdict\n\ntext = \"My dog is happy when he gets a treat and my dog is sad when he goes to the vet.\"\n\ntokens = nltk.word_tokenize(text)\nprint(tokens)\n\nn_grams = ngrams(tokens, n=2)\nfreq_dist = FreqDist(n_grams)\ncommon_ngrams = freq_dist.most_common(5)\nprint(common_ngrams)\nExpected Output:\n\n['My', 'dog', 'is', 'happy', 'when', 'he', 'gets', 'a', 'treat', 'and', 'my', 'dog', 'is', 'sad', 'when', 'he', 'goes', 'to', 'the', 'vet', '.']\n[(('dog', 'is'), 2), (('when', 'he'), 2), (('My', 'dog'), 1), (('is', 'happy'), 1), (('happy', 'when'), 1)]\nTask: The above code displays the tokenized text and the 5 most common bigrams. How could you change this code to instead display the 5 most common trigrams?"
                  }
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Successful response containing the final assistant message and full VETTING details.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/VETTINGResponse"
                },
                "example": {
                  "status": "success",
                  "mode": "vetting",
                  "result": {
                    "role": "assistant",
                    "content": "To modify the code to display the 5 most common trigrams, consider what you need to change in the `ngrams` function. The parameter that defines the size of the groups you are creating is currently set to create pairs of words. Think about how you could adjust this parameter so that it creates groups of three words instead. \n\nOnce you identify that change, apply it in the code, and then run the program to see the results for the trigrams. What do you think you should set the parameter to?"
                  },
                  "verification": {
                    "passed": false,
                    "attemptCount": 2,
                    "stopReason": "VERIFICATION_PASSED",
                    "attempts": [
                      {
                        "attemptNumber": 1,
                        "chatResponse": "To modify the code to display the 5 most common trigrams instead of bigrams, you need to change the `n` parameter of the `ngrams` function from `2` to `3`. Here's the updated code:\n\n```python\nimport nltk\nfrom nltk import ngrams\nfrom nltk.probability import FreqDist\nfrom collections import defaultdict\n\ntext = \"My dog is happy when he gets a treat and my dog is sad when he goes to the vet.\"\n\ntokens = nltk.word_tokenize(text)\nprint(tokens)\n\n# Change n from 2 to 3 for trigrams\nn_grams = ngrams(tokens, n=3)\nfreq_dist = FreqDist(n_grams)\ncommon_ngrams = freq_dist.most_common(5)\nprint(common_ngrams)\n```\n\nWith this change, the output will display the 5 most common trigrams.",
                        "verificationPassed": false,
                        "verificationOutput": "FAILED: Directly states the answer 'change the n parameter of the ngrams function from 2 to 3'."
                      },
                      {
                        "attemptNumber": 2,
                        "chatResponse": "To modify the code to display the 5 most common trigrams, consider what you need to change in the `ngrams` function. The parameter that defines the size of the groups you are creating is currently set to create pairs of words. Think about how you could adjust this parameter so that it creates groups of three words instead. \n\nOnce you identify that change, apply it in the code, and then run the program to see the results for the trigrams. What do you think you should set the parameter to?",
                        "verificationPassed": true,
                        "verificationOutput": "PASS"
                      }
                    ]
                  },
                  "safety_signals": {
                    "requires_attention": false
                  },
                  "usage": {
                    "chatTokens": {
                      "prompt": 1462,
                      "completion": 290,
                      "total": 1752
                    },
                    "verificationTokens": {
                      "prompt": 1638,
                      "completion": 27,
                      "total": 1665
                    },
                    "totalTokens": 3417
                  },
                  "metadata": {
                    "processingTimeMs": 6157,
                    "timestamp": "2025-04-22T07:19:01.714Z",
                    "sessionId": "session_abc123",
                    "userId": "user_xyz789",
                    "chatModelUsed": "viable-3",
                    "verificationModelUsed": "gpt-4o-mini"
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request. Invalid input, missing required fields, or malformed JSON. The response body contains details about the validation errors.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/VETTINGErrorResponse"
                },
                "example": {
                  "status": "error",
                  "error": {
                    "code": "INVALID_INPUT",
                    "message": "Request validation failed. See details.",
                    "details": [
                      "Missing required field for 'vetting' mode: 'context.answerKey'."
                    ]
                  },
                  "metadata": {
                    "timestamp": "2024-07-30T10:10:00Z",
                    "requestId": "api-req-id-123"
                  }
                }
              }
            }
          },
          "403": {
            "$ref": "#/components/responses/Forbidden"
          },
          "405": {
            "$ref": "#/components/responses/MethodNotAllowed"
          },
          "429": {
            "$ref": "#/components/responses/RateLimited"
          },
          "500": {
            "description": "Internal Server Error. An unexpected error occurred during processing.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/VETTINGErrorResponse"
                },
                "example": {
                  "status": "error",
                  "error": {
                    "code": "INTERNAL_ERROR",
                    "message": "An unexpected error occurred: Failed to parse model response."
                  },
                  "metadata": {
                    "timestamp": "2024-07-30T10:12:00Z",
                    "requestId": "api-req-id-456"
                  }
                }
              }
            }
          },
          "502": {
            "description": "Upstream model service error. Error occurred when communicating with a model provider.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/VETTINGErrorResponse"
                },
                "example": {
                  "status": "error",
                  "error": {
                    "code": "MODEL_ERROR",
                    "message": "Chat model failed on first attempt: model API error (500): Internal server error"
                  },
                  "metadata": {
                    "timestamp": "2024-07-30T10:11:00Z",
                    "requestId": "api-req-id-789"
                  }
                }
              }
            }
          }
        }
      }
    },
    "/v1/audio/transcriptions": {
      "post": {
        "tags": [
          "Audio"
        ],
        "summary": "Transcribe Audio",
        "description": "Transcribes uploaded audio using an OpenAI-compatible multipart/form-data request. If `model` is omitted, the default is `whisper-large-v3`. OpenAI transcription models such as `gpt-4o-transcribe`, `gpt-4o-mini-transcribe`, and `whisper-1` are supported, along with registered VIABLE Lab transcription models. Provide `duration_seconds` or `duration_minutes` when available so logs can compute per-minute cost accurately.",
        "operationId": "createAudioTranscription",
        "requestBody": {
          "required": true,
          "content": {
            "multipart/form-data": {
              "schema": {
                "$ref": "#/components/schemas/AudioTranscriptionRequest"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Audio transcription response.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/AudioTranscriptionResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Server error.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/v1/docs/metadata": {
      "get": {
        "tags": [
          "Developer Metadata"
        ],
        "summary": "Get Developer Metadata",
        "description": "Returns a compact machine-readable catalog of endpoint modes, default models, public model metadata, quickstarts, capabilities, and pricing notes. Developer frontends can use this endpoint instead of hardcoding model lists.",
        "operationId": "getDocsMetadata",
        "responses": {
          "200": {
            "description": "Developer metadata payload.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/DocsMetadataResponse"
                }
              }
            }
          }
        }
      }
    },
    "/v1/embeddings": {
      "post": {
        "tags": [
          "Embeddings"
        ],
        "summary": "Create Embeddings",
        "description": "Creates vector embeddings from text using an OpenAI-compatible request shape. If `model` is omitted, the default is `nomic-embed-text-v1.5`. Cost is token-based when provider usage is returned.",
        "operationId": "createEmbeddings",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/EmbeddingRequest"
              },
              "example": {
                "model": "nomic-embed-text-v1.5",
                "input": [
                  "alpha",
                  "beta"
                ],
                "encoding_format": "float"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Embedding response.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/EmbeddingResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Server error.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/v1/images/generations": {
      "post": {
        "tags": [
          "Images"
        ],
        "summary": "Generate Images",
        "description": "Generates images from a text prompt using an OpenAI Images-compatible request shape. If `model` is omitted, the default is `flux.2-klein`. Current public pricing is a starting per-image price and can vary by resolution. When `response_format` is `url`, the API returns public HTTPS asset URLs under `https://api.viablelab.org/v1/assets/...` instead of exposing provider-local URLs. When `response_format` is `b64_json`, inline base64 is returned to the caller; logs redact the base64 payload and include an asset URL preview when asset storage is available.",
        "operationId": "generateImages",
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "$ref": "#/components/schemas/ImageGenerationRequest"
              },
              "example": {
                "model": "flux.2-klein",
                "prompt": "A clean classroom dashboard UI",
                "n": 1,
                "size": "1024x1024",
                "response_format": "url"
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Image generation response.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ImageGenerationResponse"
                }
              }
            }
          },
          "400": {
            "description": "Invalid request.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "500": {
            "description": "Server error.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/v1/assets/{key}": {
      "get": {
        "tags": [
          "Assets"
        ],
        "summary": "Fetch Generated Asset",
        "description": "Fetches an API-generated asset stored in private R2. Generated image URL responses use this route. Upload and delete operations are not exposed; keys are generated by the API and are intentionally unguessable.",
        "operationId": "getGeneratedAsset",
        "parameters": [
          {
            "name": "key",
            "in": "path",
            "required": true,
            "description": "Generated asset key returned by an API response, for example `images/2026/06/10/<request-id>/0-<uuid>.png`.",
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Binary asset stream.",
            "content": {
              "image/png": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "image/jpeg": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              },
              "image/webp": {
                "schema": {
                  "type": "string",
                  "format": "binary"
                }
              }
            }
          },
          "404": {
            "description": "Asset not found.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          },
          "503": {
            "description": "Asset storage is not configured.",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/ErrorResponse"
                }
              }
            }
          }
        }
      }
    },
    "/v1/agents/{slug}/runs": {
      "post": {
        "tags": [
          "Agents"
        ],
        "operationId": "runAgent",
        "summary": "Run an agent turn",
        "description": "Runs one conversational turn of a published visual/code agent workflow. Requires an API key with the `agents:execute` scope and access to the agent. Preserve the returned `conversation_id` and pass it on later turns to continue the same agent chat thread. This `conversation_id` is for published agent runs; for direct chat or VETTING, include the context required by the request and treat any app- or provider-level session state as separate.",
        "security": [
          {
            "ApiKeyAuth": []
          },
          {
            "BearerAuth": []
          }
        ],
        "parameters": [
          {
            "name": "slug",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Published agent slug."
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "anyOf": [
                  {
                    "required": [
                      "input"
                    ]
                  },
                  {
                    "required": [
                      "message"
                    ]
                  },
                  {
                    "required": [
                      "messages"
                    ]
                  }
                ],
                "properties": {
                  "input": {
                    "$ref": "#/components/schemas/AgentTurnInput"
                  },
                  "conversation_id": {
                    "type": "string",
                    "description": "Continue an existing agent conversation. Omit on the first turn, store the returned value, and resend it for later turns from the same end-user session."
                  },
                  "message": {
                    "type": "string",
                    "description": "Backward-compatible text-only alias for input. Omit input when using this field."
                  },
                  "messages": {
                    "type": "array",
                    "minItems": 1,
                    "description": "Compatibility form. The last role=user message supplies this turn; use conversation_id for persisted Agent history.",
                    "items": {
                      "$ref": "#/components/schemas/ChatMessage"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Agent run result. Store `conversation_id` for future turns and use `run_id` to inspect one orchestration execution.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "object": {
                      "type": "string",
                      "example": "agent.run.result"
                    },
                    "agent": {
                      "type": "string"
                    },
                    "conversation_id": {
                      "type": "string"
                    },
                    "run_id": {
                      "type": "string"
                    },
                    "output": {
                      "type": "object",
                      "properties": {
                        "text": {
                          "type": "string"
                        },
                        "attachments": {
                          "type": "array",
                          "items": {
                            "type": "object",
                            "properties": {
                              "type": {
                                "type": "string"
                              },
                              "url": {
                                "type": "string"
                              }
                            }
                          }
                        }
                      }
                    },
                    "usage": {
                      "type": "object",
                      "properties": {
                        "prompt": {
                          "type": "integer"
                        },
                        "completion": {
                          "type": "integer"
                        },
                        "total": {
                          "type": "integer"
                        }
                      }
                    },
                    "cost": {
                      "type": "number"
                    },
                    "input_assets": {
                      "type": "array",
                      "description": "Authenticated research references created for exact input media in this turn.",
                      "items": {
                        "$ref": "#/components/schemas/ResearchAsset"
                      }
                    }
                  }
                }
              }
            }
          },
          "403": {
            "description": "The API key may not run this agent or lacks the agents:execute scope."
          },
          "404": {
            "description": "Agent not found or not published."
          }
        }
      },
      "get": {
        "tags": [
          "Agents"
        ],
        "operationId": "getAgentMetadata",
        "summary": "Method not allowed",
        "description": "Only POST is supported on this path.",
        "responses": {
          "405": {
            "description": "Use POST."
          }
        }
      }
    },
    "/v1/agents/{slug}": {
      "get": {
        "tags": [
          "Agents"
        ],
        "operationId": "getPublishedAgent",
        "summary": "Get published agent metadata",
        "parameters": [
          {
            "name": "slug",
            "in": "path",
            "required": true,
            "schema": {
              "type": "string"
            },
            "description": "Published agent slug."
          }
        ],
        "responses": {
          "200": {
            "description": "Public agent metadata.",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "object": {
                      "type": "string"
                    },
                    "slug": {
                      "type": "string"
                    },
                    "name": {
                      "type": "string"
                    },
                    "description": {
                      "type": "string",
                      "nullable": true
                    },
                    "published_version": {
                      "type": "integer"
                    }
                  }
                }
              }
            }
          },
          "404": {
            "description": "Agent not found or not published."
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "StatusResponse": {
        "type": "object",
        "properties": {
          "status": {
            "type": "string",
            "example": "ok"
          },
          "message": {
            "type": "string",
            "example": "VIABLE Lab API is running"
          },
          "documentation": {
            "type": "string",
            "format": "url",
            "example": "https://developers.viablelab.org/"
          }
        }
      },
      "Model": {
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "description": "The model identifier or alias used in API requests.",
            "example": "viable-2"
          },
          "object": {
            "type": "string",
            "example": "model"
          },
          "mode": {
            "type": "string",
            "enum": [
              "chat",
              "embedding",
              "image_generation",
              "audio_transcription",
              "audio_speech"
            ],
            "description": "Endpoint mode this model supports."
          },
          "endpoint": {
            "type": "string",
            "description": "Primary API endpoint for the model.",
            "example": "/v1/chat/completions"
          },
          "description": {
            "type": "string"
          },
          "owned_by": {
            "type": "string",
            "description": "Public owner label for display and filtering."
          },
          "intelligence": {
            "type": "string"
          },
          "speed": {
            "type": "string"
          },
          "input_modalities": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "example": [
              "text",
              "image"
            ]
          },
          "output_modalities": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "example": [
              "text"
            ]
          },
          "context_window": {
            "type": "integer",
            "nullable": true
          },
          "max_output_tokens": {
            "type": "integer",
            "nullable": true
          },
          "open_weights": {
            "type": "boolean",
            "description": "Whether the public model is backed by an open-weight model."
          },
          "reasoning_model": {
            "type": "boolean",
            "description": "Whether the model is intended for reasoning or thinking workflows."
          },
          "parameter_support": {
            "type": "object",
            "description": "Safe public parameter support hints for Playground and generated examples. Omitted or false fields should not be sent for the model.",
            "properties": {
              "temperature": {
                "type": "boolean",
                "description": "Whether the model accepts a custom temperature value."
              },
              "top_p": {
                "type": "boolean",
                "description": "Whether the model accepts a custom top_p value."
              },
              "max_tokens": {
                "type": "boolean",
                "description": "Whether the VIABLE API accepts max_tokens for this model."
              },
              "max_completion_tokens": {
                "type": "boolean",
                "description": "Whether the upstream-compatible OpenAI max_completion_tokens parameter is supported."
              },
              "reasoning_effort": {
                "type": "boolean",
                "description": "Whether the model accepts a VIABLE Lab reasoning_effort control on this endpoint."
              },
              "reasoning_effort_values": {
                "type": "array",
                "items": {
                  "type": "string"
                },
                "description": "Accepted reasoning_effort values when reasoning_effort is true."
              }
            },
            "additionalProperties": false
          },
          "supports_streaming": {
            "type": "boolean"
          },
          "capabilities": {
            "type": "object",
            "additionalProperties": {
              "type": "boolean"
            },
            "description": "Capability flags for text, images, files, PDFs, audio, tools, embeddings, and image generation."
          },
          "pricing": {
            "$ref": "#/components/schemas/PricingInfo"
          },
          "default_voice": {
            "type": "string",
            "description": "Default voice for compatible speech models."
          }
        }
      },
      "ModelListResponse": {
        "type": "object",
        "properties": {
          "object": {
            "type": "string",
            "example": "list"
          },
          "default_model": {
            "type": "string",
            "example": "gpt-4.1-nano"
          },
          "aliases": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            },
            "description": "Legacy compatibility alias map. VIABLE aliases are listed in supported_aliases and available_models without exposing internal routing targets."
          },
          "available_models": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Model"
            }
          },
          "upcoming_models": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "supported_aliases": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "description": "Supported public aliases and compatibility aliases accepted in the model field. VIABLE aliases are stable public model IDs; internal routing targets are not exposed."
          }
        }
      },
      "ChatCompletionRequest": {
        "type": "object",
        "required": [
          "messages"
        ],
        "properties": {
          "messages": {
            "type": "array",
            "minItems": 1,
            "items": {
              "$ref": "#/components/schemas/ChatMessage"
            },
            "description": "A list of messages comprising the conversation history, ending with the latest user message."
          },
          "model": {
            "type": "string",
            "description": "Full model ID or VIABLE alias to use. Defaults to gpt-4.1-nano. Examples: gpt-4.1-nano, gpt-4o, gemini-2.5-flash, gpt-oss-120b, llama-3.1-70b-instruct, viable-2. Legacy short aliases remain accepted for existing integrations; new integrations should use full model IDs or VIABLE aliases.",
            "example": "gpt-4.1-nano"
          },
          "max_tokens": {
            "type": "integer",
            "description": "Maximum number of tokens to generate. Overrides router's default if lower."
          },
          "temperature": {
            "type": "number",
            "format": "float",
            "default": 1,
            "minimum": 0,
            "maximum": 2
          },
          "top_p": {
            "type": "number",
            "format": "float",
            "default": 1,
            "minimum": 0,
            "maximum": 1
          },
          "n": {
            "type": "integer",
            "default": 1,
            "description": "How many chat completion choices to generate. (Passed through)"
          },
          "stop": {
            "description": "Up to 4 sequences where the API will stop generating. (Passed through)",
            "nullable": true,
            "oneOf": [
              {
                "type": "string"
              },
              {
                "type": "array",
                "items": {
                  "type": "string"
                },
                "maxItems": 4
              }
            ]
          },
          "presence_penalty": {
            "type": "number",
            "format": "float",
            "default": 0
          },
          "frequency_penalty": {
            "type": "number",
            "format": "float",
            "default": 0
          },
          "response_format": {
            "type": "object",
            "description": "An object specifying the format that the model must output. Use { \"type\": \"json_object\" } to enable JSON mode, which ensures the message the model generates is valid JSON. Note: The model needs instructions in the prompt to produce JSON.",
            "oneOf": [
              {
                "type": "object",
                "properties": {
                  "type": {
                    "type": "string",
                    "enum": [
                      "text"
                    ],
                    "description": "The default format. Model generates text responses."
                  }
                },
                "required": [
                  "type"
                ]
              },
              {
                "type": "object",
                "properties": {
                  "type": {
                    "type": "string",
                    "enum": [
                      "json_object"
                    ],
                    "description": "Ensures the model output is a valid JSON object."
                  }
                },
                "required": [
                  "type"
                ]
              },
              {
                "type": "object",
                "properties": {
                  "type": {
                    "type": "string",
                    "enum": [
                      "json_schema"
                    ],
                    "description": "Ensures the model output adheres to a provided JSON schema."
                  },
                  "json_schema": {
                    "type": "object",
                    "description": "Configuration including the JSON Schema the model must follow.",
                    "required": [
                      "name"
                    ],
                    "properties": {
                      "name": {
                        "type": "string",
                        "description": "The name for the schema.",
                        "maxLength": 64
                      },
                      "description": {
                        "type": "string",
                        "description": "Description of the schema for the model."
                      },
                      "schema": {
                        "type": "object",
                        "description": "The JSON Schema object itself.",
                        "additionalProperties": true
                      },
                      "strict": {
                        "type": "boolean",
                        "description": "Whether to enforce strict adherence to the schema.",
                        "default": false
                      }
                    }
                  }
                },
                "required": [
                  "type",
                  "json_schema"
                ]
              }
            ],
            "example": {
              "type": "json_object"
            }
          },
          "stream": {
            "type": "boolean",
            "description": "If true, returns OpenAI-style server-sent events from /v1/chat/completions. Streaming is supported on the main chat endpoint; vetting endpoints remain non-streaming.",
            "default": false
          },
          "provider": {
            "type": "string",
            "enum": [
              "openai",
              "gemini"
            ],
            "description": "Optional provider hint for public providers. Most clients should omit this and rely on model-first routing."
          }
        },
        "description": "Standard OpenAI-compatible Chat Completion request. Supports text and multimodal content parts. The main chat endpoint supports streaming."
      },
      "AgentTurnInput": {
        "description": "Latest user turn for an Agent. Text is retained exactly. Inline image/file data is bounded, archived byte-for-byte in private R2, and represented in research logs by an authenticated asset reference. HTTPS URLs are retained exactly as restricted provenance and are not fetched by VIABLE Lab.",
        "anyOf": [
          {
            "type": "string",
            "minLength": 1,
            "maxLength": 1048576
          },
          {
            "$ref": "#/components/schemas/AgentUserMessage"
          },
          {
            "type": "array",
            "minItems": 1,
            "maxItems": 32,
            "description": "A content-part array using text/input_text, image_url/input_image, or file/input_file aliases. input_image accepts image_url as a string or {url,detail} and an optional filename; input_file accepts inline file_data or an HTTPS file_url/url. Provider file_id values are not portable and are rejected.",
            "items": {
              "type": "object",
              "additionalProperties": true
            }
          },
          {
            "type": "array",
            "minItems": 1,
            "description": "Message array compatibility form. The last role=user message supplies the latest turn; conversation_id remains the supported way to continue stored Agent history.",
            "items": {
              "$ref": "#/components/schemas/ChatMessage"
            }
          }
        ]
      },
      "AgentUserMessage": {
        "type": "object",
        "required": [
          "role",
          "content"
        ],
        "properties": {
          "role": {
            "type": "string",
            "enum": [
              "user"
            ]
          },
          "content": {
            "oneOf": [
              {
                "type": "string",
                "minLength": 1,
                "maxLength": 1048576
              },
              {
                "type": "array",
                "minItems": 1,
                "maxItems": 32,
                "items": {
                  "type": "object",
                  "additionalProperties": true
                }
              }
            ]
          }
        },
        "additionalProperties": false
      },
      "ResearchAsset": {
        "type": "object",
        "description": "Authenticated research reference for exact user-provided media. Binary bytes remain private. The developer portal handles sign-in, authorization, preview, and downloads for researcher-facing links.",
        "properties": {
          "id": {
            "type": "string",
            "example": "rasset_0123456789abcdef0123456789abcdef01234567"
          },
          "request_id": {
            "type": "string"
          },
          "agent_id": {
            "type": "string",
            "nullable": true
          },
          "agent_run_id": {
            "type": "string",
            "nullable": true
          },
          "conversation_id": {
            "type": "string",
            "nullable": true
          },
          "direction": {
            "type": "string",
            "enum": [
              "request",
              "response"
            ]
          },
          "content_index": {
            "type": "integer",
            "nullable": true
          },
          "modality": {
            "type": "string",
            "enum": [
              "image",
              "file",
              "pdf",
              "audio"
            ]
          },
          "content_type": {
            "type": "string",
            "nullable": true
          },
          "filename": {
            "type": "string",
            "nullable": true
          },
          "byte_size": {
            "type": "integer",
            "nullable": true
          },
          "sha256": {
            "type": "string",
            "nullable": true,
            "description": "SHA-256 of the archived file bytes. Null for an external URL because VIABLE Lab does not fetch the source content."
          },
          "source_url_sha256": {
            "type": "string",
            "nullable": true,
            "description": "SHA-256 of the exact external source URL string for provenance deduplication; this is not a file-content checksum."
          },
          "source": {
            "type": "string",
            "enum": [
              "private_r2",
              "external_url"
            ]
          },
          "download_url": {
            "type": "string",
            "format": "uri",
            "description": "Sign-in-aware browser link. For a private archived object, the portal restores sign-in and starts an authorized download. For an external provenance reference that VIABLE Lab did not archive, this equals view_url and remains view-only."
          },
          "view_url": {
            "type": "string",
            "format": "uri",
            "description": "Sign-in-aware developer portal page for viewing or downloading this asset. Included as an absolute URL in research exports."
          },
          "source_url": {
            "type": "string",
            "format": "uri",
            "nullable": true,
            "description": "Exact restricted provenance URL for external references, including query parameters. Present only on authorized research surfaces and may expire according to the source service."
          },
          "created_at": {
            "type": "string",
            "format": "date-time",
            "nullable": true
          }
        }
      },
      "ChatMessage": {
        "type": "object",
        "required": [
          "role",
          "content"
        ],
        "properties": {
          "role": {
            "type": "string",
            "enum": [
              "user",
              "assistant",
              "system"
            ],
            "description": "The role of the message author."
          },
          "content": {
            "oneOf": [
              {
                "type": "string",
                "description": "The text content of the message."
              },
              {
                "type": "array",
                "description": "An array combining text, image, file, and PDF inputs for multimodal models.",
                "items": {
                  "type": "object",
                  "oneOf": [
                    {
                      "required": [
                        "type",
                        "text"
                      ],
                      "properties": {
                        "type": {
                          "type": "string",
                          "enum": [
                            "text"
                          ],
                          "description": "Type identifier for text content.",
                          "example": "text"
                        },
                        "text": {
                          "type": "string",
                          "description": "The text content.",
                          "example": "What is in this image?"
                        }
                      }
                    },
                    {
                      "required": [
                        "type",
                        "image_url"
                      ],
                      "properties": {
                        "type": {
                          "type": "string",
                          "enum": [
                            "image_url"
                          ],
                          "description": "Type identifier for image URL content.",
                          "example": "image_url"
                        },
                        "image_url": {
                          "type": "object",
                          "required": [
                            "url"
                          ],
                          "properties": {
                            "url": {
                              "type": "string",
                              "format": "uri",
                              "description": "The URL of the image.",
                              "example": "https://upload.wikimedia.org/..."
                            }
                          }
                        }
                      }
                    },
                    {
                      "required": [
                        "type",
                        "file"
                      ],
                      "properties": {
                        "type": {
                          "type": "string",
                          "enum": [
                            "file",
                            "input_file"
                          ],
                          "description": "Type identifier for file content."
                        },
                        "file": {
                          "type": "object",
                          "required": [
                            "file_data"
                          ],
                          "properties": {
                            "filename": {
                              "type": "string"
                            },
                            "mime_type": {
                              "type": "string",
                              "example": "application/pdf"
                            },
                            "file_data": {
                              "type": "string",
                              "description": "Base64 file data, preferably as a data URI."
                            }
                          }
                        }
                      }
                    }
                  ]
                }
              }
            ]
          }
        }
      },
      "CompletionUsage": {
        "type": "object",
        "properties": {
          "prompt_tokens": {
            "type": "integer"
          },
          "completion_tokens": {
            "type": "integer"
          },
          "total_tokens": {
            "type": "integer"
          }
        },
        "description": "Token usage statistics for the completion request (non-streaming)."
      },
      "ErrorResponse": {
        "type": "object",
        "properties": {
          "error": {
            "type": "object",
            "properties": {
              "message": {
                "type": "string"
              },
              "type": {
                "type": "string"
              },
              "param": {
                "type": "string",
                "nullable": true
              },
              "code": {
                "type": "string",
                "nullable": true
              }
            }
          }
        }
      },
      "ChatVettingRequest": {
        "allOf": [
          {
            "$ref": "#/components/schemas/ChatCompletionRequest"
          }
        ],
        "type": "object",
        "properties": {
          "vettingConfig": {
            "$ref": "#/components/schemas/ChatVettingConfig",
            "description": "(Optional) Configuration for the VETTING pass."
          },
          "messages": {
            "description": "Conversation history. System message can be included here."
          },
          "model": {
            "description": "Full chat model ID or VIABLE alias. Defaults apply if omitted. See /v1/models for supported chat models.",
            "example": "viable-3"
          }
        }
      },
      "ChatVettingConfig": {
        "type": "object",
        "properties": {
          "systemPrompt": {
            "type": "string",
            "description": "(Optional) A specific guideline for the internal verification model to check against. If omitted, a default safety/guidance prompt is used.",
            "example": "Do not provide code directly, only explain the concepts."
          },
          "maxAttempts": {
            "type": "integer",
            "minimum": 1,
            "maximum": 10,
            "default": 3,
            "description": "(Optional) Maximum number of internal generation/verification attempts."
          }
        }
      },
      "ChatVettingResponse": {
        "description": "Response format for Chat Vetting, including standard OpenAI fields and vetting metadata.",
        "allOf": [
          {
            "$ref": "#/components/schemas/ChatCompletionResponse"
          }
        ],
        "type": "object",
        "properties": {
          "vetting_info": {
            "$ref": "#/components/schemas/ChatVettingInfo",
            "description": "Information about the internal vetting process."
          },
          "id": {
            "type": "string"
          },
          "object": {
            "type": "string"
          },
          "created": {
            "type": "integer"
          },
          "model": {
            "type": "string"
          },
          "choices": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ChatCompletionChoice"
            }
          },
          "usage": {
            "$ref": "#/components/schemas/CompletionUsage"
          },
          "safety_signals": {
            "description": "Signals related to the safety and content appropriateness of the response.",
            "type": "object",
            "properties": {
              "requires_attention": {
                "type": "boolean",
                "description": "Indicates if the model flagged its own response as potentially addressing sensitive, harmful, or inappropriate topics, requiring human review or specific handling."
              }
            },
            "required": [
              "requires_attention"
            ]
          }
        }
      },
      "ChatVettingInfo": {
        "description": "Metadata about the VETTING pass for /v1/chat/vetting.",
        "type": "object",
        "required": [
          "attemptCount",
          "stopReason"
        ],
        "properties": {
          "attemptCount": {
            "type": "integer",
            "description": "Total number of internal generation/verification attempts made."
          },
          "stopReason": {
            "type": "string",
            "enum": [
              "VERIFICATION_PASSED",
              "MAX_ATTEMPTS_REACHED",
              "GENERATION_ERROR",
              "VERIFICATION_ERROR",
              "SAFETY_TRIGGERED"
            ],
            "description": "The reason the internal vetting process stopped. `SAFETY_TRIGGERED` indicates the chat model detected potentially harmful content based on the query/topic and halted the process before verification."
          },
          "lastFailureReason": {
            "type": "string",
            "nullable": true,
            "description": "If verification failed at least once before ultimately passing or hitting max attempts, this field contains the failure reason provided by the verification model for the *most recent* failure. Null if the first attempt passed, or if the process stopped early due to SAFETY_TRIGGERED or an error on the first attempt."
          }
        }
      },
      "ChatCompletionChoice": {
        "type": "object",
        "properties": {
          "index": {
            "type": "integer",
            "example": 0
          },
          "message": {
            "$ref": "#/components/schemas/ChatMessage"
          },
          "finish_reason": {
            "type": "string",
            "example": "stop",
            "enum": [
              "stop",
              "length",
              "error"
            ]
          },
          "logprobs": {
            "nullable": true,
            "description": "Log probability information, null if not requested/supported."
          }
        }
      },
      "ChatCompletionResponse": {
        "description": "Standard Chat Completion response format (OpenAI compatible).",
        "type": "object",
        "properties": {
          "id": {
            "type": "string",
            "example": "chatcmpl-xxxxxxxxxxxxxxxxxxxxxxx"
          },
          "object": {
            "type": "string",
            "example": "chat.completion"
          },
          "created": {
            "type": "integer",
            "format": "int64",
            "example": 1677652288
          },
          "model": {
            "type": "string",
            "description": "The model requested by the client.",
            "example": "viable-3"
          },
          "choices": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/ChatCompletionChoice"
            }
          },
          "usage": {
            "$ref": "#/components/schemas/CompletionUsage"
          },
          "system_fingerprint": {
            "type": "string",
            "nullable": true,
            "description": "System fingerprint, null if not provided."
          }
        }
      },
      "VETTINGRequest": {
        "type": "object",
        "required": [
          "mode",
          "config",
          "prompts",
          "messages"
        ],
        "properties": {
          "mode": {
            "type": "string",
            "enum": [
              "vetting",
              "chat"
            ],
            "description": "(Required) Operation mode: 'vetting' enables the verification layer, 'chat' provides standard chat."
          },
          "config": {
            "$ref": "#/components/schemas/VETTINGConfig",
            "description": "(Required) Configuration for models and verification attempts."
          },
          "prompts": {
            "$ref": "#/components/schemas/VETTINGPrompts",
            "description": "(Required) Base system prompts object. Fields within this object are optional and have defaults (see VETTINGPrompts schema)."
          },
          "context": {
            "$ref": "#/components/schemas/VETTINGContext",
            "description": "(Optional) Contextual information. The 'items' array within is required if mode is 'vetting'."
          },
          "messages": {
            "type": "array",
            "minItems": 1,
            "items": {
              "$ref": "#/components/schemas/ChatMessage"
            },
            "description": "(Required) Conversation history, ending with the last user message. Client should provide messages with roles 'user' and optionally previous 'assistant' messages. Do not include 'system' role messages here; use the `prompts` field instead."
          }
        }
      },
      "VETTINGConfig": {
        "type": "object",
        "required": [
          "chatModel"
        ],
        "properties": {
          "maxVerificationAttempts": {
            "type": "integer",
            "minimum": 1,
            "default": 3,
            "description": "(Optional) Maximum verification attempts in 'vetting' mode. Defaults to 3 if omitted."
          },
          "chatModel": {
            "$ref": "#/components/schemas/ModelConfig",
            "description": "(Required) Configuration for the chat model."
          },
          "verificationModel": {
            "$ref": "#/components/schemas/ModelConfig",
            "description": "(Required if mode='vetting') Configuration for the verification model."
          }
        }
      },
      "ModelConfig": {
        "type": "object",
        "required": [
          "modelId"
        ],
        "properties": {
          "modelId": {
            "type": "string",
            "description": "(Required) Full chat model ID or VIABLE alias. Examples: viable-2, gpt-4.1-nano, gpt-4o-mini, gemini-2.5-flash, gpt-oss-120b, llama-3.1-70b-instruct. See /v1/models for the current catalog. Non-chat models are rejected on VETTING endpoints.",
            "example": "viable-3"
          },
          "temperature": {
            "type": "number",
            "format": "float",
            "minimum": 0,
            "maximum": 2,
            "description": "(Optional) Sampling temperature. If omitted, server defaults apply (e.g., Chat: 0.7, Verify: 0.1)."
          },
          "maxTokens": {
            "type": "integer",
            "minimum": 1,
            "description": "(Optional) Maximum tokens to generate. If omitted, server defaults apply (e.g., Chat: 1024, Verify: 512)."
          },
          "topP": {
            "type": "number",
            "format": "float",
            "minimum": 0,
            "maximum": 1,
            "description": "(Optional) Nucleus sampling parameter."
          }
        }
      },
      "VETTINGPrompts": {
        "type": "object",
        "description": "Container for system prompts. The object itself is required in the request, but the fields within are optional.",
        "properties": {
          "chatSystemPrompt": {
            "type": "string",
            "description": "(Optional) Base system prompt for the chat model. If omitted, a default helpful tutor prompt is used."
          },
          "verificationSystemPrompt": {
            "type": "string",
            "description": "(Optional) Base system prompt for the verification model. If omitted and mode='vetting', a default evaluator prompt is constructed using the chat prompt and context."
          }
        }
      },
      "VETTINGContext": {
        "type": "object",
        "description": "Contextual information. The 'items' array is required if mode='vetting'.",
        "properties": {
          "sessionId": {
            "type": "string",
            "nullable": true,
            "description": "(Optional) Session identifier."
          },
          "userId": {
            "type": "string",
            "nullable": true,
            "description": "(Optional) User identifier."
          },
          "items": {
            "type": "array",
            "minItems": 1,
            "items": {
              "$ref": "#/components/schemas/VettingContextItem"
            },
            "description": "(Required if mode='vetting') Array of questions and their corresponding answer keys."
          }
        },
        "required": [
          "items"
        ]
      },
      "VettingContextItem": {
        "type": "object",
        "required": [
          "question",
          "answerKey"
        ],
        "description": "A single question and its associated answer key for the VETTING context.",
        "properties": {
          "question": {
            "$ref": "#/components/schemas/QuestionInfo",
            "description": "(Required) Details about the question being discussed."
          },
          "answerKey": {
            "$ref": "#/components/schemas/AnswerKey",
            "description": "(Required) Reference answer details for verification."
          }
        }
      },
      "QuestionInfo": {
        "type": "object",
        "required": [
          "text"
        ],
        "properties": {
          "id": {
            "type": "string",
            "nullable": true,
            "description": "(Optional) Unique identifier for the question."
          },
          "text": {
            "type": "string",
            "description": "(Required) The text of the question being discussed."
          },
          "subject": {
            "type": "string",
            "nullable": true,
            "description": "(Optional) Subject area."
          },
          "metadata": {
            "type": "object",
            "additionalProperties": true,
            "nullable": true,
            "description": "(Optional) Additional metadata."
          }
        }
      },
      "AnswerKey": {
        "type": "object",
        "required": [
          "correctAnswer"
        ],
        "properties": {
          "correctAnswer": {
            "type": "string",
            "description": "(Required) The correct answer, used by the verification layer."
          },
          "keyConcepts": {
            "type": "array",
            "items": {
              "type": "string"
            },
            "nullable": true,
            "description": "(Optional) List of key concepts/terms that should not be directly revealed."
          },
          "explanation": {
            "type": "string",
            "nullable": true,
            "description": "(Optional) Detailed explanation for the verification layer."
          }
        }
      },
      "VettingResult": {
        "type": "object",
        "required": [
          "role",
          "content"
        ],
        "properties": {
          "role": {
            "type": "string",
            "enum": [
              "assistant"
            ]
          },
          "content": {
            "type": "string"
          }
        }
      },
      "VETTINGResponse": {
        "type": "object",
        "required": [
          "status",
          "mode",
          "result",
          "usage",
          "metadata",
          "safety_signals"
        ],
        "properties": {
          "status": {
            "type": "string",
            "enum": [
              "success"
            ],
            "description": "Indicates successful processing."
          },
          "mode": {
            "type": "string",
            "enum": [
              "vetting",
              "chat"
            ],
            "description": "The mode used for this response."
          },
          "result": {
            "$ref": "#/components/schemas/VettingResult",
            "description": "The final assistant message content."
          },
          "safety_signals": {
            "description": "Signals related to the safety and content appropriateness of the primary chat response.",
            "type": "object",
            "properties": {
              "requires_attention": {
                "type": "boolean",
                "description": "Indicates if the chat model perceived the user query or topic as potentially harmful/sensitive and triggered the safety protocol (`stopReason: SAFETY_TRIGGERED`)."
              }
            },
            "required": [
              "requires_attention"
            ]
          },
          "verification": {
            "description": "Details about the verification attempts, only present in 'vetting' mode.",
            "oneOf": [
              {
                "$ref": "#/components/schemas/VerificationDetails"
              },
              {
                "type": "null"
              }
            ]
          },
          "usage": {
            "$ref": "#/components/schemas/UsageInfo",
            "description": "Aggregated token usage for the request."
          },
          "metadata": {
            "$ref": "#/components/schemas/VETTINGMetadata"
          }
        }
      },
      "VerificationDetails": {
        "type": "object",
        "nullable": true,
        "required": [
          "passed",
          "attemptCount",
          "stopReason",
          "attempts"
        ],
        "properties": {
          "passed": {
            "type": "boolean",
            "description": "Indicates if the final response passed verification (true if mode='chat')."
          },
          "attemptCount": {
            "type": "integer",
            "description": "Total number of chat generation attempts made."
          },
          "stopReason": {
            "type": "string",
            "enum": [
              "VERIFICATION_PASSED",
              "MAX_ATTEMPTS_REACHED",
              "GENERATION_ERROR",
              "VERIFICATION_ERROR",
              "SAFETY_TRIGGERED"
            ],
            "description": "Reason the vetting process stopped. `SAFETY_TRIGGERED` indicates the chat model detected potentially harmful content and halted the process before this verification attempt."
          },
          "attempts": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/AttemptDetail"
            },
            "description": "Details of each verification attempt."
          }
        }
      },
      "AttemptDetail": {
        "type": "object",
        "required": [
          "attemptNumber",
          "chatResponse",
          "verificationPassed",
          "verificationOutput"
        ],
        "properties": {
          "attemptNumber": {
            "type": "integer",
            "description": "The sequence number of this attempt."
          },
          "chatResponse": {
            "type": "string",
            "description": "The response generated by the chat model for this attempt."
          },
          "verificationPassed": {
            "type": "boolean",
            "description": "Whether this specific attempt passed verification."
          },
          "requiresAttention": {
            "type": "boolean",
            "description": "Indicates if the chat model flagged its *own response* in this attempt as potentially sensitive/harmful (based on user query/topic). True if the `stopReason` for the overall request is `SAFETY_TRIGGERED`."
          },
          "verificationOutput": {
            "type": "string",
            "description": "The raw output from the verification model ('PASS' or failure reason, or 'N/A (Safety Triggered)' if skipped)."
          }
        }
      },
      "UsageInfo": {
        "type": "object",
        "required": [
          "chatTokens",
          "totalTokens"
        ],
        "properties": {
          "chatTokens": {
            "$ref": "#/components/schemas/TokenUsageDetail",
            "description": "Token usage for the chat model calls."
          },
          "verificationTokens": {
            "$ref": "#/components/schemas/TokenUsageDetail",
            "nullable": true,
            "description": "Token usage for the verification model calls (null if mode='chat')."
          },
          "totalTokens": {
            "type": "integer",
            "description": "Total estimated tokens used for the entire request."
          }
        }
      },
      "TokenUsageDetail": {
        "type": "object",
        "required": [
          "prompt",
          "completion",
          "total"
        ],
        "properties": {
          "prompt": {
            "type": "integer"
          },
          "completion": {
            "type": "integer"
          },
          "total": {
            "type": "integer"
          }
        }
      },
      "VETTINGMetadata": {
        "type": "object",
        "required": [
          "processingTimeMs",
          "timestamp",
          "chatModelUsed"
        ],
        "properties": {
          "processingTimeMs": {
            "type": "integer",
            "description": "Total time taken by the API call in milliseconds."
          },
          "timestamp": {
            "type": "string",
            "format": "date-time"
          },
          "sessionId": {
            "type": "string",
            "nullable": true
          },
          "userId": {
            "type": "string",
            "nullable": true
          },
          "chatModelUsed": {
            "type": "string",
            "description": "Requested chat model ID or alias used for drafting."
          },
          "verificationModelUsed": {
            "type": "string",
            "nullable": true,
            "description": "Requested verification model ID or alias used for VETTING verification (null if mode='chat')."
          },
          "calculatedCost": {
            "type": "number",
            "nullable": true,
            "description": "Estimated total request cost in USD when all selected models have registry pricing; null when any selected model has unknown pricing."
          }
        }
      },
      "VETTINGErrorResponse": {
        "type": "object",
        "required": [
          "status",
          "error",
          "metadata"
        ],
        "properties": {
          "status": {
            "type": "string",
            "enum": [
              "error"
            ],
            "example": "error"
          },
          "error": {
            "type": "object",
            "required": [
              "code",
              "message"
            ],
            "properties": {
              "code": {
                "type": "string",
                "description": "Error code (e.g., INVALID_INPUT, MODEL_ERROR, INTERNAL_ERROR)."
              },
              "message": {
                "type": "string",
                "description": "Human-readable error description."
              },
              "details": {
                "type": "array",
                "items": {
                  "type": "string"
                },
                "nullable": true,
                "description": "Optional array of specific validation errors if code is INVALID_INPUT."
              }
            }
          },
          "metadata": {
            "type": "object",
            "required": [
              "timestamp"
            ],
            "properties": {
              "timestamp": {
                "type": "string",
                "format": "date-time"
              },
              "requestId": {
                "type": "string",
                "nullable": true,
                "description": "Optional request tracking ID."
              }
            }
          }
        }
      },
      "AudioSpeechRequest": {
        "type": "object",
        "required": [
          "input",
          "model"
        ],
        "properties": {
          "input": {
            "type": "string",
            "description": "The text to generate audio for. Maximum length: 4096 characters.",
            "maxLength": 4096,
            "example": "VIABLE Lab builds AI-powered learning and research tools."
          },
          "model": {
            "type": "string",
            "description": "Speech model ID. OpenAI-compatible choices include gpt-4o-mini-tts, tts-1, and tts-1-hd; registered VIABLE Lab speech models such as kokoro are also supported.",
            "enum": [
              "gpt-4o-mini-tts",
              "tts-1",
              "tts-1-hd",
              "kokoro"
            ],
            "example": "gpt-4o-mini-tts"
          },
          "voice": {
            "type": "string",
            "description": "Voice to use for generation. Required for OpenAI speech models; optional for registered speech models with a default voice.",
            "example": "alloy"
          },
          "instructions": {
            "type": "string",
            "description": "(Optional) Control the voice of your generated audio with additional instructions. Does not work with tts-1 or tts-1-hd.",
            "example": "Speak in a slightly older, male voice with a British accent."
          },
          "response_format": {
            "type": "string",
            "description": "The format for the audio output.",
            "enum": [
              "mp3",
              "opus",
              "aac",
              "flac",
              "wav",
              "pcm"
            ],
            "default": "mp3",
            "example": "mp3"
          },
          "speed": {
            "type": "number",
            "format": "float",
            "description": "The speed of the generated audio (0.25 to 4.0).",
            "minimum": 0.25,
            "maximum": 4,
            "default": 1,
            "example": 1
          }
        }
      },
      "PricingInfo": {
        "type": "object",
        "properties": {
          "input_per_million": {
            "type": "number",
            "nullable": true,
            "description": "USD per million input tokens."
          },
          "output_per_million": {
            "type": "number",
            "nullable": true,
            "description": "USD per million output tokens."
          },
          "cached_input_per_million": {
            "type": "number",
            "nullable": true,
            "description": "USD per million cached input tokens."
          },
          "image_per_unit": {
            "type": "number",
            "nullable": true,
            "description": "USD per generated image when known."
          },
          "audio_per_minute": {
            "type": "number",
            "nullable": true,
            "description": "USD per audio minute when known."
          },
          "status": {
            "type": "string",
            "example": "documented",
            "description": "Pricing status for the model, such as documented, starts_at, docs_inferred, short_context, or not_listed."
          },
          "note": {
            "type": "string",
            "nullable": true
          }
        }
      },
      "EmbeddingRequest": {
        "type": "object",
        "required": [
          "input"
        ],
        "properties": {
          "model": {
            "type": "string",
            "default": "nomic-embed-text-v1.5",
            "example": "nomic-embed-text-v1.5"
          },
          "input": {
            "oneOf": [
              {
                "type": "string"
              },
              {
                "type": "array",
                "items": {
                  "type": "string"
                }
              }
            ],
            "example": "Searchable text"
          },
          "encoding_format": {
            "type": "string",
            "enum": [
              "float",
              "base64"
            ],
            "default": "float"
          },
          "dimensions": {
            "type": "integer",
            "description": "Optional dimensions if supported by the selected model."
          }
        }
      },
      "EmbeddingResponse": {
        "type": "object",
        "properties": {
          "object": {
            "type": "string",
            "example": "list"
          },
          "data": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "object": {
                  "type": "string",
                  "example": "embedding"
                },
                "index": {
                  "type": "integer"
                },
                "embedding": {
                  "type": "array",
                  "items": {
                    "type": "number"
                  }
                }
              }
            }
          },
          "usage": {
            "$ref": "#/components/schemas/CompletionUsage"
          }
        }
      },
      "ImageGenerationRequest": {
        "type": "object",
        "required": [
          "prompt"
        ],
        "properties": {
          "model": {
            "type": "string",
            "default": "flux.2-klein",
            "example": "flux.2-klein"
          },
          "prompt": {
            "type": "string",
            "example": "A modern classroom dashboard in a clean product UI style"
          },
          "n": {
            "type": "integer",
            "minimum": 1,
            "maximum": 10,
            "default": 1
          },
          "size": {
            "type": "string",
            "example": "1024x1024"
          },
          "quality": {
            "type": "string",
            "example": "standard"
          },
          "response_format": {
            "type": "string",
            "enum": [
              "url",
              "b64_json"
            ],
            "default": "url",
            "description": "`url` returns an API-hosted HTTPS asset URL. `b64_json` returns inline base64 to the caller; logs store only a redacted size summary plus an asset preview URL when asset storage is available."
          }
        }
      },
      "ImageGenerationResponse": {
        "type": "object",
        "properties": {
          "created": {
            "type": "integer"
          },
          "data": {
            "type": "array",
            "items": {
              "type": "object",
              "properties": {
                "url": {
                  "type": "string",
                  "description": "Public HTTPS URL for the generated image. API-hosted URLs use `/v1/assets/...`."
                },
                "b64_json": {
                  "type": "string",
                  "description": "Inline base64 image data when requested with `response_format=b64_json`. This payload is redacted from D1 request logs; logs include an API-hosted asset preview URL when asset storage is available."
                },
                "revised_prompt": {
                  "type": "string"
                }
              }
            }
          }
        }
      },
      "AudioTranscriptionRequest": {
        "type": "object",
        "required": [
          "file"
        ],
        "properties": {
          "file": {
            "type": "string",
            "format": "binary",
            "description": "Audio file upload."
          },
          "model": {
            "type": "string",
            "default": "whisper-large-v3",
            "example": "whisper-large-v3",
            "description": "Transcription model ID. Defaults to whisper-large-v3. OpenAI-compatible choices include gpt-4o-transcribe, gpt-4o-mini-transcribe, and whisper-1.",
            "enum": [
              "whisper-large-v3",
              "gpt-4o-transcribe",
              "gpt-4o-mini-transcribe",
              "whisper-1"
            ]
          },
          "language": {
            "type": "string",
            "description": "Optional ISO-639-1 language code."
          },
          "prompt": {
            "type": "string"
          },
          "response_format": {
            "type": "string",
            "enum": [
              "json",
              "text",
              "srt",
              "verbose_json",
              "vtt"
            ],
            "default": "json"
          },
          "temperature": {
            "type": "number"
          },
          "duration_seconds": {
            "type": "number",
            "description": "Optional client-supplied duration for accurate cost logging."
          },
          "duration_minutes": {
            "type": "number",
            "description": "Optional client-supplied duration for accurate cost logging."
          }
        }
      },
      "AudioTranscriptionResponse": {
        "type": "object",
        "properties": {
          "text": {
            "type": "string",
            "example": "Transcribed audio text."
          }
        },
        "additionalProperties": true
      },
      "DocsMetadataResponse": {
        "type": "object",
        "properties": {
          "object": {
            "type": "string",
            "example": "viablelab.api_metadata"
          },
          "version": {
            "type": "string"
          },
          "base_url": {
            "type": "string",
            "example": "https://api.viablelab.org"
          },
          "default_model": {
            "type": "string"
          },
          "default_models_by_mode": {
            "type": "object",
            "additionalProperties": {
              "type": "string"
            }
          },
          "modes": {
            "type": "object",
            "additionalProperties": {
              "type": "array",
              "items": {
                "$ref": "#/components/schemas/Model"
              }
            }
          },
          "models": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/Model"
            }
          },
          "endpoints": {
            "type": "array",
            "items": {
              "type": "object"
            }
          },
          "quickstarts": {
            "type": "object"
          },
          "pricing_notes": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "cache": {
            "type": "object"
          },
          "agent_guide_url": {
            "type": "string",
            "example": "https://developers.viablelab.org/agents/viablelab-api.md"
          }
        }
      }
    },
    "securitySchemes": {
      "BearerAuth": {
        "type": "http",
        "scheme": "bearer",
        "description": "Bearer token authentication (Planned for future enforcement)."
      },
      "ApiKeyAuth": {
        "type": "http",
        "scheme": "bearer",
        "bearerFormat": "VIABLE Lab API key",
        "description": "VIABLE Lab API key generated from the developer dashboard. Required for protected API usage when API_KEY_ENFORCEMENT is required."
      }
    },
    "responses": {
      "Unauthorized": {
        "description": "Authentication failed. Invalid or missing Bearer token (Not currently enforced).",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Invalid authentication credentials",
                "type": "invalid_request_error",
                "code": "authentication_failed"
              }
            }
          }
        }
      },
      "Forbidden": {
        "description": "Access denied. Request source (Origin/Referer via CORS) might be invalid (temporary check), or insufficient permissions (future).",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Forbidden: Invalid Origin.",
                "type": "forbidden_error",
                "code": "invalid_origin"
              }
            }
          }
        }
      },
      "MethodNotAllowed": {
        "description": "Method Not Allowed. The HTTP method used is not supported for this endpoint.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Method Not Allowed",
                "type": "invalid_request_error",
                "code": "method_not_allowed"
              }
            }
          }
        }
      },
      "BadRequest": {
        "description": "Bad Request. The request payload is malformed, contains invalid parameters, or failed validation.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Invalid request body: JSON parsing failed",
                "type": "invalid_request_error",
                "code": "invalid_json"
              }
            }
          }
        }
      },
      "RateLimited": {
        "description": "Too Many Requests. Rate limit exceeded.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Rate limit exceeded",
                "type": "requests_error",
                "code": "rate_limit_exceeded"
              }
            }
          }
        }
      },
      "NotImplemented": {
        "description": "Not Implemented. The requested functionality is not available.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Endpoint not implemented",
                "type": "not_implemented_error",
                "code": "not_implemented"
              }
            }
          }
        }
      },
      "ServerError": {
        "description": "Internal Server Error. An unexpected error occurred on the server.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Internal Server Error",
                "type": "api_error",
                "code": "internal_error"
              }
            }
          }
        }
      },
      "BadAPI": {
        "description": "Upstream model service error. Error occurred when communicating with a model provider.",
        "content": {
          "application/json": {
            "schema": {
              "$ref": "#/components/schemas/ErrorResponse"
            },
            "example": {
              "error": {
                "message": "Error from model provider: 500",
                "type": "service_error",
                "code": "model_provider_error"
              }
            }
          }
        }
      }
    }
  }
}
