{
  "openapi": "3.1.0",
  "info": {
    "title": "Tokonomics API",
    "description": "Budget-first AI cost metering proxy. Sits between your app and any LLM provider (OpenAI, Anthropic, DeepSeek, Gemini, Mistral, xAI, Cohere, Groq, Together AI). Records every token, calculates cost, fires budget alerts.",
    "version": "1.0.0",
    "contact": {
      "name": "Tokonomics Support",
      "email": "hello@tokonomics.ca",
      "url": "https://tokonomics.ca"
    },
    "termsOfService": "https://tokonomics.ca/terms",
    "license": {
      "name": "Proprietary"
    }
  },
  "servers": [
    {
      "url": "https://tokonomics.ca",
      "description": "Production"
    }
  ],
  "security": [
    {
      "BearerAuth": []
    }
  ],
  "paths": {
    "/proxy/{provider}/{path}": {
      "post": {
        "operationId": "proxyLlmRequest",
        "summary": "Proxy an LLM API call",
        "description": "Forwards the request to the upstream LLM provider, streams the response back, and records token usage + cost. The request body is passed through unchanged — use the same format as the provider's native API.",
        "tags": ["Proxy"],
        "parameters": [
          {
            "name": "provider",
            "in": "path",
            "required": true,
            "description": "LLM provider slug",
            "schema": {
              "type": "string",
              "enum": ["openai", "anthropic", "deepseek", "gemini", "mistral", "xai", "cohere", "groq", "together"]
            }
          },
          {
            "name": "path",
            "in": "path",
            "required": true,
            "description": "Upstream API path (e.g. `chat/completions` for OpenAI, `messages` for Anthropic)",
            "schema": {
              "type": "string"
            },
            "examples": {
              "openai": { "value": "chat/completions" },
              "anthropic": { "value": "messages" }
            }
          },
          {
            "name": "X-Metering-Tags",
            "in": "header",
            "required": false,
            "description": "JSON object of custom tags for cost attribution. Stripped before forwarding to the provider.",
            "schema": {
              "type": "string"
            },
            "example": "{\"team\":\"growth\",\"feature\":\"chatbot\"}"
          },
          {
            "name": "X-Feature-Name",
            "in": "header",
            "required": false,
            "description": "Shorthand feature tag. Stripped before forwarding.",
            "schema": {
              "type": "string"
            },
            "example": "support-bot"
          },
          {
            "name": "X-Tenant-ID",
            "in": "header",
            "required": false,
            "description": "Your customer's tenant ID for per-customer cost tracking. Stripped before forwarding.",
            "schema": {
              "type": "string"
            },
            "example": "tenant_abc123"
          }
        ],
        "requestBody": {
          "required": true,
          "description": "The provider's native request body, passed through unchanged.",
          "content": {
            "application/json": {
              "schema": {
                "type": "object"
              },
              "example": {
                "model": "gpt-4o",
                "messages": [
                  { "role": "user", "content": "Hello, world!" }
                ]
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "Streamed response from the LLM provider (passed through unchanged)",
            "headers": {
              "X-Metering-Latency": {
                "description": "Round-trip latency to the upstream provider in milliseconds",
                "schema": { "type": "string" },
                "example": "342ms"
              },
              "X-RateLimit-Limit": {
                "description": "Requests allowed per minute for this API key",
                "schema": { "type": "integer" }
              },
              "X-RateLimit-Remaining": {
                "description": "Requests remaining in the current window",
                "schema": { "type": "integer" }
              }
            }
          },
          "401": {
            "description": "Invalid or missing API key",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/Error" }
              }
            }
          },
          "429": {
            "description": "Rate limit exceeded or monthly budget cap reached",
            "headers": {
              "Retry-After": {
                "description": "Seconds until the rate limit resets",
                "schema": { "type": "integer" }
              }
            },
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/Error" }
              }
            }
          },
          "502": {
            "description": "Upstream provider error",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/Error" }
              }
            }
          }
        }
      }
    },
    "/analytics/summary": {
      "get": {
        "operationId": "getAnalyticsSummary",
        "summary": "Current month spend summary",
        "description": "Returns current month total spend, budget used percentage, and breakdown by model.",
        "tags": ["Analytics"],
        "responses": {
          "200": {
            "description": "Monthly spend summary",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "current_month_spend": { "type": "number", "example": 127.45 },
                    "monthly_budget": { "type": "number", "example": 500.00 },
                    "budget_used_percent": { "type": "number", "example": 25.49 },
                    "by_model": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "model": { "type": "string", "example": "gpt-4o" },
                          "spend": { "type": "number", "example": 89.20 },
                          "requests": { "type": "integer", "example": 4520 }
                        }
                      }
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Invalid or missing API key",
            "content": {
              "application/json": {
                "schema": { "$ref": "#/components/schemas/Error" }
              }
            }
          }
        }
      }
    },
    "/analytics/daily": {
      "get": {
        "operationId": "getAnalyticsDaily",
        "summary": "Daily spend breakdown",
        "description": "Returns spend per day for the last N days.",
        "tags": ["Analytics"],
        "parameters": [
          {
            "name": "days",
            "in": "query",
            "required": false,
            "description": "Number of days to return (default 30, max 90)",
            "schema": {
              "type": "integer",
              "default": 30,
              "maximum": 90,
              "minimum": 1
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Daily spend data",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "days": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "date": { "type": "string", "format": "date", "example": "2026-06-10" },
                          "spend": { "type": "number", "example": 4.23 },
                          "requests": { "type": "integer", "example": 210 }
                        }
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/analytics/by-tag": {
      "get": {
        "operationId": "getAnalyticsByTag",
        "summary": "Spend grouped by tag",
        "description": "Returns spend grouped by a custom tag key (e.g. team, feature, env).",
        "tags": ["Analytics"],
        "parameters": [
          {
            "name": "key",
            "in": "query",
            "required": true,
            "description": "Tag key to group by",
            "schema": { "type": "string" },
            "example": "team"
          },
          {
            "name": "period",
            "in": "query",
            "required": false,
            "description": "Time period",
            "schema": {
              "type": "string",
              "enum": ["week", "month", "quarter"],
              "default": "month"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "Spend grouped by tag value",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "key": { "type": "string", "example": "team" },
                    "period": { "type": "string", "example": "month" },
                    "groups": {
                      "type": "array",
                      "items": {
                        "type": "object",
                        "properties": {
                          "value": { "type": "string", "example": "growth" },
                          "spend": { "type": "number", "example": 45.20 },
                          "requests": { "type": "integer", "example": 2300 }
                        }
                      }
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/analytics/events": {
      "get": {
        "operationId": "getAnalyticsEvents",
        "summary": "Paginated raw usage events",
        "description": "Returns individual usage event records with full detail.",
        "tags": ["Analytics"],
        "parameters": [
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": { "type": "integer", "default": 50, "maximum": 200, "minimum": 1 }
          },
          {
            "name": "offset",
            "in": "query",
            "required": false,
            "schema": { "type": "integer", "default": 0, "minimum": 0 }
          }
        ],
        "responses": {
          "200": {
            "description": "List of usage events",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "events": {
                      "type": "array",
                      "items": { "$ref": "#/components/schemas/UsageEvent" }
                    },
                    "total": { "type": "integer" },
                    "limit": { "type": "integer" },
                    "offset": { "type": "integer" }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/health": {
      "get": {
        "operationId": "healthCheck",
        "summary": "Health check",
        "description": "Returns service status. No authentication required.",
        "tags": ["System"],
        "security": [],
        "responses": {
          "200": {
            "description": "Service is healthy",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "status": { "type": "string", "example": "ok" },
                    "ts": { "type": "integer", "example": 1718020800 }
                  }
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "BearerAuth": {
        "type": "http",
        "scheme": "bearer",
        "description": "Tokonomics API key (format: `mk_` followed by 48 hex characters). Pass as `Authorization: Bearer mk_xxx`."
      }
    },
    "schemas": {
      "Error": {
        "type": "object",
        "properties": {
          "error": { "type": "string", "example": "Unauthorized" },
          "message": { "type": "string", "example": "Invalid or missing API key" }
        },
        "required": ["error"]
      },
      "UsageEvent": {
        "type": "object",
        "properties": {
          "id": { "type": "string", "format": "uuid" },
          "model": { "type": "string", "example": "gpt-4o" },
          "provider": { "type": "string", "example": "openai" },
          "input_tokens": { "type": "integer", "example": 150 },
          "output_tokens": { "type": "integer", "example": 320 },
          "cache_read_tokens": { "type": "integer", "example": 0 },
          "cache_creation_tokens": { "type": "integer", "example": 0 },
          "cost_usd": { "type": "number", "example": 0.00555 },
          "latency_ms": { "type": "integer", "example": 342 },
          "tags": {
            "type": "object",
            "additionalProperties": { "type": "string" },
            "example": { "team": "growth", "feature": "chatbot" }
          },
          "created_at": { "type": "string", "format": "date-time" }
        }
      }
    }
  },
  "tags": [
    { "name": "Proxy", "description": "Forward LLM API calls through the metering proxy" },
    { "name": "Analytics", "description": "Query usage data, spend breakdowns, and cost reports" },
    { "name": "System", "description": "Health checks and service status" }
  ]
}
