Mettre à jour les sous-modules Git de manière récursive

284

Ma structure de projet

ProjectA
-FrameworkA (submodule)
--Twig (submodule of FrameworkA)

Comment puis-je mettre à jour les sous-modules de manière récursive? J'ai déjà essayé quelques commandes git (sur root ProjectA)

git submodule foreach git pull origin master

ou

git submodule foreach --recursive git pull origin master

mais ne peut pas extraire des fichiers de Twig.

complez
la source
Que diriez - vous git-profond ?
Mathew Kurian

Réponses:

610
git submodule update --recursive

Vous voudrez aussi probablement utiliser l'option --init qui lui fera initialiser tous les sous-modules non initialisés:

git submodule update --init --recursive

Remarque: dans certaines anciennes versions de Git , si vous utilisez l' --initoption, les sous-modules déjà initialisés peuvent ne pas être mis à jour. Dans ce cas, vous devez également exécuter la commande sans --initoption.

drewag
la source
1
Que diriez-vous d'ajouter un sous-module récursif? "git submodule add FrameworkA.git" il suffit de tirer les fichiers de FrameworkA.
complez le
2
Vous pouvez juste faire un "git submodule add blah" puis "git submodule update --init --recursive".
drewag
Est-ce différent de mon chemin ci-dessous?
William Entriken du
3
@Irineau La note sur les sous-modules déjà initialisés qui ne sont pas mis à jour si --initest utilisé ne correspond pas à mes expériences sur Git 2.2.2. Je vois à la fois des sous-modules de niveau supérieur et imbriqués qui ont déjà été initialisés obtenir le bon commit vérifié lorsque j'utilise git submodule update --init --recursive, et je pense que l'affirmation selon laquelle vous devez exécuter la commande avec et sans --initest tout simplement fausse. À moins que quelqu'un ne puisse montrer la preuve que c'est le comportement ou démontrer qu'il a changé entre les versions et était une fois vrai, je prévois de le modifier complètement.
Mark Amery
3
@MarkAmery, je me souviens que c'était un problème dans une version de git dont je ne me souviens pas. Je viens de le tester en 1.9.3 et le problème ne semble plus exister. J'ai mis à jour la réponse pour faire référence à une vague "anciennes versions". Si quelqu'un peut spécifier quelle version a changé ce comportement, ce serait bien.
drewag
35

La façon dont j'utilise est:

git submodule update --init --recursive
git submodule foreach --recursive git fetch
git submodule foreach git merge origin master
William Entriken
la source
6
J'ai travaillé à changer la dernière ligne en:git submodule foreach git pull --ff-only origin master
Gilad Peleg
2
J'ajouterais aussi --recursive à la dernière ligne: "git submodule foreach --recursive git merge origin master" sinon vous pouvez obtenir un sous-module sale quand il a lui-même mis à jour un sous-module.
Michael Scott Cuthbert
Je cherchais ça depuis trois heures. Merci Monsieur. Pour ajouter à cela, vous pouvez également utiliser ces commandes pour commettre, telles que: git submodule foreach --recursive 'git commit -a | :'. Le :fait boucler quel que soit le résultat. Voir le lien stackoverflow.com/questions/19728933/… .
Pidgeon débutant
17

Comme il peut arriver que la branche par défaut de vos sous-modules ne le soit pasmaster (ce qui arrive souvent dans mon cas), voici comment j'automatise les mises à niveau complètes des sous-modules Git:

git submodule init
git submodule update
git submodule foreach 'git fetch origin; git checkout $(git rev-parse --abbrev-ref HEAD); git reset --hard origin/$(git rev-parse --abbrev-ref HEAD); git submodule update --recursive; git clean -dfx'
Sébastien Varrette
la source
J'ai essayé d'ajouter cette commande dans mon Makefile générique mais je suis toujours bloqué pour que GNU Make ignore l'interprétation de la séquence $ (...), malgré sa présence entre guillemets simples. Quelqu'un a une idée?
Sebastien Varrette
Votre commande est ce dont j'avais besoin merci! Mais je reçois: Entering 'Core' fatal: ambiguous argument 'origin/HEAD': unknown revision or path not in the working tree.Core est le sous
Sanandrea
Aussi, je suppose que vous devez comprendre ce commentaire stackoverflow.com/a/18008139/3383543
Ahmad AlMughrabi
ne pas avoir l'option récursive signifie que cela ne fonctionne que si vos sous-modules ne comprennent plus de sous-modules.
erikbwork
15

Dans Git récent (j'utilise la v2.15.1), les éléments suivants fusionneront les modifications de sous-module en amont dans les sous-modules de manière récursive:

git submodule update --recursive --remote --merge

Vous pouvez ajouter --initpour initialiser tous les sous-modules non initialisés et les utiliser --rebasesi vous souhaitez rebaser au lieu de fusionner.

Vous devez ensuite valider les modifications:

git add . && git commit -m 'Update submodules to latest revisions'
mrts
la source
Cela, je pensais que je faisais quelque chose de mal, mais votre réponse m'a confirmé que cela git submodule update --remote my-dir/my-submodulefonctionne aussi bien
iomv