[{"data":1,"prerenderedAt":1005},["ShallowReactive",2],{"pricing-plans":3,"content-page-\u002Fdocs\u002Fbrands":4,"api-docs-metadata":506,"i-ph:list":3,"i-ph:caret-right":3,"i-ph:copy":3,"i-ph:caret-down":3,"i-ph:twitter-logo":3,"i-ph:youtube-logo":3},null,{"id":5,"title":6,"body":7,"description":496,"extension":497,"meta":498,"navigation":501,"path":502,"seo":503,"stem":504,"__hash__":505},"all\u002Fdocs\u002Fbrands.md","Brands",{"type":8,"value":9,"toc":489},"minimark",[10,14,28,33,40,111,126,133,141,149,242,245,249,255,283,294,395,405,409,485],[11,12,6],"h1",{"id":13},"brands",[15,16,17,18,22,23,27],"p",{},"A ",[19,20,21],"strong",{},"brand"," is a structured token kit — logos, colors, typography, icons — that templates bind to. Bind a layer's fill to ",[24,25,26],"code",{},"colors.primary"," once, and every render follows the brand; swap the brand (or override tokens per render) and the same design re-skins itself.",[29,30,32],"h2",{"id":31},"token-model","Token model",[15,34,35,36,39],{},"Brand tokens are a nested object addressed by ",[19,37,38],{},"dot paths",":",[41,42,43,56],"table",{},[44,45,46],"thead",{},[47,48,49,53],"tr",{},[50,51,52],"th",{},"Group",[50,54,55],{},"Example tokens",[57,58,59,85,103],"tbody",{},[47,60,61,67],{},[62,63,64],"td",{},[24,65,66],{},"logos",[62,68,69,72,73,72,76,72,79,72,82],{},[24,70,71],{},"logos.logo",", ",[24,74,75],{},"logos.logoDark",[24,77,78],{},"logos.logoLight",[24,80,81],{},"logos.icon",[24,83,84],{},"logos.iconLight",[47,86,87,92],{},[62,88,89],{},[24,90,91],{},"colors",[62,93,94,72,96,72,99,102],{},[24,95,26],{},[24,97,98],{},"colors.secondary",[24,100,101],{},"colors.accent",", copy\u002Fbackground colors",[47,104,105,108],{},[62,106,107],{},"Typography, icons, …",[62,109,110],{},"font families and weights, icon style preferences",[15,112,113,114,117,118,121,122,125],{},"Each brand holds ",[19,115,116],{},"draft tokens"," (being edited) and ",[19,119,120],{},"live tokens"," (what published renders use). Templates reference tokens through brand bindings in the editor; a template can also declare a ",[24,123,124],{},"defaultBrandId",".",[15,127,128],{},[129,130],"img",{"alt":131,"src":132},"A brand's token book: logo variants, color tokens, and live previews of templates rendered with the brand","\u002Fimages\u002Fdocs\u002Fbrands\u002Fbrand-token-book.png",[29,134,136,137,140],{"id":135},"per-render-overrides-brandtweaks","Per-render overrides (",[24,138,139],{},"brandTweaks",")",[15,142,143,144,39],{},"Any render can override brand tokens by dot path without touching the brand itself — see the ",[145,146,148],"a",{"href":147},"\u002Fdocs\u002Frendering","Rendering API",[150,151,156],"pre",{"className":152,"code":153,"language":154,"meta":155,"style":155},"language-json shiki shiki-themes github-light github-dark","{\n  \"pageId\": \"PAGE_ID\",\n  \"format\": \"png\",\n  \"brandTweaks\": {\n    \"colors.primary\": \"#7c3aed\",\n    \"logos.logo\": \"https:\u002F\u002Fcdn.example.com\u002Facme-logo.svg\"\n  }\n}\n","json","",[24,157,158,167,184,197,206,219,230,236],{"__ignoreMap":155},[159,160,163],"span",{"class":161,"line":162},"line",1,[159,164,166],{"class":165},"sVt8B","{\n",[159,168,170,174,177,181],{"class":161,"line":169},2,[159,171,173],{"class":172},"sj4cs","  \"pageId\"",[159,175,176],{"class":165},": ",[159,178,180],{"class":179},"sZZnC","\"PAGE_ID\"",[159,182,183],{"class":165},",\n",[159,185,187,190,192,195],{"class":161,"line":186},3,[159,188,189],{"class":172},"  \"format\"",[159,191,176],{"class":165},[159,193,194],{"class":179},"\"png\"",[159,196,183],{"class":165},[159,198,200,203],{"class":161,"line":199},4,[159,201,202],{"class":172},"  \"brandTweaks\"",[159,204,205],{"class":165},": {\n",[159,207,209,212,214,217],{"class":161,"line":208},5,[159,210,211],{"class":172},"    \"colors.primary\"",[159,213,176],{"class":165},[159,215,216],{"class":179},"\"#7c3aed\"",[159,218,183],{"class":165},[159,220,222,225,227],{"class":161,"line":221},6,[159,223,224],{"class":172},"    \"logos.logo\"",[159,226,176],{"class":165},[159,228,229],{"class":179},"\"https:\u002F\u002Fcdn.example.com\u002Facme-logo.svg\"\n",[159,231,233],{"class":161,"line":232},7,[159,234,235],{"class":165},"  }\n",[159,237,239],{"class":161,"line":238},8,[159,240,241],{"class":165},"}\n",[15,243,244],{},"This is the multi-brand pattern: one template, N brands, N on-brand outputs — without duplicating designs.",[29,246,248],{"id":247},"managing-brands","Managing brands",[15,250,251,254],{},[19,252,253],{},"In the app:"," create and edit brands under your space's Brands section; the editor's brand panel binds layers to tokens.",[15,256,257,260,261,265,266,72,269,72,272,72,275,278,279,282],{},[19,258,259],{},"Via MCP (API-key friendly):"," AI agents and scripts can manage brands through the ",[145,262,264],{"href":263},"\u002Fdocs\u002Fintegrations\u002Fmcp","MCP server"," with a Bearer API key — ",[24,267,268],{},"list_brands",[24,270,271],{},"get_brand",[24,273,274],{},"create_brand",[24,276,277],{},"update_brand",", and ",[24,280,281],{},"resolve_brand"," (extract brand tokens from a website).",[15,284,285,288,289,293],{},[19,286,287],{},"Via REST (session-authenticated):"," the dashboard uses these endpoints. They require a logged-in session — they are ",[290,291,292],"em",{},"not"," callable with an API key today; use MCP for programmatic access.",[41,295,296,309],{},[44,297,298],{},[47,299,300,303,306],{},[50,301,302],{},"Method",[50,304,305],{},"Path",[50,307,308],{},"Notes",[57,310,311,330,348,367,381],{},[47,312,313,318,323],{},[62,314,315],{},[24,316,317],{},"GET",[62,319,320],{},[24,321,322],{},"\u002Fapi\u002Fv1\u002Fbrands?page=&perPage=",[62,324,325,326,329],{},"List brands in the current space. ",[24,327,328],{},"?public=true"," lists public brands without auth.",[47,331,332,336,341],{},[62,333,334],{},[24,335,317],{},[62,337,338],{},[24,339,340],{},"\u002Fapi\u002Fv1\u002Fbrands\u002F:id",[62,342,343,344,347],{},"Fetch one brand. Public brands (with ",[24,345,346],{},"publicOn",") need no auth.",[47,349,350,355,360],{},[62,351,352],{},[24,353,354],{},"POST",[62,356,357],{},[24,358,359],{},"\u002Fapi\u002Fv1\u002Fbrands",[62,361,362,363,366],{},"Create — ",[24,364,365],{},"{ name, tokens?, draftTokens?, liveTokens?, variants?, extra? }",". External image URLs in tokens are re-uploaded to your space.",[47,368,369,374,378],{},[62,370,371],{},[24,372,373],{},"PUT",[62,375,376],{},[24,377,340],{},[62,379,380],{},"Update (same fields, all optional).",[47,382,383,388,392],{},[62,384,385],{},[24,386,387],{},"DELETE",[62,389,390],{},[24,391,340],{},[62,393,394],{},"Soft-delete.",[15,396,397,398,401,402,125],{},"List responses have the standard shape ",[24,399,400],{},"{ list, count, pagesCount }","; single-document responses return ",[24,403,404],{},"{ doc }",[29,406,408],{"id":407},"brand-fields","Brand fields",[41,410,411,421],{},[44,412,413],{},[47,414,415,418],{},[50,416,417],{},"Field",[50,419,420],{},"Description",[57,422,423,436,446,456,466,476],{},[47,424,425,433],{},[62,426,427,72,430],{},[24,428,429],{},"_id",[24,431,432],{},"name",[62,434,435],{},"Identity.",[47,437,438,443],{},[62,439,440],{},[24,441,442],{},"draftTokens",[62,444,445],{},"Tokens as currently edited.",[47,447,448,453],{},[62,449,450],{},[24,451,452],{},"liveTokens",[62,454,455],{},"Tokens used by published renders.",[47,457,458,463],{},[62,459,460],{},[24,461,462],{},"tokens",[62,464,465],{},"Resolved\u002Flegacy token set.",[47,467,468,473],{},[62,469,470],{},[24,471,472],{},"variants",[62,474,475],{},"Named variations of the kit.",[47,477,478,482],{},[62,479,480],{},[24,481,346],{},[62,483,484],{},"When set, the brand is publicly readable.",[486,487,488],"style",{},"html pre.shiki code .sVt8B, html code.shiki .sVt8B{--shiki-default:#24292E;--shiki-dark:#E1E4E8}html pre.shiki code .sj4cs, html code.shiki .sj4cs{--shiki-default:#005CC5;--shiki-dark:#79B8FF}html pre.shiki code .sZZnC, html code.shiki .sZZnC{--shiki-default:#032F62;--shiki-dark:#9ECBFF}html .default .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .shiki span {color: var(--shiki-default);background: var(--shiki-default-bg);font-style: var(--shiki-default-font-style);font-weight: var(--shiki-default-font-weight);text-decoration: var(--shiki-default-text-decoration);}html .dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}html.dark .shiki span {color: var(--shiki-dark);background: var(--shiki-dark-bg);font-style: var(--shiki-dark-font-style);font-weight: var(--shiki-dark-font-weight);text-decoration: var(--shiki-dark-text-decoration);}",{"title":155,"searchDepth":169,"depth":169,"links":490},[491,492,494,495],{"id":31,"depth":169,"text":32},{"id":135,"depth":169,"text":493},"Per-render overrides (brandTweaks)",{"id":247,"depth":169,"text":248},{"id":407,"depth":169,"text":408},"Brand kits as structured tokens — colors, logos, typography — bound into templates and overridable per render with brandTweaks.","md",{"layout":499,"updatedAt":500},"docs","2026-07-06",true,"\u002Fdocs\u002Fbrands",{"title":6,"description":496},"docs\u002Fbrands","mvXLovo5GTZBcKj9pa1erSRnew6Vi70JAZg-WgHcMSM",{"success":501,"routes":507,"total":1003,"generatedAt":1004,"canViewAllApiDocs":580},[508,554,566,622,679,700,721,736,749,761,772,789,816,841,860,872,883,894,903,909,927,938,953,965,978],{"path":509,"method":354,"summary":510,"description":511,"tags":512,"group":513,"requestBody":514,"responses":546,"actionName":553},"\u002Fapi\u002Fcode-to-image","Render code snippets as images","Render source code with syntax highlighting to PNG, WebP, or JPEG. No API token required.",[513],"Rendering",{"content":515},{"application\u002Fjson":516},{"schema":517},{"type":518,"required":519,"properties":520},"object",[24],{"code":521,"lang":524,"theme":526,"format":528,"width":534,"height":537,"quality":539,"showLineNumbers":541,"style":544},{"type":522,"description":523},"string","Source code to render",{"type":522,"description":525},"Language for highlighting (e.g. js, ts). Default: js",{"type":522,"description":527},"Shiki theme. Default: github-dark",{"type":522,"enum":529,"description":533},[530,531,532],"png","webp","jpeg","Output format. Default: png (lossless)",{"type":535,"description":536},"number","Optional width",{"type":535,"description":538},"Optional height",{"type":535,"description":540},"Optional quality",{"type":542,"description":543},"boolean","Show 1-based line numbers in a left gutter. Default: false",{"type":518,"description":545},"Optional style options",{"200":547,"400":549,"500":551},{"description":548},"Image (data URL or binary depending on format)",{"description":550},"Missing or invalid code",{"description":552},"Failed to generate code image","codeToImage",{"path":555,"method":354,"summary":556,"description":557,"tags":558,"group":559,"responses":560,"actionName":565},"\u002Fapi\u002Fdemo-token","Create a demo token","Mint a short-lived, IP-throttled demo token (stored only in Redis, ~1h TTL) that can render PUBLIC templates with tweaks — no account or API key required. Each client IP can mint up to 5 tokens per rolling hour. Use the token as `Authorization: Bearer demo_…` or `?demo=demo_…` against GET \u002Fapi\u002Frender\u002F:pageId.",[559],"Authentication",{"200":561,"429":563},{"description":562},"Demo token created",{"description":564},"Per-IP demo token quota reached","createDemoToken",{"path":567,"method":317,"summary":568,"description":569,"tags":570,"group":513,"parameters":571,"responses":614,"actionName":621},"\u002Fapi\u002Frender\u002F:pageId","Render a page by ID (GET)","Render by page ID with query parameters. Supports draft (database), publish cache, png\u002Fsvg\u002Fwebp\u002Fpdf, JSON or binary responses, tweaks, and brandTweaks — aligned with POST \u002Fapi\u002Frender. Auth depends on template requireGetRenderToken (Bearer or gt query).",[513],[572,577,587,591,597,601,605,609],{"in":573,"name":574,"required":501,"schema":575,"description":576},"path","pageId",{"type":522},"Page ID to render",{"in":578,"name":579,"required":580,"schema":581,"description":586},"query","format",false,{"type":522,"enum":582},[530,583,531,584,585],"svg","pdf","pptx","Output format. Default: png",{"in":578,"name":588,"required":580,"schema":589,"description":590},"draft",{"type":542},"If true, load from database instead of publish cache. Default: false",{"in":578,"name":592,"required":580,"schema":593,"description":596},"output",{"type":522,"enum":594},[154,595],"binary","Response shape: omit or json for metadata + file URL; binary for raw bytes",{"in":578,"name":598,"required":580,"schema":599,"description":600},"pageIds",{"type":522},"Comma-separated page IDs for merged PDF (format=pdf only)",{"in":578,"name":602,"required":580,"schema":603,"description":604},"gt",{"type":522},"GET render secret when Bearer is not used",{"in":578,"name":606,"required":580,"schema":607,"description":608},"scale",{"type":535,"minimum":162,"maximum":199},"Output resolution multiplier for png\u002Fwebp. Overrides the template's renderScale. Default 2.",{"in":578,"name":610,"required":580,"schema":611,"description":613},"quality",{"type":535,"minimum":162,"maximum":612},100,"WebP encode quality (webp only). Overrides the template's webpQuality. Default 90.",{"200":615,"401":617,"404":619},{"description":616},"Binary image\u002FPDF or application\u002Fjson with file metadata",{"description":618},"Missing or invalid API token",{"description":620},"Page or template not found","renderPage",{"path":623,"method":354,"summary":624,"description":625,"tags":626,"group":513,"requestBody":627,"responses":671,"actionName":678},"\u002Fapi\u002Frender\u002Findex","Render by page ID","Render a page by ID from the publish cache, or from the database when draft: true. Requires API token. Does not accept full inline page payloads. Optional body field renderType (satori, takumi, html) overrides the template's rendererType. Use format pdf for the HTML + Chrome PDF pipeline (always uses the HTML renderer). For multi-page PDFs, send pageIds and optional tweaksPerPage (same length). Default response is application\u002Fjson with timings and a URL to the uploaded render; set output to binary (or binary: true) to return raw bytes.",[513],{"content":628},{"application\u002Fjson":629},{"schema":630},{"type":518,"description":631,"properties":632},"For raster formats use pageId. For PDF use pageId (single) or pageIds (merged in order).",{"pageId":633,"pageIds":635,"tweaksPerPage":639,"templateId":642,"draft":644,"format":646,"tweaks":650,"brandTweaks":652,"emojiType":654,"output":656,"binary":661,"renderType":663,"scale":668,"quality":670},{"type":522,"description":634},"Page ID to render (required for png\u002Fsvg\u002Fwebp; optional for pdf when pageIds is set)",{"type":636,"items":637,"description":638},"array",{"type":522},"Multiple pages for merged PDF (format pdf only)",{"type":636,"items":640,"description":641},{"type":518},"Per-page tweaks aligned with pageIds when rendering PDF",{"type":522,"description":643},"Optional; when set, validated against the page's template (parallel fetch)",{"type":542,"description":645},"If true, load page and template from database instead of publish cache. Default: false",{"type":522,"enum":647,"description":649},[530,583,531,584,585,648],"html5","Output format. Default: png. pdf and pptx use HTML + Chrome; pptx builds an editable slide per page. html5 returns a self-contained HTML5 display-ad ZIP (Google Ads) for a single page.",{"type":518,"description":651},"Variable overrides; keys may use dot paths for nested values. For Variable[] sources, use \"varId.nested.path\" when patching object values.",{"type":518,"description":653},"Brand token overrides by dot path (e.g. logos.icon or brand.logos.icon). Merged into resolved brand tokens before render.",{"type":522,"description":655},"e.g. twemoji, openmoji. Default from template",{"type":522,"enum":657,"description":660},[154,595,658,659],"image","raw","Response shape: omit or json for application\u002Fjson (default); binary, image, or raw for raw body",{"type":542,"description":662},"If true, same as output binary (raw body)",{"type":522,"enum":664,"description":667},[665,666],"takumi","html","Override rendering engine (takumi or html). Ignored when format is pdf (HTML pipeline). Legacy value 'satori' is accepted and treated as 'takumi'.",{"type":535,"minimum":162,"maximum":199,"description":669},"Output resolution multiplier for png\u002Fwebp (logical layout unchanged, pixels multiplied). Overrides the template's renderScale. Default 2.",{"type":535,"minimum":162,"maximum":612,"description":613},{"200":672,"400":674,"401":676,"404":677},{"description":673},"Default: application\u002Fjson with render metadata and file.url. With output binary: image\u002Fpng, image\u002Fsvg+xml, image\u002Fwebp, or application\u002Fpdf.",{"description":675},"Invalid body (e.g. missing pageId)",{"description":618},{"description":620},"render",{"path":680,"method":317,"summary":681,"description":682,"tags":683,"parameters":684,"responses":694,"actionName":699},"\u002Fapi\u002Frenders\u002Flogs","List render logs","Render request logs for the current space, optionally narrowed to one template. Session-authenticated (dashboard login) — not callable with an API key.",[513],[685,688,691],{"in":578,"name":686,"required":580,"description":687},"templateId","Only logs for this template's pages",{"in":578,"name":689,"required":580,"description":690},"page","Page number",{"in":578,"name":692,"required":580,"description":693},"perPage","Items per page (default 50)",{"200":695,"401":697},{"description":696},"JSON { list, count, pagesCount } of render log entries",{"description":698},"Not logged in","listRenderLogs",{"path":701,"method":317,"summary":702,"description":703,"tags":704,"parameters":706,"responses":717,"actionName":720},"\u002Fapi\u002Ftemplates\u002Fpublic","List public templates","List published community\u002Fgallery templates with their cached pages. No authentication required.",[705],"Templates",[707,710,713,715],{"in":578,"name":708,"required":580,"description":709},"search","Search name + description (max 80 chars)",{"in":578,"name":711,"required":580,"description":712},"category","Category filter, or \"featured\" for the curated list",{"in":578,"name":689,"required":580,"description":714},"Page number (default 1)",{"in":578,"name":692,"required":580,"description":716},"Items per page (max 100)",{"200":718},{"description":719},"JSON { list, count, pagesCount } — templates include their published pages","listPublicTemplates",{"path":722,"method":317,"summary":723,"description":724,"tags":725,"parameters":726,"responses":730,"actionName":735},"\u002Fapi\u002Ftemplates\u002Fpublic\u002F:id","Get a public template","Fetch one published template (with its pages) by ID. Only templates with publicOn are returned; private IDs 404. No authentication required.",[705],[727],{"in":573,"name":728,"required":501,"description":729},"id","Template ID",{"200":731,"404":733},{"description":732},"JSON { doc } — the template including published pages",{"description":734},"Template not found or not public","getPublicTemplateDoc",{"path":340,"method":387,"summary":737,"description":738,"tags":739,"parameters":740,"responses":743,"actionName":748},"Delete a brand","Soft-delete a brand by ID. Session-authenticated (dashboard login; owner\u002Fadmin\u002Feditor).",[6],[741],{"in":573,"name":728,"required":501,"description":742},"Brand ID",{"200":744,"404":746},{"description":745},"JSON { success: true, id }",{"description":747},"Brand not found in your space","deleteBrand",{"path":340,"method":317,"summary":750,"description":751,"tags":752,"parameters":753,"responses":755,"actionName":760},"Get a brand","Fetch one brand by ID. Public brands (publicOn set) need no auth; private brands require a dashboard session in the owning space. For API-key access use the MCP server (get_brand).",[6],[754],{"in":573,"name":728,"required":501,"description":742},{"200":756,"404":758},{"description":757},"JSON { doc } — the brand with its token sets",{"description":759},"Not found or not accessible","getBrand",{"path":340,"method":373,"summary":762,"description":763,"tags":764,"parameters":765,"responses":767,"actionName":771},"Update a brand","Update a brand by ID (same fields as create, all optional). Session-authenticated (dashboard login; owner\u002Fadmin\u002Feditor). For API-key access use the MCP server (update_brand).",[6],[766],{"in":573,"name":728,"required":501,"description":742},{"200":768,"404":770},{"description":769},"JSON { doc } — the updated brand",{"description":747},"updateBrand",{"path":773,"method":317,"summary":774,"description":775,"tags":776,"parameters":777,"responses":783,"actionName":788},"\u002Fapi\u002Fv1\u002Fbrands\u002Findex","List brands","List brands in the current space. Session-authenticated (dashboard login); pass ?public=true to list public brands anonymously. For API-key access use the MCP server (list_brands).",[6],[778,779,780],{"in":578,"name":689,"required":580,"description":714},{"in":578,"name":692,"required":580,"description":693},{"in":578,"name":781,"required":580,"description":782},"public","\"true\" to list public brands without auth",{"200":784,"401":786},{"description":785},"JSON { list, count, pagesCount } of brands",{"description":787},"Not logged in (when public is not set)","listBrands",{"path":773,"method":354,"summary":790,"description":791,"tags":792,"requestBody":793,"responses":811,"actionName":815},"Create a brand","Create a brand in the current space. Session-authenticated (dashboard login; owner\u002Fadmin\u002Feditor). External image URLs inside tokens are re-uploaded to your space. For API-key access use the MCP server (create_brand).",[6],{"content":794},{"application\u002Fjson":795},{"schema":796},{"type":518,"required":797,"properties":798},[432],{"name":799,"draftTokens":801,"liveTokens":803,"tokens":805,"variants":807,"extra":809},{"type":522,"description":800},"Brand name",{"type":518,"description":802},"Token kit being edited (logos, colors, typography, …)",{"type":518,"description":804},"Token kit used by published renders",{"type":518,"description":806},"Resolved token set",{"type":518,"description":808},"Named variations of the kit",{"type":518,"description":810},"Free-form extras",{"200":812,"401":814},{"description":813},"JSON { doc } — the created brand",{"description":698},"createBrand",{"path":817,"method":317,"summary":818,"description":819,"tags":820,"group":821,"parameters":822,"responses":834,"actionName":840},"\u002Fapi\u002Fv1\u002Fpublic\u002Fcontent\u002F:collection\u002F:slug","Get an entry","Read a single PUBLISHED entry by slug. Authenticate with a content.read API key (Authorization: Bearer …). The slug is matched against the collection's configured preview.slugField (defaults to \"slug\"). Only liveData is returned; use ?depth= to resolve references and ?variants= for personalization.",[821],"Content",[823,826,829,832],{"in":573,"name":824,"required":501,"description":825},"collection","The collection's API name",{"in":573,"name":827,"required":501,"description":828},"slug","The entry slug",{"in":578,"name":830,"required":580,"description":831},"depth","Resolve reference fields to this depth (default 0)",{"in":578,"name":472,"required":580,"description":833},"Comma-separated variant ids; returns personalization-resolved values",{"200":835,"401":837,"404":838},{"description":836},"JSON { doc } — the published entry",{"description":618},{"description":839},"Collection or entry not found","publicGetContentBySlug",{"path":842,"method":317,"summary":843,"description":844,"tags":845,"group":821,"parameters":846,"responses":853,"actionName":859},"\u002Fapi\u002Fv1\u002Fpublic\u002Fcontent\u002F:collection\u002Findex","List entries","List PUBLISHED entries in a collection. Authenticate with a content.read API key (Authorization: Bearer …). Only liveData is returned — never drafts. Values under `data` are keyed by field API name. Supports pagination, reference resolution (?depth=), and personalization (?variants=).",[821],[847,848,849,851,852],{"in":573,"name":824,"required":501,"description":825},{"in":578,"name":689,"required":580,"description":714},{"in":578,"name":692,"required":580,"description":850},"Items per page (default 20)",{"in":578,"name":830,"required":580,"description":831},{"in":578,"name":472,"required":580,"description":833},{"200":854,"401":856,"404":857},{"description":855},"JSON { list, count, pagesCount } of published entries",{"description":618},{"description":858},"Collection not found","publicListContent",{"path":861,"method":387,"summary":862,"description":863,"tags":864,"responses":866,"actionName":871},"\u002Fapi\u002Fv1\u002Fshaders\u002F:id","Delete a shader","Permanently remove a shader from the current space.",[865],"Shaders",{"200":867,"404":869},{"description":868},"JSON { deleted: true }",{"description":870},"No such shader","deleteShader",{"path":861,"method":317,"summary":873,"description":874,"tags":875,"responses":876,"actionName":882},"Get a shader","Fetch one shader including its vetted `program` — the only source a client should compile. Status is enforced here on every request, which is what makes revoking a working kill switch: a quarantined or revoked shader returns 410 and stops loading everywhere immediately.",[865],{"200":877,"404":879,"410":880},{"description":878},"JSON { doc }",{"description":870},{"description":881},"Shader is quarantined or revoked","getShader",{"path":861,"method":373,"summary":884,"description":885,"tags":886,"responses":887,"actionName":893},"Update a shader","Editing source or the manifest re-runs the full vetting pipeline and produces a new content hash — an existing approval is never inherited by code that was not vetted. A rejected edit returns 422 and leaves the stored shader untouched.",[865],{"200":888,"404":890,"422":891},{"description":889},"JSON { doc, report }",{"description":870},{"description":892},"Rejected by vetting; the stored shader is unchanged","updateShader",{"path":895,"method":354,"summary":896,"description":897,"tags":898,"responses":899,"actionName":902},"\u002Fapi\u002Fv1\u002Fshaders\u002F:id\u002Fstatus","Set a shader status (kill switch)","Revoke, quarantine, or restore a shader. Because GET enforces status on every fetch, revoking stops the shader loading everywhere at once — there is no client deny-list to push and no cache to wait out. Restoring also clears the accumulated watchdog trips.",[865],{"200":900,"404":901},{"description":878},{"description":870},"setShaderStatus",{"path":904,"method":354,"summary":905,"description":906,"tags":907,"actionName":908},"\u002Fapi\u002Fv1\u002Fshaders\u002F:id\u002Ftelemetry","Report a client watchdog trip","Called by a viewer whose frame watchdog disabled this shader. Enough independent trips ",[865],"reportShaderTrip",{"path":910,"method":317,"summary":911,"description":912,"tags":913,"parameters":914,"responses":922,"actionName":926},"\u002Fapi\u002Fv1\u002Fshaders\u002Findex","List shaders","List the current space's shaders. Pass ?public=true to list published shaders anonymously. Program source is omitted from the listing — fetch a single shader to obtain it.",[865],[915,916,917,920],{"in":578,"name":689,"required":580,"description":714},{"in":578,"name":692,"required":580,"description":693},{"in":578,"name":918,"required":580,"description":919},"status","approved | quarantined | revoked",{"in":578,"name":781,"required":580,"description":921},"\"true\" to list public shaders without auth",{"200":923,"401":925},{"description":924},"JSON { list, count, pagesCount }",{"description":787},"listShaders",{"path":910,"method":354,"summary":928,"description":929,"tags":930,"responses":931,"actionName":937},"Create a shader","Submit a GLSL fragment body plus a typed input manifest. The shader is vetted before anything is stored: byte caps, a static policy scan, loop normalisation to constant bounds, a cost model, then a real compile and fuzz render inside a sandboxed child process. A rejected submission returns 422 with the stage-by-stage report and is not saved.",[865],{"200":932,"401":934,"422":935},{"description":933},"JSON { doc, report } — the stored shader and its vetting report",{"description":698},{"description":936},"Rejected by vetting; data.report explains which stage refused","createShader",{"path":939,"method":387,"summary":940,"description":941,"tags":942,"parameters":944,"responses":947,"actionName":952},"\u002Fapi\u002Fv1\u002Ftokens\u002Fapi-keys\u002F:id","Delete an API key","Revoke an API key immediately. Session-authenticated (dashboard login; owner\u002Fadmin).",[943],"Tokens",[945],{"in":573,"name":728,"required":501,"description":946},"Token ID",{"200":948,"404":950},{"description":949},"JSON { message } confirmation",{"description":951},"Token not found in your space","deleteApiKey",{"path":939,"method":954,"summary":955,"description":956,"tags":957,"parameters":958,"responses":960,"actionName":964},"PATCH","Update an API key","Rename, change expiry, or adjust scopes of an API key. Session-authenticated (dashboard login; owner\u002Fadmin).",[943],[959],{"in":573,"name":728,"required":501,"description":946},{"200":961,"404":963},{"description":962},"JSON { doc } — the updated key",{"description":951},"updateApiKey",{"path":966,"method":317,"summary":967,"description":968,"tags":969,"parameters":970,"responses":973,"actionName":977},"\u002Fapi\u002Fv1\u002Ftokens\u002Fapi-keys\u002Findex","List API keys","List API keys for the current space. Session-authenticated (dashboard login; owner\u002Fadmin).",[943],[971,972],{"in":578,"name":689,"required":580,"description":714},{"in":578,"name":692,"required":580,"description":850},{"200":974,"401":976},{"description":975},"JSON { list, count, pagesCount } of API keys",{"description":698},"listApiKeys",{"path":966,"method":354,"summary":979,"description":980,"tags":981,"requestBody":982,"responses":998,"actionName":1002},"Create an API key","Create a space-scoped API key. The plain token is returned once, on creation. Session-authenticated (dashboard login; owner\u002Fadmin).",[943],{"content":983},{"application\u002Fjson":984},{"schema":985},{"type":518,"required":986,"properties":987},[432],{"name":988,"expiresAt":990,"neverExpires":992,"shortToken":994,"scopes":996},{"type":522,"description":989},"Key name (max 200 chars)",{"type":522,"description":991},"ISO datetime expiry",{"type":542,"description":993},"No expiry. Default: false",{"type":542,"description":995},"Shorter ~96-bit token instead of ~256-bit. Default: false",{"type":518,"description":997},"Optional restrictions: { mcpTools?: string[], apiEndpoints?: string[] }. Omit a list to allow all; [] denies all.",{"200":999,"401":1001},{"description":1000},"JSON { doc } including the plain token (shown only once)",{"description":698},"createApiKey",25,"2026-08-19T19:21:11.342Z",1787167272953]