Глиф Учебники

Ошибка rejected — non-fast-forward при git push

Справочник · Git · 2 минуты чтения

Текст
 ! [rejected]        main -> main (non-fast-forward)
error: failed to push some refs to 'https://github.com/ivan/todo.git'
hint: Updates were rejected because the tip of your current branch is behind
hint: its remote counterpart. If you want to integrate the remote changes,
hint: use 'git pull' before pushing again.

На сервере есть коммиты, которых нет у вас: кто-то отправил свои, или вы сами отправили их с другого компьютера. Сервер не принимает отправку, которая затёрла бы эти коммиты. Решение — сначала забрать их, потом отправить свои:

Bash
git pull
git push

Вариант той же ошибки — ! [rejected] main -> main (fetch first): Git ещё даже не скачивал новые коммиты с сервера. Решение то же.

git pull просит выбрать способ: divergent branches

В свежих версиях Git git pull может остановиться:

Текст
hint: You have divergent branches and need to specify how to reconcile them.
fatal: Need to specify how to reconcile divergent branches.

Новые коммиты есть и у вас, и на сервере, и Git просит один раз решить, как их объединять. Самый понятный вариант — слиянием:

Bash
git config --global pull.rebase false
git pull
git push

git pull создаст коммит слияния и откроет редактор с сообщением — сохраните и закройте его. Если вместо слияния вы хотите переносить свои коммиты поверх чужих (прямая история без коммитов слияния), задайте pull.rebase true — но сначала прочитайте об rebase в уроке Работа в команде.

Если при git pull возник конфликт — решите его, как в справке Как решить конфликт, и затем git push.

refusing to merge unrelated histories

Текст
fatal: refusing to merge unrelated histories

Так бывает с первой отправкой: репозиторий на сервере создали с файлом README или лицензией, и у него свой первый коммит, никак не связанный с вашей историей. Если уверены, что объединить нужно именно эти два репозитория, разрешите слияние один раз:

Bash
git pull origin main --allow-unrelated-histories
git push -u origin main

Если в обоих есть файл с одним именем (часто README.md), будет конфликт — решите его обычным способом.

Нельзя: принудительная отправка

git push --force «решает» ошибку, заменяя ветку на сервере вашей — и все чужие коммиты, которых у вас нет, пропадают с сервера. В общую ветку так отправлять нельзя. Принудительная отправка нужна только после осознанного переписывания своей ветки (--amend, rebase), и тогда безопаснее git push --force-with-lease.

Подводные камни