Construire un site d'annuaire semble trivial jusqu'à ce que vous vous retrouviez à devoir connecter des bases de données, des couches de mise en cache et des frameworks front-end réactifs juste pour afficher ce qui n'est, au fond, qu'une table des matières organisée. J'ai récemment créé Social Tools List, un site de comparaison de logiciels de médias sociaux. Mon objectif était de le mettre en ligne rapidement, de le maintenir rapide et d'éviter la maintenance d'une infrastructure pour un contenu qui ne change que lorsque j'ajoute ou mets à jour un outil. J'ai opté pour une pile "static-first" : Astro pour la génération du site, TypeScript pour les données structurées et Cloudflare Workers pour le déploiement. Le résultat est un site qui se charge instantanément, ne coûte presque rien en hébergement et ne nécessite aucune administration de base de données.

Pourquoi l'approche "static-first" est pertinente pour un annuaire

De nombreuses applications web optent par défaut pour le rendu côté serveur ou des architectures de type "single-page" car elles semblent être des choix sûrs et modernes. Mais tous les sites ne reçoivent pas d'entrées utilisateur dynamiques à chaque requête. Social Tools List est une ressource à forte intensité de lecture. Les données de comparaison changent lorsque je pousse une mise à jour, pas lorsqu'un visiteur actualise la page. Le rendu HTML anticipé élimine le besoin de requêtes de base de données à la périphérie (edge), de compilation de modèles à la volée ou de la surcharge d'hydratation dans le navigateur. Je génère le site au moment du build, je déploie les fichiers statiques et je laisse un worker léger gérer l'enveloppe. Cela permet de maintenir des temps de réponse faibles et d'éliminer toute une classe d'erreurs d'exécution (runtime).

Stocker les données dans TypeScript, pas dans une base de données

Je n'utilise pas de base de données. Chaque outil de l'annuaire est défini comme un objet TypeScript avec un slug, un nom, un domaine et un tableau de workflows pris en charge. Une entrée typique ressemble à ceci :

{
  slug: 'buffer',
  name: 'Buffer',
  domain: 'buffer.com',
  workflows: ['scheduling', 'analytics']
}

Stocker les données dans le même langage que celui utilisé pour construire le site présente deux avantages immédiats. Premièrement, les pull requests deviennent des revues de contenu. Lorsque j'ajoute un outil, le diff montre les champs et les valeurs exacts, et un collaborateur peut repérer une faute de frappe ou un mauvais domaine sans avoir à apprendre l'interface d'un CMS. Deuxièmement, le compilateur TypeScript impose la structure de chaque enregistrement. Si j'oublie d'inclure un slug ou si je fais une faute d'orthographe dans une clé de workflow, le build échoue avant même que les données erronées n'atteignent une page.

Une base de données introduirait des migrations, des chaînes de connexion, des stratégies de mise en cache et des routines de sauvegarde. Pour un annuaire de quelques centaines d'entrées que je gère manuellement, cette surcharge est un pur frein. Les données statiques dans des modules TypeScript constituent le choix le plus économique et le plus correct pour ce modèle. Le terme "correct" est important. Il ne s'agit pas seulement d'économiser de l'argent, mais de supprimer des couches d'abstraction qui résolvent des problèmes que je n'ai pas.

Laisser Astro gérer le routage et le rendu

Astro génère une page HTML par outil à partir d'une seule route dynamique. Je définis un composant de mise en page (layout), et Astro génère automatiquement les métadonnées, les titres et les données structurées pour chaque entrée. Comme le même jeu de données alimente l'index principal, les hubs de catégories de workflows et les pages de détails individuelles, il n'y a aucun risque qu'une carte sur la page d'accueil affiche une description différente de celle de la page de détails elle-même. Dans les configurations CMS traditionnelles, on observe souvent un décalage : l'API renvoie une version, le cache une autre, et le rendu côté client une troisième. La génération statique à partir d'une source unique de vérité (single source of truth) empêche cela.

L'architecture "islands" d'Astro permet également d'ajouter facilement de petits éléments interactifs sans polluer toute la page avec du JavaScript. Le site est livré en HTML statique, et seul le script de filtrage hydrate sa partie spécifique du DOM. Il n'y a pas d'environnement d'exécution (runtime) de framework qui enveloppe l'ensemble du document. Astro traite également les métadonnées de page comme une priorité de premier ordre. Chaque page d'outil possède sa propre balise title et sa propre méta description dérivées directement de l'enregistrement TypeScript, je n'ai donc pas besoin d'un plugin séparé ou d'une bibliothèque de gestion du head.

Filtrer sans framework

La recherche et le filtrage poussent souvent les développeurs à installer React, Vue ou une lourde bibliothèque de gestion d'état. J'y ai résisté. Astro rend la liste complète en HTML pur sur le serveur. Un petit script en JavaScript pur (vanilla), de moins d'un kilo-octet, s'exécute dans le navigateur et bascule la propriété d'affichage (display) des éléments de la liste en fonction d'une étiquette de workflow ou d'une correspondance textuelle.

Serving the complete markup sounds inefficient if you come from an API-driven background. But consider the overhead of a typical dynamic approach. The browser downloads a JavaScript bundle, hydrates a component tree, calls an endpoint, waits for JSON, and then renders rows. For a directory that lists fewer than one hundred tools, that ritual is slower and less reliable than hiding divs that are already in the document. My script attaches event listeners to filter buttons, reads a data-workflow attribute on each row, and sets non-matches to hidden. The operation takes milliseconds.

Because the list is present in the initial HTML, the site is usable without JavaScript. Search engine crawlers see every link and every description. Users on slow networks or with script blockers still get the full directory. The filtering is an enhancement, not a gate.

Sitemaps and Robots as Code

Sitemaps and robots.txt are not afterthoughts written by hand. They are Astro routes that consume the same dataset and URL helpers as