Question Comment puis-je forcer correctement une poussée Git?


J'ai mis en place un repo "principal" distant non-nue et l'ai cloné sur mon ordinateur. J'ai apporté quelques modifications locales, mis à jour mon référentiel local et repoussé les modifications vers mon repo distant. Les choses allaient bien jusque-là.

Maintenant, j'ai dû changer quelque chose dans le repo distant. Puis j'ai changé quelque chose dans mon repo local. J'ai réalisé que le changement de repo à distance n'était pas nécessaire. J'ai donc essayé de git push de mon repo local à mon repo distant, mais j'ai eu une erreur comme:

Pour vous éviter de perdre l'historique, les mises à jour non rapides   rejeté Fusionne les modifications à distance avant de pousser à nouveau. Voir la note   à propos de la section de fast-forwards git push --help pour plus de détails.

Je pensais que probablement

git push --force

forcerait ma copie locale à pousser les changements à la télécommande et à faire la même chose. Cela force la mise à jour, mais quand je reviens au repo distant et que je fais un commit, je remarque que les fichiers contiennent des changements obsolètes (ceux que le repo distant avait auparavant).

Comme je l'ai mentionné dans le commentaires à l'une des réponses:

[J'ai] essayé de forcer, mais lorsque je retourne sur le serveur maître pour enregistrer les changements, j'ai une mise à jour obsolète. Ainsi, quand je commets les dépôts ne sont pas les mêmes. Et quand j'essaye d'employer git push encore, j'obtiens la même erreur.

Comment puis-je résoudre ce problème?


908
2018-04-01 05:35


origine


Réponses:


Faites juste:

git push origin <your_branch_name> --force

ou si vous avez un dépôt spécifique:

git push https://git.... --force

Cela supprimera votre (vos) commit (s) précédent (s) et poussera votre actuel.

Ce n'est peut-être pas correct, mais si quelqu'un trébuche sur cette page, pense qu'ils pourraient vouloir une solution simple ...

Court drapeau

Notez également que -f est court pour --force, alors

git push origin <your_branch_name> -f

travaillera aussi.


1726
2017-09-26 21:31



Et si push --force ne fonctionne pas, vous pouvez le faire push --delete. Regardez 2sd ligne sur cette instance:

git reset --hard HEAD~3  # reset current branch to 3 commits ago
git push origin master --delete  # do a very very bad bad thing
git push origin master  # regular push

Mais méfiez-vous...

Ne jamais revenir sur une histoire de git publique!

En d'autres termes:

  • Ne jamais force pousser sur un dépôt public.
  • Ne fais pas ceci ou quoi que ce soit qui puisse casser quelqu'un pull.
  • Ne jamais reset ou rewrite l'histoire dans un repo quelqu'un a peut-être déjà tiré.

Bien sûr, il y a même des exceptions exceptionnellement rares à cette règle, mais dans la plupart des cas, ce n'est pas nécessaire et cela va générer des problèmes pour tout le monde.

Faites un retour à la place.

Et toujours faire attention à ce que vous poussez à un dépôt public. Revenant:

git revert -n HEAD~3..HEAD  # prepare a new commit reverting last 3 commits
git commit -m "sorry - revert last 3 commits because I was not careful"
git push origin master  # regular push

En effet, tous les deux têtes d'origine (du revenir et de la réinitialisation du mal) contiendra les mêmes fichiers.


modifier pour ajouter des informations mises à jour et plus d'arguments autour push --force

Envisager de pousser la force avec bail au lieu de pousser, mais préfèrent toujours revenir

Un autre problème push --force peut apporter est quand quelqu'un pousse quelque chose avant de le faire, mais après que vous avez déjà été chercher. Si vous poussez votre force rebasé version maintenant vous remplacer le travail des autres.

git push --force-with-lease introduit dans le git 1.8.5 (merci à @VonC commenter la question) essaie d'aborder ce problème spécifique. Fondamentalement, il va apporter une erreur et ne pas pousser si la télécommande a été modifiée depuis votre dernier chargement.

C'est bon si vous êtes vraiment sûr push --force est nécessaire, mais veulent toujours éviter plus de problèmes. J'irais aussi loin pour dire que ce devrait être le défaut push --force comportement. Mais c'est encore loin d'être une excuse pour forcer push. Les gens qui récupéré avant votre rebaser aura encore beaucoup de problèmes, qui pourraient être facilement évités si vous aviez retourné au lieu.

Et puisque nous parlons de git --push instances...

Pourquoi quelqu'un voudrait-il pousser?

@linquize apporté un bon exemple de force de poussée sur les commentaires: données sensibles. Vous avez mal divulgué des données qui ne devraient pas être poussées. Si vous êtes assez rapide, vous pouvez "réparer"* en forçant une poussée sur le dessus.

* le les données seront toujours sur la télécommande sauf si vous faites aussi ramasser les ordures, ou nettoyer en quelque sorte. Il y a aussi le potentiel évident pour qu'il soit propagé par d'autres qui récupéré déjà, mais vous avez l'idée.


198
2018-05-22 22:03



Tout d'abord, je ne ferais aucun changement directement dans le repo "principal". Si vous voulez vraiment avoir un repo "principal", alors vous devriez seulement pousser dessus, ne jamais le changer directement.

En ce qui concerne l'erreur que vous obtenez, avez-vous essayé git pull de votre dépôt local, puis git push au dépôt principal? Ce que vous êtes en train de faire (si je l'ai bien compris) est de forcer la poussée et ensuite de perdre vos changements dans le repo "principal". Vous devez fusionner les modifications localement en premier.


17
2018-04-01 05:42



Si je suis sur ma branche locale A, et que je veux pousser la branche locale B vers la branche d'origine C, je peux utiliser la syntaxe suivante:

git push --force origin B:C

13
2018-05-28 18:25



Je recommande vraiment de:

  • pousser seulement au dépôt principal

  • assurez-vous que le principal repo est un repo nu, afin de ne jamais avoir de problème avec l'arbre de travail repo principal n'étant pas en phase avec son .git base. Voir "Comment faire pour pousser un référentiel git local vers un autre ordinateur?"

  • Si vous devez faire une modification dans le repo principal (nu), clonez-le (sur le serveur principal), faites votre modification et repoussez-la

En d'autres termes, gardez un repo nu accessible à la fois depuis le serveur principal et l'ordinateur local, afin d'avoir un seul repo amont de / vers lequel tirer / tirer.


10
2018-04-01 05:53



C'était notre solution pour remplacer le maître sur un dépôt de gitHub d'entreprise tout en maintenant l'histoire.

push -f maîtriser sur les référentiels d'entreprise est souvent désactivé pour maintenir l'historique des branches. Cette solution a fonctionné pour nous.

git fetch desiredOrigin
git checkout -b master desiredOrigin/master // get origin master

git checkout currentBranch  // move to target branch
git merge -s ours master  // merge using ours over master
// vim will open for the commit message
git checkout master  // move to master
git merge currentBranch  // merge resolved changes into master

pousser votre branche à desiredOrigin et créer un PR


5
2018-05-26 21:31



utilisez cette commande:

git push -f origin master

3
2018-04-10 14:00