Вопрос по git-push, git – Git Push error: отказывается обновлять извлеченную ветку

155

Я решил некоторые конфликты слияния, зафиксировал их, затем попытался отправить свои изменения и получил следующую ошибку:

c:\Program Files (x86)\Git\bin\git.exe push --recurse-submodules=check "origin" master:master
Done
remote: error: refusing to update checked out branch: refs/heads/master
remote: error: By default, updating the current branch in a non-bare repository
remote: error: is denied, because it will make the index and work tree inconsistent
remote: error: with what you pushed, and will require 'git reset --hard' to match
remote: error: the work tree to HEAD.
remote: error: 
remote: error: You can set 'receive.denyCurrentBranch' configuration variable to
remote: error: 'ignore' or 'warn' in the remote repository to allow pushing into
remote: error: its current branch; however, this is not recommended unless you
remote: error: arranged to update its work tree to match what you pushed in some
remote: error: other way.
remote: error: 
remote: error: To squelch this message and still keep the default behaviour, set
remote: error: 'receive.denyCurrentBranch' configuration variable to 'refuse'.
To C:/Development/GIT_Repo/Project
 ! [remote rejected] master -> master (branch is currently checked out)
error: failed to push some refs to 'C:/Development/GIT_Repo/Project'

Кто-нибудь знает, что может быть причиной этой ошибки?

На самом деле у вас теперь есть безопасный способ перейти к непроигрышному репо с Git 2.3.0 (февраль 2015 г.) иgit config receive.denyCurrentBranch=updateInstead:stackoverflow.com/a/28262104/6309 VonC
дублируется:stackoverflow.com/questions/2816369/… cregox
Возможный дубликатGit push error '[remote rejected] master -> master (branch is currently checked out)' Sören

Ваш Ответ

9   ответов
20

Перейдите в каталог repo /, в который вы нажимаете на удаленном компьютере, и введите

$ git config core.bare true
Это не работает. Хранилище остается пустым после вставки в него.
186

Существует два типа репозиториев:голый и не голый

Голые репозитории не имеют рабочей копии, и вы можете нажать на них. Это те типы репозиториев, которые вы получаете в Github! Если вы хотите создать пустой репозиторий, вы можете использовать

git init --bare

So, in short, you can't push to a non-bare repository (Изменить: Ну, вы не можете нажать на текущую извлеченную ветку хранилища. С пустым хранилищем вы можете нажать на любую ветку, поскольку ни одна из них не извлечена. Хотя это возможно, отправка в не пустые хранилища не распространена) , Что вы можете сделать, это извлечь и объединить из другого хранилища. Вот какpull request что вы можете увидеть в работах Github. Вы просите их оторваться от вас, и вы не толкаете их силой.


UpdateСпасибо VonC за указание на это в последних версиях git (в настоящее время 2.3.0),возможно нажатие на извлеченную ветку не-пустого репозитория, Тем не менее, вы все еще не можете подтолкнуть кdirty рабочее дерево, которое в любом случае не является безопасной операцией.

На самом деле, вы можете просто перейти в не-пустой репозиторий, просто не можете перейти в одну ветвь, котораяcurrently checked out.
Да! Это правильно, спасибо! Поскольку у меня есть около миллиона дел, я случайно клонировал рабочий каталог .... дох! Funky
На самом деле у вас теперь есть безопасный способ перейти к непроигрышному репо с Git 2.3.0 (февраль 2015 г.) иgit config receive.denyCurrentBranch=updateInstead:stackoverflow.com/a/28262104/6309
@skelly Ваш клон не голый, а копия на github. Таким образом, хотя у обоих клонов есть вся история, копия на github не проверяет коммит, но ваша копия делает это, чтобы вы могли работать!
На самом деле есть десятки других сценариев. Например, некоторые из моих репозиториев находятся только на моей рабочей станции и на моем ноутбуке (не код, а заметки, которые я делаю). На каждом у меня есть две ветки "рабочая станция" и "ноутбук". На рабочей станции я только проверяю «рабочую станцию» и нажимаю только на «рабочую станцию» ветка на ноутбуке (и наоборот).
1

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

В моей ситуации это было так. Удаление.git папка на пульте позволила мне нажать начальный коммит.
8

TLDR

  1. Pull & push again: git pull &&& git push.
  2. Still a problem? Push into different branch: git push origin master:foo and merge it on remote repo.
  3. Alternatively force the push by adding -f (denyCurrentBranch needs to be ignored).

По сути, ошибка означает, что ваш репозиторий не соответствует удаленному коду (его индекс и рабочее дерево не соответствуют тому, что вы нажали).

