Fusionner la branche de développement avec le maître

764

J'ai deux branches à savoir masteret developmentdans un référentiel GitHub. Je fais tout mon développement dans la branche développement comme indiqué.

git branch development
git add *
git commit -m "My initial commit message"
git push -u origin development

Maintenant, je veux fusionner toutes les modifications de la developmentbranche dans le master. Mon approche actuelle est:

git checkout master 
git merge development
git push -u origin master 

Veuillez me faire savoir si la procédure que je suis est correcte.

Pawan
la source
7
git pull -udéfinit le suivi en amont de la branche (ou de toutes les branches si vous en appuyez sur plusieurs). Une fois qu'il est défini, le suivi persiste. Il n'y a aucune raison de l'utiliser en permanence.
David Culp

Réponses:

1166

J'aime généralement fusionner masterdans le developmentpremier afin que s'il y a des conflits, je puisse résoudre dans la developmentbranche elle-même et mes masterrestes propres.

(on branch development)$ git merge master
(resolve any merge conflicts if there are any)
git checkout master
git merge development (there won't be any conflicts now)

Il n'y a pas beaucoup de différence entre les deux approches, mais j'ai parfois remarqué que je ne veux pas encore fusionner la branche master, après les avoir fusionnées, ou qu'il reste encore du travail à faire avant de pouvoir les fusionner , donc j'ai tendance à laisser masterintacte jusqu'à la fin.

EDIT: Des commentaires

Si vous souhaitez savoir qui a effectué la fusion et quand, vous pouvez utiliser l' --no-ffindicateur lors de la fusion pour le faire. Ceci est généralement utile que lors de la fusion developmentdans la master(dernière étape), parce que vous pourriez avoir besoin de fusionner masteren development(première étape) plusieurs fois dans votre flux de travail et la création d' un noeud pour commettras ceux - ci pourraient ne pas être très utile.

git merge --no-ff development
Sailesh
la source
71
Il y a un léger inconvénient à cette approche: la fusion réelle vers le maître est très probablement une fusion à avance rapide et ne crée donc aucun nœud de validation. Ce n'est pas un problème avec le code réel sur la branche, mais il est difficile de savoir plus tard, qui a effectué la fusion réelle à maîtriser et à quel moment. Un explicite --no-ffà la fusion à master est nécessaire pour résoudre ce problème.
michas
11
Oui, c'est exactement pour ça --no-ff. :)
michas
19
C'est git merge --no-ff developmentjuste pour corriger l'utilisation de @ elect.
jewbix.cube
2
@sailesh pouvez-vous mettre à jour votre réponse pour inclure l'indicateur de fusion git, si vous êtes d'accord avec les commentaires?
Utilisateur Web
2
@Mars, la fusion remplacera un fichier si l'ancien changement était dans l'ascendance directe du commit. Par exemple, laissez A->B->Cêtre maître et A->X->Yest votre branche de développement. Si vous modifiez une partie d'un fichier dans Xlequel il pourrait y avoir eu des conflits avec une modification dans A, ce ne sera pas un conflit, car Aest un ancêtre de X. En ce qui concerne les modifications perdues, consultez stackoverflow.com/questions/7147680/… pour récupérer les modifications.
Sailesh
103

Personnellement, mon approche est similaire à la vôtre, avec quelques branches de plus et quelques écrasements de commits quand ils reviennent au master.

Un de mes collègues n'aime pas trop devoir changer de branche et reste sur la branche de développement avec quelque chose de similaire aux suivants tous exécutés à partir de la branche de développement.

git fetch origin master

git merge master

git push origin development:master

La première ligne s'assure qu'il a des validations en amont qui ont été faites pour master depuis la dernière mise à jour de son référentiel local.

Le second tire ces changements (le cas échéant) du maître au développement

Le troisième pousse la branche de développement (maintenant complètement fusionnée avec master) vers origin / master.

J'ai peut-être un peu tort son flux de travail de base, mais c'est l'essentiel.

David Culp
la source
Merci! Cela me semble plus intuitif.
Jamie Nicholl-Shelley
2
Oui - dans les 6 ans et plus depuis que j'ai écrit cela, je l'ai moi aussi adopté - bien qu'avec la rebasemise à jour de la devbranche au lieu de merge.
David Culp
32

Explication du bas pour ceux qui sont venus ici sans aucune connaissance des branches.

La logique de développement de branche principale de base est la suivante: vous ne travaillez que sur une autre branche et utilisez le maître uniquement pour fusionner une autre branche.

Vous commencez à créer une nouvelle branche de cette façon:

1) Cloner le référentiel dans votre répertoire local (ou créer un nouveau référentiel):

