{
  "openapi": "3.1.0",
  "info": {
    "title": "Ohio Sports Rankings School Branding API",
    "version": "1.0.0",
    "description": "Public school identity, color, and normalized PNG or validated SVG logo data. SVG assets reject active and external content. Anonymous requests are limited to 30 per minute per IP. Approved bearer tokens with the school-branding:read ability are unlimited."
  },
  "servers": [
    { "url": "https://ohsportsrank.com", "description": "Production" }
  ],
  "tags": [
    { "name": "School Branding" }
  ],
  "paths": {
    "/api/v1/school-branding": {
      "get": {
        "tags": ["School Branding"],
        "summary": "List school branding",
        "operationId": "listSchoolBranding",
        "security": [{}, { "bearerAuth": [] }],
        "parameters": [
          { "name": "q", "in": "query", "schema": { "type": ["string", "null"], "minLength": 2, "maxLength": 100 }, "description": "Search name, common name, or city." },
          { "name": "updated_since", "in": "query", "schema": { "type": ["string", "null"], "format": "date-time" }, "description": "Return schools changed at or after this timestamp." },
          { "name": "has_branding", "in": "query", "schema": { "type": ["boolean", "null"] }, "description": "Filter schools with any branding data or with none." },
          { "name": "out_of_state", "in": "query", "schema": { "type": ["boolean", "null"] }, "description": "Filter Ohio schools or out-of-state opponents." },
          { "name": "per_page", "in": "query", "schema": { "type": "integer", "minimum": 1, "maximum": 100, "default": 50 } },
          { "name": "page", "in": "query", "schema": { "type": "integer", "minimum": 1, "default": 1 } }
        ],
        "responses": {
          "200": {
            "description": "Paginated branding collection.",
            "headers": {
              "X-RateLimit-Limit": { "schema": { "type": "integer" }, "description": "Anonymous request limit for the current window." },
              "X-RateLimit-Remaining": { "schema": { "type": "integer" } }
            },
            "content": { "application/json": { "schema": { "$ref": "#/components/schemas/SchoolBrandingCollection" } } }
          },
          "422": { "$ref": "#/components/responses/ValidationError" },
          "429": { "$ref": "#/components/responses/RateLimited" }
        }
      }
    },
    "/api/v1/school-branding/{stateId}": {
      "get": {
        "tags": ["School Branding"],
        "summary": "Get school branding",
        "operationId": "getSchoolBranding",
        "security": [{}, { "bearerAuth": [] }],
        "parameters": [
          { "name": "stateId", "in": "path", "required": true, "schema": { "type": "integer" }, "description": "Stable Ohio Sports Rankings school state ID." }
        ],
        "responses": {
          "200": {
            "description": "School branding resource.",
            "content": { "application/json": { "schema": { "type": "object", "required": ["data"], "properties": { "data": { "$ref": "#/components/schemas/SchoolBranding" } } } } }
          },
          "404": { "$ref": "#/components/responses/NotFound" },
          "429": { "$ref": "#/components/responses/RateLimited" }
        }
      }
    }
  },
  "components": {
    "securitySchemes": {
      "bearerAuth": { "type": "http", "scheme": "bearer", "description": "Optional dedicated Sanctum token. A token carrying only school-branding:read has unlimited access to these endpoints and is rejected on every other API route." }
    },
    "schemas": {
      "NullableString": { "type": ["string", "null"] },
      "Colors": {
        "type": "object",
        "required": ["primary", "secondary"],
        "properties": {
          "primary": { "$ref": "#/components/schemas/NullableString" },
          "secondary": { "$ref": "#/components/schemas/NullableString" }
        }
      },
      "Logos": {
        "type": "object",
        "required": ["primary", "alternate"],
        "properties": {
          "primary": { "type": ["string", "null"], "format": "uri", "description": "Absolute PNG or SVG URL." },
          "alternate": { "type": ["string", "null"], "format": "uri", "description": "Absolute PNG or SVG URL." }
        }
      },
      "LogoFormats": {
        "type": "object",
        "required": ["primary", "alternate"],
        "properties": {
          "primary": { "type": ["string", "null"], "enum": ["png", "svg", null] },
          "alternate": { "type": ["string", "null"], "enum": ["png", "svg", null] }
        }
      },
      "SchoolBranding": {
        "type": "object",
        "required": ["state_id", "name", "common_name", "city", "nickname", "girls_nickname", "out_of_state", "colors", "logos", "logo_formats", "updated_at"],
        "properties": {
          "state_id": { "type": "integer" },
          "name": { "type": "string" },
          "common_name": { "$ref": "#/components/schemas/NullableString" },
          "city": { "$ref": "#/components/schemas/NullableString" },
          "nickname": { "$ref": "#/components/schemas/NullableString" },
          "girls_nickname": { "$ref": "#/components/schemas/NullableString" },
          "out_of_state": { "type": "boolean" },
          "colors": { "$ref": "#/components/schemas/Colors" },
          "logos": { "$ref": "#/components/schemas/Logos" },
          "logo_formats": { "$ref": "#/components/schemas/LogoFormats" },
          "updated_at": { "type": ["string", "null"], "format": "date-time" }
        }
      },
      "PaginationLinks": {
        "type": "object",
        "additionalProperties": true,
        "required": ["first", "last", "prev", "next"]
      },
      "PaginationMeta": {
        "type": "object",
        "additionalProperties": true,
        "required": ["current_page", "last_page", "per_page", "total"]
      },
      "SchoolBrandingCollection": {
        "type": "object",
        "required": ["data", "links", "meta"],
        "properties": {
          "data": { "type": "array", "items": { "$ref": "#/components/schemas/SchoolBranding" } },
          "links": { "$ref": "#/components/schemas/PaginationLinks" },
          "meta": { "$ref": "#/components/schemas/PaginationMeta" }
        }
      },
      "Error": {
        "type": "object",
        "additionalProperties": true,
        "properties": { "message": { "type": "string" } }
      }
    },
    "responses": {
      "ValidationError": { "description": "Invalid query parameters.", "content": { "application/json": { "schema": { "$ref": "#/components/schemas/Error" } } } },
      "NotFound": { "description": "School not found.", "content": { "application/json": { "schema": { "$ref": "#/components/schemas/Error" } } } },
      "RateLimited": {
        "description": "Rate limit exceeded.",
        "headers": { "Retry-After": { "schema": { "type": "integer" } } },
        "content": { "application/json": { "schema": { "allOf": [{ "$ref": "#/components/schemas/Error" }, { "type": "object", "properties": { "retry_after": { "type": "integer" } } }] } } }
      }
    }
  }
}