Обычно вы должныpull первым, чтобы получить последние изменения иpush это снова.

Если это не поможет, попробуйте перейти в другую ветку, например:

git push origin master:foo

затем объедините эту ветку в удаленном хранилище с master.

Если вы изменили некоторые прошлые коммиты преднамеренно черезgit rebase и вы хотите переопределить репо с вашими изменениями, вы, вероятно, хотите форсировать толчок, добавив-f/--force параметр (не рекомендуется, если вы этого не сделалиrebase). Если все еще не работает, вам нужно установитьreceive.denyCurrentBranch вignore на удалённом сервере, как подсказывает git-сообщение через:

git config receive.denyCurrentBranch ignore
38

Summary

Вы не можете нажать на одну извлеченную ветвь репозитория, потому что это будет связываться с пользователем этого репозитория таким образом, который, скорее всего, закончитсяloss of data and history, Но вы можете нажать на любую другую ветку того же хранилища.

Поскольку в пустых репозиториях никогда не проверяется какая-либо ветка, вы всегда можете перейти в любую ветку пустого репозитория.

Autopsy of the problem

Когда ветвь извлечена, фиксация добавит новый коммит с заголовком текущей ветки в качестве его родителя и переместит заголовок ветви в этот новый коммит.

Так

A ← B
    ↑
[HEAD,branch1]

становится

A ← B ← C
        ↑
    [HEAD,branch1]

Но если бы кто-то мог нажать на эту ветку между ними, пользователь получал бы то, что называет gitdetached head Режим:

A ← B ← X
    ↑   ↑
[HEAD] [branch1]

Теперь пользователь больше не находится в branch1, без явного запроса проверить другую ветку. Хуже того, пользователь сейчасoutside any branchи любой новый коммит будет простоdangling:

      [HEAD]
        ↓
        C
      ↙
A ← B ← X
        ↑
       [branch1]

Гипотетически, если в этот момент пользователь проверяет другую ветвь, то этот висячий коммит становится честной игрой для Git.garbage collector.

Я немного расширилstackoverflow.com/questions/2816369/…
12

Как уже существует репозиторий, работающий

git config --bool core.bare true

на удаленном репозитории должно хватить

From the core.bare documentation

Если true (bare = true), предполагается, что хранилище пустое, без рабочего каталога. В этом случае ряд команд, которым требуется рабочий каталог, будет отключен, например, git-add или git-merge (но вы сможете нажать на него).

Этот параметр автоматически определяется git-clone или git-init при создании хранилища. По умолчанию хранилище, оканчивающееся на «/. Git» предполагается, что он не голый (bare = false), в то время как все остальные репозитории предполагаются пустыми (bare = true).

3

ваше удаленное репо находится в той ветке, которую вы хотите нажать. Вы можете попробовать оформить еще одну ветку на удаленной машине. Я сделал это, после чего эти ошибки исчезли, и я добился успеха в своем удаленном репо. Обратите внимание, что я использую ssh для подключения собственного сервера вместо github.com.

91

сначала проверив, что на пульте не было ничего проверено (на самом деле это не предполагалось), а затем обнажил его:

$ git config --bool core.bare true

После этого git push работал нормально.

Это позволит протолкнуть историю изменений, но эти изменения не будут отражены в непроявленном репо.
Это исправление в одну строку, которое я искал ... но, может быть, объясните голые не голые репозитории, такие как ответ @shahbaz
13

git config --global receive.denyCurrentBranch updateInstead

Я настроил диск F: почти полностью для синхронизации между моим рабочим столом Windows 10 и ноутбуком с Windows 10 с помощью Git. Я запустил вышеупомянутую команду на обеих машинах.

Сначала я поделился F-диском рабочего стола в сети. Затем я смог клонировать его на своем ноутбуке, запустив:

F: git clone 'file://///DESKTOP-PC/f'

К сожалению, все файлы оказались в разделе & quot; F: \ f \ & quot; на моем ноутбуке, а не под F: \ напрямую. Но мне удалось вырезать и вставить их вручную. Git все еще работал с нового места позже.

Затем я попытался внести некоторые изменения в файлы на ноутбуке, зафиксировать их и перенести обратно на рабочий стол. Это не работало, пока я не запустил команду git config, упомянутую выше.

Обратите внимание, что я выполнил все эти команды из Windows PowerShell на обеих машинах.

ОБНОВЛЕНИЕ: у меня все еще были проблемы, подталкивающие изменения, в некоторых случаях. Наконец, я просто начал извлекать изменения, запустив на компьютере следующее, на которое я хочу получить последние коммиты:

git pull --all --prune

Похожие вопросы