Il y a deux façons de rater l'architecture du contenu et la plupart des projets en choisissent une. D'un côté, les puristes du tout-dans-Git, pour qui corriger une coquille signifie une branche, une pull request et un déploiement complet. De l'autre, ceux qui décident que le CMS devrait tout contenir — chaînes d'interface, configuration de mise en page, design tokens, tout — jusqu'à ce que le site ne puisse plus afficher un bouton sans un aller-retour réseau. J'ai construit mon portfolio et ce blog sur la même couche de contenu, et la seule chose qui a tenu, c'est une frontière stricte entre les deux.
Au début, tout ce que je construisais vivait dans des fichiers du dépôt — INI, puis JSON —, tout versionné et entièrement sous ma main. C'était simple jusqu'à ce que ça ne le soit plus. Le jour où l'on veut corriger une phrase depuis son téléphone, ou publier une pensée sans ouvrir d'éditeur, le contenu uniquement-en-fichiers devient un mur. Forcer un déploiement pour déplacer une virgule, c'est gâcher un déploiement.
Alors la première fois que j'ai pris un CMS headless, j'ai sur-corrigé et j'y ai tout mis — libellés d'UI, réglages de thème, état des composants —, dans des tables distantes à côté du texte réel. Cela échange un mode de défaillance contre un pire. Maintenant le chrome de l'interface arrive par le réseau, l'internationalisation devient un appel d'API, et un hoquet du CMS peut faire tomber une page qui n'a aucune raison de dépendre du CMS. La réponse n'a jamais été un côté ou l'autre. C'est un contrat entre ce qui change au quotidien et ce qui définit le système.
Le CMS reçoit le contenu narratif et mutable, et rien d'autre — les choses qui grandissent et changent sans que personne ait besoin de refactoriser. Sur ce blog, c'est chaque article, extrait et sujet : j'écris et je publie depuis un écran d'administration sans toucher au code source. Sur le portfolio, ce sont les études de cas, les jalons, les compétences ; terminer un contrat est une modification de contenu, pas une release. C'est aussi le bon foyer pour les quelques réglages globaux qui doivent changer sans déploiement : une annonce, les métadonnées de l'auteur, un feature flag. Si je peux le rédiger, le réviser ou le supprimer sur un coup de tête, sa place est dans la base de données.
Tout ce qui décide du comportement de l'application, ou qui a besoin que le compilateur le vérifie, reste dans le code. Le dictionnaire d'interface est le cas le plus clair : les deux sites sont localisés en six langues, mais les libellés de navigation, les textes de boutons, les placeholders et les aria-labels vivent dans du JSON typé dans le dépôt, parce que les chercher dans un CMS ajouterait de la latence au rendu de la structure et risquerait une clé manquante en pleine hydratation. Même chose pour les règles de routage, la configuration des thèmes, les durées d'animation, les schémas de validation : ils veulent une vérification à la compilation, pas une ligne de base de données. Et les ressources statiques : images, icônes et vignettes appartiennent au projet, où le build peut les optimiser et le cache peut leur faire confiance, sans aller-retour média vers le CMS dans le chemin de rendu.
Certaines choses n'entrent dans aucune boîte. Commentaires, likes, compteurs de vues, registres de limitation de débit, sessions — à haute fréquence, transactionnels, exigeant une vraie intégrité — n'ont leur place ni dans un CMS conçu pour la rédaction, ni dans des fichiers reconstruits à chaque déploiement. Les fils de commentaires ont besoin de réponses, de vérifications d'authentification, de modération. Un compteur de likes écraserait une reconstruction statique et ramperait à travers une API d'écriture de CMS. Les limites de débit et les journaux d'accès ont besoin d'une vraie base de données faisant un vrai travail en temps réel. C'est un troisième magasin, et prétendre que c'est l'un des deux autres, c'est ainsi qu'on se retrouve avec une version lente et fragile des deux.
Les histoires vont dans le CMS. La structure va dans le code. Tout ce qui compte, s'incrémente ou limite va dans une base de données qui ne fait rien de tout cela.
L'architecture est surtout l'acte de tracer des lignes puis de refuser de les déplacer par confort. Le contenu et le code ont des cycles de vie différents ; dès qu'on cesse de prétendre le contraire, les outils cessent de se battre contre nous. Le CMS me laisse publier de n'importe où. Le dépôt garde les parties qui doivent être justes à la compilation réellement justes à la compilation. La frontière entre les deux est la seule raison pour laquelle l'un comme l'autre sont agréables à utiliser.
Les fondations sont posées ; maintenant, il faut construire.