$ cd /var/www
$ git clone [email protected]:user_name/repository_name.git

2) Créez une nouvelle branche. Il contiendra les derniers fichiers de votre référentiel de branche principale

$ git branch new_branch

3) Changez votre branche git actuelle en new_branch

$ git checkout new_branch

4) Faites du codage, engage, comme d'habitude…

$ git add .
$ git commit -m “Initial commit”
$ git push (pushes commits only to “new_branch”)

5) Lorsque le travail est terminé sur cette branche, fusionnez avec la branche «maître»:

$ git merge master
$ git checkout master (goes to master branch)
$ git merge development (merges files in localhost. Master shouldn’t have any  commits ahead, otherwise there will be a need for pull and merging code by hands!)
$ git push (pushes all “new_branch” commits to both branches - “master” and “new_branch”)

Mise à jour: je recommande fortement d'utiliser GitKraken pour cela pour voir l'arborescence visuelle des changements et mieux voir toute la logique et les validations.

Gediminas
la source
J'ai aimé votre approche de ne pas travailler sur master. mais aujourd'hui quand je jouais avec gitflow, j'ai créé la releasebranche our of the develop. Puis ajouté un fichier de note de version et validé. Puis a terminé la version qui fusionne à la fois master/develop. mais ma branche principale avait seulement une note de sortie nouvellement ajoutée. aucun autre fichier lors des validations de développement précédentes n'y a été mis à jour.
Amit Shah
si vous travaillez sur une autre branche que master, assurez-vous d'avoir validé et poussé les modifications apportées à cette branche. Vous pouvez alors voir à quoi ressemblent les fichiers sur l'interface graphique de github.com ou bitbucket.com et essayer de cliquer sur Fusionner, sur le site Web. Il devrait tout mettre à jour, de votre branche au maître. Si le maître a des fichiers plus récents, cela devrait être un conflit et vous obtiendrez le message d'erreur. Je ne suis pas sûr d'avoir répondu assez bien, veuillez me donner un message sinon :)
Gediminas
J'utilise sourcetree comme interface graphique et référentiel github. J'ai essayé 2 fois avec test de release. le maître n'a jamais mis à jour avec la dernière branche de développement.
Amit Shah
essayez d'utiliser sur le site github.com en direct les fichiers de votre succursale sur laquelle vous travaillez. Sont-ils poussés? Si oui, essayez de cliquer sur la même branche - Fusionner et vous verrez ce qui se passe. Dans mon expérience personnelle avec sourcetree est assez mauvaise - je n'ai pas pu comprendre pleinement ce qui se passe dans mes succursales aussi
Gediminas
Merci @Gediminas pour l'explication détaillée. J'étais confus dans les mots-clés git avant de lire votre réponse .. :)
Dinesh Suthar
21

Ce serait formidable si vous pouviez utiliser le workflow Git Flow . Il peut fusionner facilement la branche de développement en maître.

Ce que vous voulez faire, c'est simplement suivre l'instruction git-flow mentionnée ici:

PAS:

  • configurer le projet git-flow
  • créer des succursales et tout fusionner pour se développer
  • exécutez la commande git flow release start <version_number>
  • puis fournir un message significatif pour la sortie
  • exécutez la commande git flow release finish <version_number>
  • il fusionnera tout en maître et changera la branche en maître .
  • exécutez la commande git pushpour publier les modifications sur le maître distant .

Pour plus d'informations, visitez la page - http://danielkummer.github.io/git-flow-cheatsheet/

Harsha
la source
1
La solution si quelqu'un utilise git flow!
Csaba Toth le
21
1. //pull the latest changes of current development branch if any        
git pull (current development branch)

2. //switch to master branch
git checkout master 

3. //pull all the changes if any
git pull

4. //Now merge development into master    
git merge development

5. //push the master branch
git push origin master
Rizwan Siddiquee
la source
9

Oui, c'est correct, mais cela ressemble à un flux de travail très basique, où vous mettez simplement les modifications en mémoire tampon avant qu'elles ne soient prêtes pour l'intégration. Vous devriez examiner des workflows plus avancés pris en charge par git. Vous aimerez peut-être l' approche par branche de sujet , qui vous permet de travailler sur plusieurs fonctionnalités en parallèle, ou l' approche de graduation qui étend un peu votre flux de travail actuel.

