Self-hosted: theme manifests so a template can own its layout - #1442
Conversation
No component read general.styleTemplate: every template rendered the
identical tree and differed only through CSS custom properties. Themes
are now code-level manifests ({ id, tier, components? }) over named
seams (Shell, Navigation, Sidebar, ArchiveList, PostCard), resolved
reactively through useThemeComponents so the editor's config-store
preview restructures live and exiting preview restores the baseline.
The five existing templates migrate as manifests with NO components
key: resolution falls back to the shared defaults, which are exactly
the components the shell hardcoded before, so rendering is unchanged
by construction and the registry test pins the no-op (every roster id
present, no overrides, unknown ids resolving like apply-config-dom
does). BlogLayout becomes the Shell resolver; the previous frame moves
to DefaultShell, which itself resolves Navigation and Sidebar through
the registry so a theme can replace either without owning the frame.
Sidebar placement and visibility stay pure CSS via the existing
attribute contract; route topology stays global, so layout variants
render inside existing routes and deep links never fork per theme.
Closes #1418
Code Review by Qodo
1.
|
|
Warning Review limit reached
Next review available in: 32 minutes You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (9)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
PR Summary by QodoSelf-hosted: add theme manifests and seam-based component resolution
AI Description
Diagram
High-Level Assessment
Files changed (8)
|
Code Review by Qodo
1.
|
Review follow-up: extract the pure half of useThemeComponents so the resolution is testable without rendering, and pin per-seam IDENTITY for every roster template: the no-op migration means the very same component functions render, so nothing remounts.
The identity test imports the real default components, whose chain touches @ecency/ui; vitest had no resolution for it. Mirror the rsbuild alias to the committed dist, exactly what the shipped bundle uses.
Closes #1418. Independent of the signup chain (base develop); pairs with the merged #1436, whose config-store preview is what lets a structural theme preview correctly.
No component read
general.styleTemplate: all five templates rendered the identical component tree and differed only through CSS custom properties, which caps how different two templates can look. This introduces the architecture that lifts that cap without changing a rendered byte today:src/themes/manifest.tsdefines a theme as{ id, tier, components? }over five named seams: Shell (the page frame), Navigation, Sidebar, ArchiveList (the feed container) and PostCard. Absent entries fall back to shared defaults.src/themes/registry.tsholds one manifest per roster id. All five existing templates carry NO components key: they are CSS-only, so resolution falls back to exactly the components the shell used to hardcode. The registry test pins this no-op (registry total over the roster, no overrides, unknown ids resolving to the default the same wayapply-config-domresolves the attribute).useThemeComponentsresolves the active template's components reactively through the config store, so the Configuration Editor's preview restructures live and exiting preview restores the baseline components.BlogLayoutbecomes the Shell resolver; the previous frame moves toDefaultShell, which itself resolves Navigation and Sidebar through the registry, so a theme can replace the masthead or the rail without owning the whole frame. The feed resolves ArchiveList and PostCard the same way.--theme-*token contract stays mandatory per theme and route topology stays global so deep links never fork per theme.Deliberately deferred: an EmptyState seam and per-theme option sets (#1419) join when the first layout-level theme (Journal, #1420) actually needs them; the search results card call site joins the PostCard seam at the same time.
tieris carried but not yet enforced; server-side enforcement lands with the first premium theme (#1421).SPA 882 tests, typecheck and production build green.