Créer des thèmes — vue d'ensemble

Un thème contrôle l'apparence de votre site public : couleurs, typographie, mise en page, le markup de chaque page publiée. Les thèmes Flexweg CMS sont des composants React rendus en HTML au moment

Un thème contrôle l'apparence de votre site public : couleurs, typographie, mise en page, le markup de chaque page publiée. Les thèmes Flexweg CMS sont des composants React rendus en HTML au moment de la publication — vous écrivez du JSX, le publisher appelle react-dom/server.renderToStaticMarkup() dans le navigateur de l'admin, et la chaîne résultante est uploadée sur Flexweg.

Les thèmes peuvent être livrés en :

  • Thème in-tree — un dossier sous src/themes/ bundlé dans l'admin aux côtés des intégrés. Mieux quand vous maintenez votre propre fork de l'admin.
  • Thème externe — un ZIP avec un bundle ESM pré-compilé, installé au runtime via le bouton Install theme. Mieux quand vous voulez distribuer des thèmes indépendamment des releases admin.

Les deux partagent le même shape de manifest et la même API runtime. Cette section parcourt le chemin in-tree d'abord (plus simple pour développer), puis couvre ce qui diffère pour les thèmes externes.

Ce qu'est un thème, structurellement

src/themes/<id>/
├── manifest.ts (ou .tsx)     ← export default le ThemeManifest
├── style.ts (ou compileCss)   ← optionnel, transformation de la CSS
├── theme.css / theme.scss     ← styles importés via ?inline
├── tailwind.config.cjs        ← si pipeline Tailwind
├── i18n.ts                    ← bundles { en, fr, ... }
├── SettingsPage.tsx           ← optionnel, page de réglages
├── templates/
│   ├── BaseLayout.tsx         ← contient les sentinels (CRITIQUE)
│   ├── HomeTemplate.tsx
│   ├── SingleTemplate.tsx
│   ├── CategoryTemplate.tsx
│   ├── AuthorTemplate.tsx
│   └── NotFoundTemplate.tsx
├── components/                ← sous-composants partagés
└── blocks/                    ← optionnel, blocs de thème

Les six templates obligatoires

Chaque thème déclare exactement six templates :

Template Quand est-il rendu
base Le wrapper HTML autour de tout. <html>, <head>, <body>. Contient les sentinels que les plugins remplacent.
home /index.html (en mode latest-posts). Pas utilisé en mode static-page (SingleTemplate est utilisé à la place).
single Chaque post / page publié individuellement.
category Chaque archive de catégorie (<slug>/index.html).
author Chaque page d'auteur (/authors/<uid>.html).
notFound /404.html.

Le BaseLayout, c'est critique

Le BaseLayout enveloppe les autres templates. Il contient :

  • <html>, <head>, <body> structure

  • Les balises meta SEO (<title>, <meta description>, og:image, etc.)

  • Le wordmark / logo du header

  • Les containers [data-cms-menu="header"] / [data-cms-menu="footer"] pour les menus dynamiques

  • Le lien <link rel="stylesheet" href="/theme-assets/<id>.css">

  • Les deux sentinels obligatoires :

    • <meta name="x-cms-head-extra" /> — remplacée par les filtres page.head.extra
    • <script type="application/x-cms-body-end" /> — remplacée par les filtres page.body.end

Sans ces deux sentinels, les plugins comme core-seo, flexweg-favicon, flexweg-custom-code et flexweg-rss ne fonctionnent pas.

TSX
export function BaseLayout({ site, pageTitle, pageDescription, ogImage, currentPath, children }) {
  const lang = site.settings.language ?? "en";
  return (
    <html lang={lang}>
      <head>
        <meta charSet="utf-8" />
        <meta name="viewport" content="width=device-width, initial-scale=1" />
        <title>{pageTitle}</title>
        {pageDescription && <meta name="description" content={pageDescription} />}
        {ogImage && <meta property="og:image" content={ogImage} />}
        <link rel="stylesheet" href={site.themeCssPath} />
        {/* OBLIGATOIRE */}
        <meta name="x-cms-head-extra" />
      </head>
      <body>
        {children}
        {/* OBLIGATOIRE */}
        <script type="application/x-cms-body-end" />
      </body>
    </html>
  );
}

Les templates reçoivent des props serializables

Les composants de thème doivent être des consumers de props purs / serializables — pas de hooks Firestore, pas de context admin. Le publisher résout les URLs, les MediaView shapes, les ResolvedMenuItem, etc. avant de rendre.

Voir Templates et props pour ce que reçoit chaque template.

CSS — deux pipelines au choix

  • SCSS : theme.scss importé via ?inline. Vite compile au build. Voir Pipelines CSS.
  • Tailwind : theme.css + tailwind.config.cjs. Le script build-theme-tailwind.mjs tourne avant Vite.

Dans les deux cas, manifest.cssText est le résultat final que l'admin upload sur Flexweg à theme-assets/<id>.css. Si votre thème a une page de réglages avec overrides de palette / polices, exposez compileCss(config) qui transforme cssText en CSS finale baked.

Prochaines étapes