Blog moderne propulsé par Next.js 15 et WordPress en mode Headless CMS via WPGraphQL. Design minimaliste avec mode sombre, interface ShadCN UI et configuration centralisée dans WordPress.
- Framework : Next.js 16 (App Router) avec Turbopack
- Langage : TypeScript 5
- Styling : Tailwind CSS v4
- UI Components : ShadCN UI (Radix UI primitives)
- Animations : Motion (Framer Motion)
- Icons : Lucide React
- Font : DM Sans (Google Fonts)
npm installCréer un fichier .env.local à la racine du projet :
# WordPress GraphQL API URL
# Cette URL est utilisée pour :
# - Les requêtes GraphQL vers WordPress
# - Autoriser automatiquement les images provenant de ce domaine
NEXT_PUBLIC_WORDPRESS_API_URL=https://your-wordpress-site.com/graphql
# Site URL (pour SEO, sitemap, RSS, etc.)
NEXT_PUBLIC_SITE_URL=http://localhost:3000
# GitHub Token (Optionnel - recommandé pour éviter les erreurs 403)
# Améliore la limite de rate de l'API GitHub de 60 à 5000 requêtes/heure
# Pour créer un token : https://github.com/settings/tokens
# Permissions : Aucune permission nécessaire (token public read-only)
GITHUB_TOKEN=💡 Configuration automatique des images : Le hostname de
NEXT_PUBLIC_WORDPRESS_API_URLest automatiquement extrait et ajouté àimages.remotePatternsde Next.js pour autoriser le chargement des images WordPress.
⚠️ Prérequis WordPress : Votre instance WordPress doit avoir le plugin WPGraphQL installé et activé.
💡 GitHub Token (Optionnel) : Pour éviter les erreurs 403 lors de l'affichage du nombre d'étoiles GitHub, vous pouvez créer un token personnel sans aucune permission. Cela augmente la limite de 60 à 5000 requêtes/heure. Sans token, un système de cache en mémoire limite les appels à l'API.
npm run devLe site sera accessible sur http://localhost:3000
npm run build
npm start- ✅ Configuration centralisée dans WordPress (titre, description, URL)
- ✅ Multi-catégories par article avec filtres dynamiques
- ✅ Recherche instantanée (
Ctrl+K/Cmd+K) en temps réel - ✅ Navigation précédent/suivant entre articles
- ✅ Breadcrumb SEO avec Schema.org JSON-LD
- ✅ Flux RSS & Sitemap XML dynamiques
- ✅ Table des matières interactive avec scroll spy
- ✅ Mode sombre/clair avec persistance localStorage
- ✅ Sidebar responsive (TOC + partage social)
- ✅ Barre de progression de lecture
- ✅ Design minimaliste et épuré
- ✅ Animations fluides avec Motion
- ✅ Rendu HTML WordPress avec sanitization
- ✅ Coloration syntaxique des blocs de code (Shiki)
- ✅ Images optimisées avec Next.js Image
- ✅ Temps de lecture estimé
- ✅ Partage social (X, LinkedIn, WhatsApp, Email)
- ✅ Support Markdown enrichi
- ✅ Open Graph & Twitter Cards
- ✅ ISR (Incremental Static Regeneration)
- ✅ Metadata dynamiques depuis WordPress
- ✅ Sitemap XML automatique
- ✅ robots.txt configuré
- ✅ Accessibilité (skip links, ARIA labels)
- ✅ Formulaire de contact
- ✅ Page À propos
- ✅ Bouton vers le repo Github (avec étoiles dynamiques)
- ✅ Support React 19
Le frontend récupère dynamiquement les données suivantes depuis WordPress via WPGraphQL :
Récupérée via getGeneralSettings() :
Champs disponibles :
title: Titre du site (ex: "Mon Blog")description: Description du site pour le SEOurl: URL racine du site WordPress
Utilisée dans :
- Métadonnées SEO (
layout.tsx) - Flux RSS (
rss.xml/route.ts) - Footer (
footer.tsx) - Navbar (
navbar.tsx)
Récupérés via getAllPosts(), getPostBySlug(), getPaginatedPosts(), searchPosts() :
Champs de base :
id: Identifiant unique GraphQLdatabaseId: ID numérique dans la base de donnéestitle: Titre de l'articleslug: Slug URL-friendly (ex: "mon-article")date: Date de publication (ISO 8601)excerpt: Extrait/résumé de l'article (HTML)content: Contenu complet de l'article (HTML)
Image à la une (featuredImage) :
sourceUrl: URL de l'imagealtText: Texte alternatif pour l'accessibilité
Auteur (author.node) :
name: Nom complet de l'auteuravatar.url: URL de l'avatar Gravatar
Catégories (categories.nodes[]) :
name: Nom de la catégorie (ex: "Technologie")slug: Slug de la catégorie (ex: "technologie")
Récupérées via getAllCategories() :
id: Identifiant unique GraphQLdatabaseId: ID numériquename: Nom de la catégorieslug: Slug URLcount: Nombre d'articles dans cette catégorie
Récupération des articles adjacents via getAdjacentPosts(slug) :
previousPost: Article précédent ({ slug, title })nextPost: Article suivant ({ slug, title })
| Composant/Page | Données WordPress utilisées |
|---|---|
layout.tsx |
GeneralSettings (title, description, url) |
page.tsx (accueil) |
Liste des 6 articles les plus récents |
blog/page.tsx |
Tous les articles + catégories pour filtres |
blog/[slug]/page.tsx |
Article complet avec auteur, catégories, image |
navbar.tsx |
Titre du site depuis GeneralSettings |
footer.tsx |
Titre du site depuis GeneralSettings |
rss.xml/route.ts |
Articles + métadonnées du site |
sitemap.ts |
Tous les slugs d'articles |
search-dialog.tsx |
Recherche d'articles via searchPosts() |
article-navigation.tsx |
Articles précédent/suivant |
blog-list.tsx |
Articles paginés avec filtres catégorie |
Pour que le frontend fonctionne correctement, assurez-vous que WordPress est configuré avec :
- Installer et activer le plugin WPGraphQL (version 1.13+ recommandée)
- Accessible depuis WordPress Admin → Extensions → Ajouter
- Vérifier que l'endpoint
/graphqlest accessible
Remplir dans Réglages → Général :
- Titre du site : Utilisé dans navbar, footer, metadata
- Slogan : Utilisé comme description SEO
- URL WordPress : URL de base du site
Pour chaque article publié, s'assurer de :
- ✅ Assigner une image à la une (recommandé: 1200x630px)
- ✅ Assigner au moins une catégorie
- ✅ Renseigner un extrait (sinon généré automatiquement)
- ✅ Structurer le contenu avec des titres H2/H3 (pour la TOC)
- Créer des catégories pertinentes (Tech, Design, Business, etc.)
- Utiliser des slugs URL-friendly
- Optimiser les images avant upload
- Utiliser le champ Alt Text pour l'accessibilité
Modifier les variables CSS dans src/app/globals.css :
@layer base {
:root {
--background: 0 0% 100%;
--foreground: 222.2 84% 4.9%;
/* ... autres variables */
}
.dark {
--background: 222.2 84% 4.9%;
--foreground: 210 40% 98%;
/* ... autres variables */
}
}Modifier dans src/app/layout.tsx :
import { Inter } from "next/font/google";
const inter = Inter({
subsets: ["latin"],
variable: "--font-sans",
});Ctrl+K/Cmd+K- Ouvrir la barre de recherche↑/↓- Naviguer dans les résultats de rechercheEntrée- Sélectionner un résultatÉchap- Fermer la recherche
- Push le code sur GitHub
- Importer le projet sur Vercel
- Configurer les variables d'environnement :
NEXT_PUBLIC_WORDPRESS_API_URLNEXT_PUBLIC_SITE_URL
- Déployer
Le projet supporte output: "standalone" pour :
- Docker : Créer une image Docker avec
Dockerfile - VPS : Déployer avec PM2 ou systemd
- Netlify : Adapter pour les Edge Functions
Un Dockerfile est inclus pour le déploiement containerisé :
# Build l'image
docker build -t blog-nextjs .
# Run le conteneur
docker run -p 3000:3000 \
-e NEXT_PUBLIC_WORDPRESS_API_URL=https://your-wordpress.com/graphql \
-e NEXT_PUBLIC_SITE_URL=https://your-blog.com \
blog-nextjs- View Transitions API (navigation fluide)
- Images Open Graph dynamiques avec
@vercel/og - Newsletter fonctionnelle (Resend/SendGrid)
- Commentaires
- Optimisation des images (blur placeholder automatique)
- Mode Lecture immersif (sans distractions)
- Support multi-langue (i18n)
- Dark mode par défaut selon système
- Système de thèmes saisonniers 🎃🎄🧧 (auto-switch Halloween, Noël, Nouvel an chinois)
- PWA (Progressive Web App)
- Analytics intégré
- CI/CD automatisé
Les contributions sont les bienvenues ! N'hésitez pas à :
- Fork le projet
- Créer une branche (
git checkout -b feature/amazing-feature) - Commit les changements (
git commit -m 'Add amazing feature') - Push sur la branche (
git push origin feature/amazing-feature) - Ouvrir une Pull Request
npm run dev- Lancer le serveur de développement avec Turbopacknpm run build- Build de productionnpm start- Démarrer le serveur de productionnpm run lint- Linter le code avec ESLint
MIT © FabLrc
✨ Développé avec ❤️ par FabLrc
Si ce projet vous plaît, n'hésitez pas à lui donner une ⭐️ sur GitHub !



