Bye-bye les Submodules : Migrer vers Git Subtree sans douleur
Marre des submodules qui cassent votre CI/CD ? Voici comment migrer proprement vers un subtree pour un workflow de contenu enfin zen.
On ne va pas se mentir : les submodules Git, c’est un peu comme cette vieille chaudière au fond de la cave. Ça marche, mais on a toujours peur que ça nous pète à la figure au pire moment (souvent un vendredi à 17h, lors d’un déploiement critique).
Cet article est la suite logique de mon comparatif Git Submodule vs. Git Subtree : Lequel Choisir ?. Si, comme moi, vous en avez eu marre des pointeurs mystérieux et des “detached HEAD” qui ruinent votre journée, voici comment passer au subtree proprement, sans perdre de données et en gardant votre santé mentale intacte.
Le décor : J’utilise un site Astro où mon contenu (mes précieux fichiers .mdx) vit dans un dépôt séparé. Jusqu’ici, c’était lié via un submodule dans billets-blogue/. On va transformer ça en subtree pour que le contenu fasse enfin partie intégrante du projet principal.
Avant de tout casser : la sécurité d’abord
On n’est pas des sauvages. Avant de supprimer quoi que ce soit, assurez-vous que tout ce qui traînait dans votre submodule est bien pushé sur son propre dépôt.
Petite astuce de paranoïaque (très utile en dev) : faites un clone frais de votre dépôt de contenu ailleurs sur votre machine. C’est votre filet de sécurité au cas où on ferait une fausse manip et croyez-moi je m’y connais en fausse manip.
git clone https://github.com/user/billets-blogue.git ~/projets/sauvegarde-billets
Étape 1 : On s’isole
L’audace c’est bien, mais la prudence c’est mieux. On ne fait jamais ce genre de bidouille directement sur main.
git checkout main
git checkout -b migration-subtree-bye-bye-submodules
Étape 2 : Le grand ménage
Pour virer un submodule, Git demande un peu de doigté. C’est une opération en trois temps pour ne laisser aucune trace de graisse sur les murs.
# 1. On débranche la configuration locale
git submodule deinit -f billets-blogue
# 2. On supprime la référence dans le projet et ce bon vieux .gitmodules
git rm -rf billets-blogue
# 3. On nettoie les entrailles de Git (le dossier interne)
# Si ce dossier n'existe pas, pas de panique, c'est juste qu'il n'était pas init ici.
rm -rf .git/modules/billets-blogue
# 4. On valide ce nouveau départ
git commit -m "chore: suppression définitive du submodule (enfin !)"
Note de style : J’utilise le préfixe
chore:pour mes messages de commit. C’est propre, ça range les tâches de maintenance dans une case à part, et ça fait plaisir aux amateurs de Conventional Commits.
Étape 3 : Place au Subtree
C’est là que la magie opère. On commence par ajouter le dépôt de contenu comme un “remote”. Ça nous évitera de taper l’URL complète à chaque fois qu’on veut récupérer un article.
# On ajoute le remote
git remote add billets-blogue https://github.com/user/billets-blogue.git
# On injecte le subtree
git subtree add --prefix=billets-blogue billets-blogue main --squash
On décode la commande (parce que c’est un peu barbare) :
--prefix=billets-blogue: C’est le dossier de destination dans votre projet.billets-blogue: Le nom du remote qu’on vient de créer.main: La branche qu’on veut pointer.--squash: Indispensable. Ça évite d’importer tout l’historique du repo de contenu (les 400 commits de “typo fix”) dans votre projet principal. On condense tout en un seul commit propre.
Étape 4 : Le moment de vérité
On merge sur main et on observe le résultat.
git checkout main
git merge migration-subtree-bye-bye-submodules
git push origin main
Le bonus “zénitude” : Si votre plateforme de déploiement (Vercel, Netlify ou votre propre VPS) s’embêtait à faire des git submodule update --init, vous pouvez supprimer tout ça. Un simple npm run build suffit maintenant, puisque le contenu est physiquement là. C’est pas une dinguerie, ça ? 🚀
Workflow au quotidien : récupérer les nouveautés
Maintenant que vous êtes sur un subtree, voici comment vous récupérez les derniers commits poussés sur votre autre dépôt :
git subtree pull --prefix=billets-blogue billets-blogue main --squash
git push origin main
La flemme est une vertu : l’alias Git
Taper cette commande à chaque fois ? Trop long. Ajoutez ceci à votre .git/config (au niveau du projet) :
[alias]
blog-pull = subtree pull --prefix=billets-blogue billets-blogue main --squash
Désormais, un simple git blog-pull suffit à mettre votre blog à jour.
Le bilan des courses
| Situation | Submodule | Subtree |
|---|---|---|
| Premier clone | Vide (faut faire un --init) | Tout est là, direct. |
| Déploiement | Parfois capricieux | Zéro config, c’est du code standard. |
| Mise à jour | git submodule update | git subtree pull |
| Historique | Pointeur vers un commit | Contenu réel (squashé) |
La migration est terminée ! Votre contenu est désormais un citoyen de première classe dans votre dépôt principal. C’est plus simple, plus robuste et franchement, dans mon cas, ça fait un truc en moins à gérer quand je veux juste publier un article.