Sergiu Dumitriu
la source
6

Si vous êtes sur Mac ou Ubuntu, accédez au dossier de travail de la branche. Dans le terminal

supposons que harisdev est le nom de la branche.

git checkout master

s'il y a des fichiers non suivis ou non validés, vous obtiendrez une erreur et vous devrez valider ou supprimer tous les fichiers non suivis ou non validés.

git merge harisdev 

git push origin master

Une dernière commande pour supprimer la branche.

$ git branch -d harisdev
Haris Np
la source
Qu'est-ce qui est spécifique à Mac ou Ubuntu?
talonx
Désolé. Aucune des autres réponses n'a mentionné que les commandes devraient être données dans le terminal et la commande pour supprimer la branche. En fait, je voulais juste ajouter la commande pour supprimer la branche afin que le développeur ne joue plus avec la même branche à l'avenir. J'utilise Mac, donc je l'ai mentionné. Votre question est valide et aucune de ces commandes n'est spécifique à Mac ou Ubuntu.
Haris Np
Merci de clarifier.
talonx
5

Étape 1

Créez et passez à une nouvelle branche "dev", où vos fichiers git locaux sont synchronisés avec la branche distante mais "dev" n'existe pas encore.

git branch dev # create
git checkout dev # switch
# No need to git add or git commit, the current
# branch's files will be cloned to the new branch by-default.
git push --set-upstream origin dev # push the "dev" branch to the remote.

Étape 2

Apportez vos modifications à la branche "dev" (votre courant si vous suivez l'étape 1), validez-les et envoyez-les à la branche "dev" distante.

git add .
git commit -S -m "my first commit to the dev branch" # remove the -S if you're not "secure", secure = when you already setup crypto private and public keys (i.e "verified" green sign in github)
git push -u origin dev # push the changes to the remote, -u origin dev is optional but good to use.

Étape 3

Fusionnez votre branche "dev" dans le "master".

git checkout dev # switch to "dev" branch if you're not already.
git merge master # optionally, this command is being used to resolve any conflicts if you pushed any changes to your "master" but "dev" doesn't have that commit.
git checkout master # switch to "master", which is the branch you want to be merged.
git merge --no-ff dev # merge the "dev" branch into the "master" one.
kataras
la source
4

C'est comme ça que je le fais d'habitude. Tout d'abord, assurez-vous que vous êtes prêt à fusionner vos modifications dans master.

  1. Vérifiez si le développement est à jour avec les dernières modifications de votre serveur distant avec un git fetch
  2. Une fois la récupération terminée git checkout master.
  3. Assurez-vous que la branche principale dispose des dernières mises à jour en exécutant git pull
  4. Une fois les préparatifs terminés, vous pouvez démarrer la fusion avec git merge development
  5. Poussez les modifications avec git push -u origin masteret vous avez terminé.

Vous pouvez en savoir plus sur la fusion de git dans l'article.

Nesha Zoric
la source
3

1) Sur le développement de branche, vérifiez l'état de git en utilisant la commande suivante:

git status

Il ne devrait pas y avoir de code non engagé. Si c'est le cas, poussez votre code sur la branche Développement:

git add *

git commit -m "My initial commit message"

git push origin Development

2) Sur la branche Développement, exécutez les deux commandes suivantes:

git branch -f master HEAD

git push -f origin master

Il poussera votre code de branche de développement vers la branche principale.

Himanshu Mahajan
la source
Est-ce que cela pousse également toutes les validations de développement vers master, ou ajoute simplement un nouveau commit unique dans master?
roule du
1
comment cela fonctionne-t-il réellement? spécifiquement "git branch master" lorsque vous êtes sur le développement ressemble à de la folie. comment pouvez-vous créer une nouvelle branche appelée master, s'il existe déjà une branche appelée master? les documents disent que -f fait ceci: réinitialiser <branchname> à <startpoint>. Qu'est-ce que ça veut dire?
John Little
Cette force ne pousse-t-elle pas le maître local sur le maître distant? Cela semble être une mauvaise idée si vous travaillez en équipe.
Nick
-fn'est pas recommandé.
DawnSong
2

Basé sur @Sailesh et @DavidCulp:

