From fd241f70cf46e7f6701ea8d449d7f46adbeec4a3 Mon Sep 17 00:00:00 2001 From: Emmanuel Ruiz Date: Sat, 10 Oct 2026 21:50:13 -0400 Subject: [PATCH 1/2] fix(siteImport): rewrite var() references to the slug a colour token is emitted under Site Import turned root colour custom properties into framework tokens, which the framework emits under the normalised slug (`--brand---neutral--700` -> `--brand-neutral-700`), but left the imported `var()` references on the authored name, so they no longer resolved. The slug is now settled at plan time by `normalizeImportedColorTokens`, and every changed name is rewritten in the imported style rules and node inline styles before conflict detection, so the conflict step and the commit see the emitted name. Two names that normalise to the same slug both survive with a numeric suffix instead of one being dropped at commit. Token renames (normalisation and conflict renames) now also rename declarations of the variable in other rules, their priorities, and raw @keyframes CSS, so a `.dark { --bg: ... }` override follows its token. Conflict rename targets skip the import's other token names and any custom property the imported CSS declares, and a colour custom rename is normalised like the slug it becomes. The rename helpers move from conflicts.ts into siteImport/varRefs.ts, which keeps conflicts.ts under the 700-line module budget. Fixes #615 --- docs/features/site-import.md | 7 +- src/__tests__/siteImport/applyImport.test.ts | 37 +++++ src/__tests__/siteImport/colorTokens.test.ts | 49 +++++- src/__tests__/siteImport/conflicts.test.ts | 118 +++++++++++++- src/core/siteImport/buildPlan.ts | 30 +++- src/core/siteImport/colorTokens.ts | 52 +++++++ src/core/siteImport/conflicts.ts | 117 ++++++-------- src/core/siteImport/index.ts | 2 +- src/core/siteImport/varRefs.ts | 154 +++++++++++++++++++ 9 files changed, 481 insertions(+), 85 deletions(-) create mode 100644 src/core/siteImport/varRefs.ts diff --git a/docs/features/site-import.md b/docs/features/site-import.md index de6093e12..f22ce4456 100644 --- a/docs/features/site-import.md +++ b/docs/features/site-import.md @@ -15,7 +15,7 @@ CSS declarations containing `var()`, `env()`, `clamp()`, `min()`, or `max()` pas - **Per-stylesheet import modes:** each top-level linked stylesheet either converts to editable style rules (default) or imports verbatim as a page-scoped `SiteFile` stylesheet (`options.stylesheetModes`, picked in the Review step). There are no generated scope classes — page isolation comes from the kept file's runtime scope. - `commitImportPlan(plan, adapter)` — uploads assets, then wraps all store writes in a single `adapter.commit` call → one Cmd+Z reverts the whole import. - Static imports load the current CMS draft into the editor store on demand when launched outside `/admin/site`; if no draft exists, the modal creates an empty site before analysis. -- Conflict resolution: rename with a numeric suffix (default), overwrite, skip, or custom-rename — per page slug, per class name, per design token (colour / font CSS variable), and per divergent cross-stylesheet class definition, with category-level bulk actions. Token renames rewrite `var(--x)` references so imports stay faithful. +- Conflict resolution: rename with a numeric suffix (default), overwrite, skip, or custom-rename — per page slug, per class name, per design token (colour / font CSS variable), and per divergent cross-stylesheet class definition, with category-level bulk actions. Token renames rewrite `var(--x)` references, and declarations of the same variable in other rules, so imports stay faithful. - What imports: pages, linked CSS plus unconditional local CSS `@import` graphs, `kind:'class'` and `kind:'ambient'` style rules, stylesheets kept as page-scoped files, `@keyframes`, uploadable media/font files, root CSS color tokens, root CSS font tokens, `@font-face` families, known external font stylesheet imports, safe extra HTML attributes on base modules, body-level classes/attributes/style metadata, bare DOM text nodes in mixed content, and executable HTML scripts as page-scoped runtime scripts. Module-script imports from known npm CDNs are rewritten to bare package imports and added to the site dependency manifest. - CMS bundle import preserves selected exported tables, rows, optional site shell, media, folders, and redirects using the same merge strategies as site transfer (`replace`, `merge-add`, `merge-overwrite`). - HTML forms import through the shared HTML importer as first-class form primitives (`base.form`, controls, labels, submit buttons), not as custom containers. @@ -46,6 +46,7 @@ src/core/siteImport/ ├── applyAssetRewrites.ts — patch fragment props + CSS/@keyframes url() with new media URLs (post-upload) ├── linkRewrite.ts — rewrite intra-site to cms:page: refs ├── conflicts.ts — detect page-slug + class-name + design-token collisions; apply resolutions (incl. var(--x) rewrites) +├── varRefs.ts — rename a custom property across imported rules, inline styles and @keyframes (var(--x) refs + --x declarations) ├── adapter.ts — SiteImportAdapter + SiteImportTransaction interfaces (the ONE transaction contract; the editor store implements it directly) ├── paths.ts — dirname/joinPaths for FileMap-relative path resolution ├── planCss.ts — single CSS-source parse path (external sheets + per-page inline