Git отклонен без ускоренной перемотки вперед - PullRequest
87 голосов
/ 14 апреля 2011

Я чувствую, что этот вопрос задавался много раз, но решение, как правило, состоит в том, что «я удалил каталог и заново выполнил свою работу с новой проверкой». Я сделал коммит и нажал, но понял, что указал неправильный номер билета в сообщении фиксации. Поэтому я посмотрел на SO для быстрого решения и в итоге набрал в терминале следующее:

$ git reset --soft HEAD^
$ git commit -m "... correct message ..."

Единственная проблема в том, что я получаю следующее сообщение об ошибке:

To prevent you from losing history, non-fast-forward updates were rejected
Merge the remote changes before pushing again.  See the 'Note about
fast-forwards' section of 'git push --help' for details.

Я использую модель git-flow и работаю над ветвью разработки. Как я могу объединить вещи обратно, чтобы сделать Git счастливым снова?

Ответы [ 4 ]

172 голосов
/ 14 апреля 2011

Если вы отправляете коммит на сервер, а затем переписываете этот коммит локально (с помощью git reset, git rebase, git filter-branch,или любые другие манипуляции с историей), а затем отправив этот переписанный коммит обратно на сервер, вы облажаетесь с любым другим, кто его вытянул.Вот пример;скажем, вы зафиксировали A и отправили его на сервер.

-*-*-A <-- master

-*-*-A <-- origin/master

Теперь вы решили переписать A, как вы упомянули, сбросить и повторно зафиксировать.Обратите внимание, что это оставляет висячий коммит, A, который в конечном итоге будет собираться мусором, так как он недоступен.

-*-*-A
    \
     A' <-- master

-*-*-A  <-- origin/master

Если кто-то еще, скажем, Фред, отключит master от сервера, пока вы 'делая это, у них будет ссылка на A, с которой они могли бы начать работать:

-*-*-A' <-- master

-*-*-A  <-- origin/master

-*-*-A-B <-- fred/master

Теперь, если бы вы смогли подтолкнуть вашу A 'к origin / master, это создаст-вперед, он не будет иметь в своей истории.Так что, если Фред попытается вытащить снова, ему внезапно придется слиться, и он снова введет коммит A:

-*-*-A' <-- master

-*-*-A  <-- origin/master

-*-*-A-B-\ 
    \     * <-- fred/master
     A'--/

Если Фред заметит это, то он может сделать ребаз, чтопредотвратить повторное появление коммита А.Но он должен был это заметить и не забыть сделать это;и если у вас есть несколько человек, которые сбросили A, им всем пришлось бы перебазировать, чтобы не получить дополнительный коммит A в дереве.

Таким образом, вообще не стоит менять историю нарепо, из которого тянут другие люди.Однако, если вы знаете, что никто не извлекает из этого репо (например, это ваше собственное частное репо, или у вас есть только один другой разработчик, работающий над проектом, с которым вы можете легко координировать свои действия), то вы можете принудительно применить его.обновите, запустив:

git push -f

или

git push origin +master

Они оба проигнорируют проверку для не-быстрой пересылки и обновят то, что на сервере, до вашей новой версии A ', оставив ревизию A, чтобы в конечном итоге она стала собирать мусор.

Вполне возможно, что принудительные нажатия полностью отключаются с помощью опции конфигурации receive.denyNonFastForwards.Эта опция включена по умолчанию в общих репозиториях.В этом случае, если вы действительно хотите принудительно нажать кнопку, лучшим вариантом будет удалить ветвь и воссоздать ее с помощью git push origin :master; git push origin master:master.Однако опция denyNonFastForwards включена по причине, которая описана выше;в общем хранилище это означает, что теперь каждый, кто его использует, должен убедиться, что он обновляется в новой истории.

В общем хранилище обычно лучше просто добавить новые коммиты сверху, чтобы решить любую проблемуу тебя есть;вы можете использовать git revert для генерации коммитов, которые будут отменять изменения предыдущих коммитов.

52 голосов
/ 14 апреля 2011

Сила git push:

git push origin +develop
14 голосов
/ 14 апреля 2011

Возможно, вам придется сделать git pull, который МОЖЕТ автоматически слить материал для вас.Тогда вы можете совершить еще раз.Если у вас есть конфликты, вам будет предложено их разрешить.

Имейте в виду, вы должны указать, из какой ветки вы хотите извлечь, если вы не обновили свой gitconfig, чтобы указать ...

Например:

git pull origin develop:develop
7 голосов
/ 19 июля 2013

Я использовал EGit и тоже столкнулся с этой проблемой.Просто попытался rebase текущую ветку и все заработало.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...