(on branch development)
$ git fetch origin master
$ git merge FETCH_HEAD
(resolve any merge conflicts if there are any)
$ git checkout master
$ git merge --no-ff development (there won't be any conflicts now)

La première commande s'assurera que vous avez tous les commits en amont effectués sur le maître distant, avec une réponse Sailesh qui ne se produirait pas.

Le second effectuera une fusion et créera des conflits que vous pourrez ensuite résoudre.

Après cela, vous pouvez enfin commander master pour passer en master.

Ensuite, vous fusionnez la branche de développement sur le maître local. L'indicateur no-ff créera un nœud de validation dans master pour que toute la fusion soit traçable.

Après cela, vous pouvez valider et pousser votre fusion.

Cette procédure s'assurera qu'il y a un commit de fusion du développement au master que les gens peuvent voir, puis s'ils regardent la branche de développement, ils peuvent voir les validations individuelles que vous avez faites dans cette branche pendant son développement.

Vous pouvez éventuellement modifier votre commit de fusion avant de le pousser, si vous souhaitez ajouter un résumé de ce qui a été fait dans la branche de développement.

EDIT: ma réponse d'origine suggérait un git merge masterqui n'a rien fait, il vaut mieux le faire git merge FETCH_HEADaprès avoir récupéré l'origine / master

Cisco
la source
2

Une fois que vous avez «vérifié» la branche de développement, vous ...

 git add .
 git commit -m "first commit"
 git push origin dev
 git merge master

 git checkout master 
 git merge dev
 git push origin master 
Tiago Medici
la source
1

Si vous utilisez gerrit, les commandes suivantes fonctionnent parfaitement.

git checkout master
git merge --no-ff development

Vous pouvez enregistrer avec le message de validation par défaut. Assurez-vous que l'ID de modification a été généré. Vous pouvez utiliser la commande suivante pour vous en assurer.

git commit --amend

Poussez ensuite avec la commande suivante.

git push origin HEAD:refs/for/refs/heads/master

Vous pourriez rencontrer un message d'erreur comme ci-dessous.

! [remote rejected] HEAD -> refs/for/refs/heads/master (you are not allowed to upload merges)

Pour résoudre ce problème, l'administrateur du projet gerrit doit créer une autre référence dans gerrit nommée 'refs / for / refs / heads / master' ou 'refs / for / refs / heads / *' (qui couvrira toutes les branches à l'avenir). Accordez ensuite l'autorisation «Push Merge Commit» à cette référence et l'autorisation «Soumettre» si nécessaire pour soumettre le GCR.

Maintenant, essayez à nouveau la commande push ci-dessus, et cela devrait fonctionner.

Crédits:

https://github.com/ReviewAssistant/reviewassistant/wiki/Merging-branches-in-Gerrit

https://stackoverflow.com/a/21199818/3877642

Sankaran Srinivasan
la source
1

Je pense que la solution la plus simple serait

git checkout master
git remote update
git merge origin/Develop -X theirs
git commit -m commit -m "New release"
git push --recurse-submodules=check --progress "origin" refs/heads/Master

Cela préserve également l'historique de toutes les branches utilisées

Vishal
la source
-4
1. //push the latest changes of current development branch if any        
git push (current development branch)

2. //switch to master branch
git checkout master 

3. //pull all the changes if any from (current development branch)
git pull origin (current development branch)

4. //Now merge development into master    
git merge development

5. //push the master branch
git push origin master

Error
To https://github.com/rajputankit22/todos-posts.git
 ! [rejected]        master -> master (fetch first)
error: failed to push some refs to 'https://github.com/rajputankit22/todos-posts.git'
hint: Updates were rejected because the remote contains work that you do
hint: not have locally. This is usually caused by another repository pushing
hint: to the same ref. You may want to first integrate the remote changes
hint: (e.g., 'git pull ...') before pushing again.
hint: See the 'Note about fast-forwards' in 'git push --help' for details.

Then Use 
5. //push the master branch forcefully
git push -f origin master
Ankit Kumar Rajpoot
la source
1
Pousser de force lorsque vous voyez que l'erreur n'est presque jamais la bonne chose à faire, sauf si vous êtes très certain de savoir pourquoi votre branche locale manque des validations de la branche distante. En général, il est préférable de revenir à l'étape 3 et à pullnouveau. De plus, la valeur ajoutée de cette réponse n'est pas claire par rapport aux réponses existantes.
Kyle Strand