// Generates src/styles/tokens.gen.css from the hub frontend's design tokens. // // The hub's Tailwind entry (internal/webapp/frontend/src/tw.css) is the single // source of truth for the BearDrive palette. It can't be imported directly: // `@theme { … }` is Tailwind syntax, and this site deliberately doesn't run // Tailwind. So we read that one block and re-emit it as plain custom // properties on :root. // // This is why the docs site lives in the OSS repo. The cloud landing page sits // in a different Go module and has to keep a *copy* of these tokens, policed by // cloud/web/landing/scripts/check-tokens.mjs. Here there is no copy to police — // the file below is generated, gitignored, and cannot drift. import { readFileSync, writeFileSync, mkdirSync } from "node:fs"; import { fileURLToPath } from "node:url"; import { dirname, resolve, relative } from "node:path"; const here = dirname(fileURLToPath(import.meta.url)); const SOURCE = resolve(here, "../../../internal/webapp/frontend/src/tw.css"); const OUT = resolve(here, "../src/styles/tokens.gen.css"); const src = readFileSync(SOURCE, "utf8"); const block = src.match(/@theme\s*\{([\s\S]*?)\n\}/); if (!block) { throw new Error(`no @theme block found in ${SOURCE}`); } // Declarations only — comments and blank lines don't survive the trip. const decls = block[1] .split("\n") .map((line) => line.trim()) .filter((line) => line.startsWith("--")) .map((line) => ` ${line}`); if (decls.length === 0) { throw new Error(`@theme block in ${SOURCE} declared no custom properties`); } mkdirSync(dirname(OUT), { recursive: true }); writeFileSync( OUT, [ `/* GENERATED by scripts/tokens.mjs from ${relative(resolve(here, "../../.."), SOURCE)} — do not edit. */`, ":root {", ...decls, "}", "", ].join("\n"), ); console.log(`tokens: wrote ${decls.length} properties to src/styles/tokens.gen.css`);