Comment obtenez-vous que git tire toujours d'une branche spécifique?

485

Je ne suis pas un git master, mais je travaille avec lui depuis un certain temps maintenant, avec plusieurs projets différents. Dans chaque projet, je peux toujours git clone [repository]et à partir de là, toujours git pull, tant que je n'ai pas de changements en suspens, bien sûr.

Récemment, j'ai dû revenir à une branche précédente, et je l'ai fait avec git checkout 4f82a29. Quand j'étais à nouveau prêt à tirer, j'ai constaté que je devais remettre ma branche en maître. Maintenant, je ne peux pas tirer en utilisant une ligne droite, git pullmais au lieu de cela, je dois spécifier git pull origin master, ce qui est ennuyeux, et m'indique que je ne comprends pas bien ce qui se passe.

Qu'est-ce qui a changé qui ne me permet pas de faire une ligne droite git pullsans spécifier l'origine master, et comment puis-je le changer?

MISE À JOUR:

-bash-3.1$ cat config
[core]
    repositoryformatversion = 0
    filemode = true
    bare = false
    logallrefupdates = true
[branch "master"]
[remote "origin"]
    url = [email protected]:user/project.git
    fetch = refs/heads/*:refs/remotes/origin/*

MISE À JOUR 2: Pour être clair, je comprends que ma méthode d'origine était peut-être incorrecte, mais je dois corriger ce dépôt afin de pouvoir simplement l'utiliser à git pullnouveau. Actuellement, git pull se traduit par:

-bash-3.1$ git pull
You asked me to pull without telling me which branch you
want to merge with, and 'branch.master.merge' in
your configuration file does not tell me either.  Please
name which branch you want to merge on the command line and
try again (e.g. 'git pull  ').
See git-pull(1) for details on the refspec.

If you often merge with the same branch, you may want to
configure the following variables in your configuration
file:

    branch.master.remote = 
    branch.master.merge = 
    remote..url = 
    remote..fetch = 

See git-config(1) for details.

Je peux dire git pullquelle branche fusionner, et cela fonctionne correctement, mais git pullne fonctionne pas comme il le faisait à l'origine avant le mien git checkout.

David Smith
la source
À quoi ressemble votre .git / config? Qu'avez-vous fait après avoir vérifié ce commit?
Ryan Graham
Avez-vous effectué des validations en plus de 4f82a29?
Pat Notz
Pat, je n'ai fait aucun commit par-dessus. C'est sur un serveur, et nous devions revenir à une version stable afin de cacher un bug que nous avions créé. Ce système n'est pas à des fins de développement, donc je voulais simplement revenir en arrière, attendre pendant que nous corrigions le bogue, puis revenir à la version principale.
David Smith
2
Ryan, j'ai mis à jour pour inclure le .git / config. Après le départ, je n'ai rien fait. Cet ordinateur est un serveur, pas pour le développement.
David Smith

Réponses:

731

Sous [branch "master"], essayez d'ajouter ce qui suit au fichier de configuration Git du dépôt ( .git/config):

[branch "master"]
    remote = origin
    merge = refs/heads/master

Cela dit à Git 2 choses:

  1. Lorsque vous êtes sur la branche principale, la télécommande par défaut est l'origine.
  2. Lors de l'utilisation git pullsur la branche principale, sans télécommande ni branche spécifiées, utilisez la télécommande par défaut (origine) et fusionnez les modifications de la branche principale distante.

Je ne sais pas pourquoi cette configuration aurait été supprimée de votre configuration. Vous devrez peut-être également suivre les suggestions que d'autres personnes ont publiées, mais cela peut fonctionner (ou aider au moins).

Si vous ne souhaitez pas modifier le fichier de configuration à la main, vous pouvez utiliser l'outil de ligne de commande à la place:

$ git config branch.master.remote origin
$ git config branch.master.merge refs/heads/master
mipadi
la source
2
Cela a également fonctionné pour moi, j'avais vérifié un projet de github. J'utilise OS X 10.4
Sam Barnum
Merci très bien - ce qui est arrivé à moi sur un seul projet de développement avec un référentiel « serveur » et deux ordinateurs (dont je faisais souvent pousser / tirer sans problème avant le pépin), ne sais pas pourquoi, mais le correctif a travaillé bien!
chesterbr
1
Qu'entendez-vous par Under [branche "master"]
ianj
3
@ianj: dans le fichier de configuration Git (à partir de la racine du référentiel, .git/config).
mipadi
1
@ianj: Depuis la ligne de commande, vous pouvez toujours le faire à la $ git config branch.master.remote origin ; git config branch.master.merge refs/heads/masterplace.
mipadi
139

Si vous préférez, vous pouvez définir ces options via la ligne de commande (au lieu de modifier le fichier de configuration) comme suit:

  $ git config branch.master.remote origin
  $ git config branch.master.merge refs/heads/master

Ou, si vous êtes comme moi et que vous souhaitez que ce soit la valeur par défaut dans tous vos projets, y compris ceux sur lesquels vous pourriez travailler à l'avenir, ajoutez-le en tant que paramètre de configuration global:

  $ git config --global branch.master.remote origin
  $ git config --global branch.master.merge refs/heads/master
Tête
la source
12
+1 pour connaître le mot magique "refs / heads / master". Je n'avais pas mal à comprendre comment définir la variable, mais n'a absolument aucune idée de quoi le mettre à , et les pages de l' homme ne sont pas beaucoup d' aide. J'ai finalement trouvé le bon endroit dans les documents après avoir trouvé cette réponse. Pour les curieux: le mot magique fait référence à un chemin de fichier .gitdans lequel git semble conserver le code de hachage du mastercommit en cours.
mokus
84
git branch --set-upstream master origin/master

Cela ajoutera les informations suivantes à votre configfichier:

[branch "master"]
    remote = origin
    merge = refs/heads/master

Si vous en avez, branch.autosetuprebase = alwaysil ajoutera également:

    rebase = true
cmcginty
la source
1
Je trouve que c'est le moyen le plus simple de faire en sorte que git se comporte comme demandé, surtout s'il y a plus de branches, pas seulement à distance (même si vous devez le faire pour chaque branche, c'est une fois par branche)
s3v3n
2
Je viens d'essayer ceci, et j'obtiens l'erreur fatal: Not a valid object name: 'origin/master'.même si originc'est une télécommande valide, et masterexiste, comme d'habitude, dans les deux dépôts.
Ken Williams du
2
Ken, vous devez d'abord faire "git fetch origin" pour obtenir les noms des branches distantes.
Eric Lee
14
Le nouveau git veut que vous utilisiez git branch --set-upstream-to=origin/master master.
orbeckst le
52

J'ai du mal à me souvenir de l'exact git configou des git brancharguments comme dans les réponses de mipadi et Casey, donc j'utilise ces 2 commandes pour ajouter la référence en amont:

git pull origin master
git push -u origin master

Cela ajoutera les mêmes informations à votre .git / config, mais je trouve cela plus facile à retenir.

Luke Sampson
la source
1
Je suis d'accord. Cela devrait être la meilleure réponse la plus simple.
linbianxiaocao
2
Votre réponse doit comprendre pourquoi cela fonctionne et se référer à la section dans les documents qui explique pourquoi.
vfclists
24

Git pull combine deux actions: récupérer de nouvelles validations à partir du référentiel distant dans les branches suivies, puis les fusionner dans votre branche actuelle .

Lorsque vous avez extrait un commit particulier, vous n'avez pas de branche actuelle, vous n'avez que HEAD pointant vers le dernier commit que vous avez fait. N'a git pulldonc pas tous ses paramètres spécifiés. Voilà pourquoi cela n'a pas fonctionné.

Sur la base de vos informations mises à jour, ce que vous essayez de faire est de rétablir votre dépôt à distance. Si vous connaissez le commit qui a introduit le bogue, la manière la plus simple de gérer cela est d' git revertenregistrer un nouveau commit qui annule le commit de buggy spécifié:

$ git checkout master
$ git reflog            #to find the SHA1 of buggy commit, say  b12345
$ git revert b12345
$ git pull
$ git push

Puisque c'est votre serveur que vous souhaitez changer, je suppose que vous n'avez pas besoin de réécrire l'historique pour masquer la validation du buggy.

Si le bogue a été introduit dans une validation de fusion, cette procédure ne fonctionnera pas. Voir Comment-annuler une fusion défectueuse .

Paul
la source
Vous me donnez une excellente éducation ici, ce que j'apprécie, mais je ne décris peut-être pas très bien ma situation, donc ce n'est pas une correspondance exacte pour mon flux de travail. Je posterai probablement une autre question pour y répondre. Merci cependant, Paul! +1 à vous, monsieur.
David Smith
J'ai mal lu votre situation. Je suis content que vous ayez obtenu la réponse dont vous aviez besoin.
Paul
12

Il existe également un moyen de configurer Git, il extrait et pousse toujours la branche distante équivalente vers la branche actuellement extraite de la copie de travail. Cela s'appelle une branche de suivi que git ready recommande de définir par défaut .

Pour le référentiel suivant au-dessus du répertoire de travail actuel:

git config branch.autosetupmerge true

Pour tous les référentiels Git, qui ne sont pas configurés autrement:

git config --global branch.autosetupmerge true

Une sorte de magie, à mon humble avis, mais cela pourrait aider dans les cas où la branche spécifique est toujours la branche actuelle .

Lorsque vous avez branch.autosetupmergedéfini trueet extrait une branche pour la première fois, Git vous explique comment suivre la branche distante correspondante:

(master)$ git checkout gh-pages
Branch gh-pages set up to track remote branch gh-pages from origin.
Switched to a new branch 'gh-pages'

Git poussera alors automatiquement vers cette branche correspondante:

(gh-pages)$ git push
Counting objects: 8, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (6/6), done.
Writing objects: 100% (6/6), 1003 bytes, done.
Total 6 (delta 2), reused 0 (delta 0)
To [email protected]:bigben87/webbit.git
   1bf578c..268fb60  gh-pages -> gh-pages
Bengt
la source
10

Ne voulant pas modifier mon fichier de configuration git, j'ai suivi les informations dans le post de @ mipadi et utilisé:

$ git pull origin master

la source
13
Il s'agissait de le faire automatiquement plutôt que de le spécifier.
Eric
4

Votre question immédiate de savoir comment le faire tirer maître, vous devez faire ce qu'il dit. Spécifiez la spécification de référence à extraire dans votre configuration de branche.

[branch "master"]
    merge = refs/heads/master
Ryan Graham
la source
Cela ne devrait-il pas être "refs / heads / master"? Selon git-pull (1), il s'agit du nom de la branche sur le site distant qui est fusionnée par défaut.
Adam Monsen
Oui, tu as raison. Le dépôt dont j'ai pris l'exemple est un cas particulier. Corrigée.
Ryan Graham
0

Je voulais juste ajouter quelques informations, nous pouvons vérifier ces informations si elles git pullse réfèrent automatiquement à une branche ou non.

Si vous exécutez la commande git remote show origin,, (en supposant que l'origine est le nom abrégé de remote), git affiche ces informations, qu'il existe git pullou non une référence par défaut .

Vous trouverez ci-dessous un exemple de sortie (extrait de la documentation git).

$ git remote show origin
* remote origin
  Fetch URL: https://github.com/schacon/ticgit
  Push  URL: https://github.com/schacon/ticgit
  HEAD branch: master
  Remote branches:
    master                               tracked
    dev-branch                           tracked
  Local branch configured for 'git pull':
    master merges with remote master
  Local ref configured for 'git push':
    master pushes to master (up to date)

Veuillez noter la partie où il apparaît, branche locale configurée pour git pull.

Dans ce cas, git pullfera référence àgit pull origin master

Initialement, si vous avez cloné le référentiel, en utilisant git clone, ces choses sont automatiquement prises en charge. Mais si vous avez ajouté une télécommande manuellement à l'aide de git remote add, ceux-ci sont absents de la configuration git. Si tel est le cas, alors la partie où il affiche "Branche locale configurée pour 'git pull':", serait manquante dans la sortie de git remote show origin.

Les prochaines étapes à suivre si aucune configuration n'existe pour git pull, ont déjà été expliquées par d'autres réponses.

dr_dev
la source