{"openapi":"3.1.0","info":{"title":"Brandkit API","version":"1.0.0","description":"Extract canonical brand logos, favicons, colors, typography, and brand books from a URL.","license":{"name":"Private"}},"servers":[{"url":"https://brandkit.danielhowells.com"}],"externalDocs":{"description":"Agent-readable documentation","url":"https://brandkit.danielhowells.com/llms.txt"},"tags":[{"name":"logos","description":"Logo and favicon extraction"},{"name":"brand-books","description":"Richer brand-book extraction"},{"name":"catalog","description":"Recent and cached assets"}],"paths":{"/health":{"get":{"operationId":"get_health","tags":["catalog"],"summary":"Check API health","responses":{"200":{"description":"API is healthy","content":{"application/json":{"schema":{"type":"object","required":["ok","service"],"properties":{"ok":{"type":"boolean"},"service":{"type":"string"}}}}}}}}},"/v1/logo":{"get":{"operationId":"get_logo","tags":["logos"],"summary":"Extract a logo response for a URL","description":"Returns the best logo and favicon candidates with confidence, source, format, dimensions, tone, and sanitised SVG when available.","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","examples":["stripe.com"]},"description":"Domain or URL to extract from."},{"name":"refresh","in":"query","required":false,"schema":{"type":"string","enum":["1"]},"description":"Set to 1 to bypass the 30-day cache and re-extract."}],"responses":{"200":{"description":"Logo extraction response","headers":{"cache-control":{"schema":{"type":"string"},"description":"Public cache policy for the response."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LogoResponse"}}}},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}},"post":{"operationId":"post_logo","tags":["logos"],"summary":"Extract a logo response from a JSON body","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UrlRequest"},"examples":{"stripe":{"value":{"url":"stripe.com","refresh":false}}}}}},"responses":{"200":{"description":"Logo extraction response","headers":{"cache-control":{"schema":{"type":"string"},"description":"Public cache policy for the response."}},"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LogoResponse"}}}},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/logo.svg":{"get":{"operationId":"get_logo_svg","tags":["logos"],"summary":"Return the extracted SVG logo","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","examples":["stripe.com"]},"description":"Domain or URL to extract from."},{"name":"refresh","in":"query","required":false,"schema":{"type":"string","enum":["1"]},"description":"Set to 1 to bypass the 30-day cache and re-extract."}],"responses":{"200":{"description":"Sanitised SVG logo","content":{"image/svg+xml":{"schema":{"type":"string"}}}},"302":{"description":"Remote SVG asset redirect"},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"404":{"description":"No SVG logo available","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/logo.raster":{"get":{"operationId":"get_logo_raster","tags":["logos"],"summary":"Return the extracted raster logo","description":"Returns a raster logo proxy. Transparent padding is trimmed before serving when possible.","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","examples":["stripe.com"]},"description":"Domain or URL to extract from."},{"name":"refresh","in":"query","required":false,"schema":{"type":"string","enum":["1"]},"description":"Set to 1 to bypass the 30-day cache and re-extract."}],"responses":{"200":{"description":"Raster logo bytes","content":{"image/png":{"schema":{"type":"string","format":"binary"}},"image/jpeg":{"schema":{"type":"string","format":"binary"}},"image/webp":{"schema":{"type":"string","format":"binary"}}}},"302":{"description":"Remote raster asset redirect"},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"404":{"description":"No raster logo available","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/favicon":{"get":{"operationId":"get_favicon","tags":["logos"],"summary":"Return or redirect to the best favicon","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","examples":["stripe.com"]},"description":"Domain or URL to extract from."},{"name":"refresh","in":"query","required":false,"schema":{"type":"string","enum":["1"]},"description":"Set to 1 to bypass the 30-day cache and re-extract."}],"responses":{"200":{"description":"Inline SVG favicon or proxied raster favicon","content":{"image/svg+xml":{"schema":{"type":"string"}},"image/png":{"schema":{"type":"string","format":"binary"}},"image/x-icon":{"schema":{"type":"string","format":"binary"}}}},"302":{"description":"Remote favicon asset redirect"},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"404":{"description":"No favicon available","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/brand":{"get":{"operationId":"get_brand_book","tags":["brand-books"],"summary":"Extract a full brand book for a URL","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","examples":["stripe.com"]},"description":"Domain or URL to extract from."},{"name":"refresh","in":"query","required":false,"schema":{"type":"string","enum":["1"]},"description":"Set to 1 to bypass the 30-day cache and re-extract."}],"responses":{"200":{"description":"Brand-book extraction response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrandBookResponse"}}}},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"500":{"description":"Workflow failed","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}},"post":{"operationId":"post_brand_book","tags":["brand-books"],"summary":"Extract a full brand book from a JSON body","requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UrlRequest"}}}},"responses":{"200":{"description":"Brand-book extraction response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/BrandBookResponse"}}}},"400":{"description":"Missing or invalid URL","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"500":{"description":"Workflow failed","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/logo/recent":{"get":{"operationId":"list_recent_logos","tags":["catalog"],"summary":"List recently fetched logo responses","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","minimum":1,"maximum":60,"default":24}}],"responses":{"200":{"description":"Recent logo responses","headers":{"cache-control":{"schema":{"type":"string"},"description":"Public cache policy for the response."}},"content":{"application/json":{"schema":{"type":"object","required":["logos"],"properties":{"logos":{"type":"array","items":{"$ref":"#/components/schemas/RecentLogoResponse"}}}}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}},"/v1/brand/{domain}/{slot}":{"get":{"operationId":"get_brand_asset_slot","tags":["brand-books"],"summary":"Redirect to a cached brand-book asset slot","parameters":[{"name":"domain","in":"path","required":true,"schema":{"type":"string","examples":["stripe.com"]}},{"name":"slot","in":"path","required":true,"schema":{"type":"string","enum":["mark","logotype","light","dark","favicon"]}}],"responses":{"302":{"description":"Redirect to cached asset URL"},"404":{"description":"No cached brand book or slot asset","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}},"429":{"description":"Rate limited","content":{"application/problem+json":{"schema":{"$ref":"#/components/schemas/Problem"}}}}}}}},"components":{"schemas":{"UrlRequest":{"type":"object","required":["url"],"properties":{"url":{"type":"string","examples":["stripe.com"]},"refresh":{"type":"boolean","default":false,"description":"When true, bypasses the 30-day extraction cache."}}},"LogoResponse":{"type":"object","required":["domain","logo","favicon","sources","candidates"],"properties":{"domain":{"type":"string","examples":["stripe.com"]},"name":{"type":"string"},"logo":{"anyOf":[{"$ref":"#/components/schemas/LogoAsset"},{"type":"null"}]},"favicon":{"anyOf":[{"$ref":"#/components/schemas/LogoAsset"},{"type":"null"}]},"sources":{"type":"array","items":{"type":"string"}},"candidates":{"type":"integer","minimum":0}}},"RecentLogoResponse":{"allOf":[{"$ref":"#/components/schemas/LogoResponse"},{"type":"object","required":["fetchedAt"],"properties":{"fetchedAt":{"type":"string","format":"date-time"}}}]},"LogoAsset":{"type":"object","required":["url","format","source","confidence"],"properties":{"url":{"type":"string"},"format":{"type":"string","enum":["svg","png","ico","jpg","webp"]},"source":{"type":"string"},"confidence":{"type":"number","minimum":0,"maximum":1},"svg":{"type":"string","description":"Sanitised SVG source."},"width":{"type":"integer","minimum":1},"height":{"type":"integer","minimum":1},"bytes":{"type":"integer","minimum":0},"tone":{"type":"string","enum":["dark","light","colored-dark","colored-light","colored"]},"trimmed":{"type":"boolean","description":"True when raster dimensions reflect the tight content bounding box."}}},"BrandBookResponse":{"type":"object","required":["domain","brandBook","cached"],"properties":{"domain":{"type":"string"},"cached":{"type":"boolean"},"brandBook":{"$ref":"#/components/schemas/BrandBook"}}},"BrandBook":{"type":"object","required":["domain","name","logo","colors","typography","source"],"properties":{"domain":{"type":"string"},"name":{"type":"string"},"description":{"type":"string"},"logo":{"type":"object","properties":{"mark":{"$ref":"#/components/schemas/BrandAsset"},"logotype":{"$ref":"#/components/schemas/BrandAsset"},"light":{"$ref":"#/components/schemas/BrandAsset"},"dark":{"$ref":"#/components/schemas/BrandAsset"},"favicon":{"$ref":"#/components/schemas/BrandAsset"}}},"colors":{"type":"object","required":["primary","palette"],"properties":{"primary":{"type":"string","pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$"},"palette":{"type":"array","items":{"type":"string","pattern":"^#(?:[0-9a-fA-F]{3}){1,2}$"},"maxItems":8}}},"typography":{"type":"object","required":["primary"],"properties":{"primary":{"type":"object","required":["family","source"],"properties":{"family":{"type":"string"},"source":{"type":"string","enum":["google","adobe","system","unknown"]},"stack":{"type":"string"}}}}},"source":{"type":"object","required":["fetchedAt","ttl","sources","confidence","aiCurated"],"properties":{"fetchedAt":{"type":"string","format":"date-time"},"ttl":{"type":"integer","minimum":1},"sources":{"type":"array","items":{"type":"string"}},"confidence":{"type":"number","minimum":0,"maximum":1},"aiCurated":{"type":"boolean"}}}}},"BrandAsset":{"type":"object","required":["url","format","bytes"],"properties":{"url":{"type":"string","format":"uri"},"format":{"type":"string","enum":["svg","png","ico","jpg","webp"]},"width":{"type":"integer","minimum":1},"height":{"type":"integer","minimum":1},"bytes":{"type":"integer","minimum":0}}},"Problem":{"type":"object","required":["type","title","status","detail","instance","code","error","message","doc_uri","is_retriable","request_id"],"properties":{"type":{"type":"string","format":"uri"},"title":{"type":"string"},"status":{"type":"integer"},"detail":{"type":"string"},"instance":{"type":"string"},"code":{"type":"string"},"error":{"type":"string"},"message":{"type":"string"},"doc_uri":{"type":"string","format":"uri"},"is_retriable":{"type":"boolean"},"request_id":{"type":"string"},"retry_after":{"type":"integer","minimum":1}}}}}}