Git: «В настоящее время нет ни на одной ветке». Есть ли простой способ вернуться на ветку, сохранив изменения?


202

Итак, я проделал некоторую работу в хранилище, и когда я собираюсь сделать коммит, я понимаю, что в настоящее время я не нахожусь ни в одной ветке.

Это часто случается при работе с подмодулями, и я могу решить это, но процесс утомителен, и я подумал, что должен быть более простой способ сделать это.

Есть ли простой способ вернуться на ветку, сохранив изменения?

Ответы:


214

Если вы не совершали:

git stash
git checkout some-branch
git stash pop

Если вы совершили и ничего не изменили с тех пор:

git log --oneline -n1 # this will give you the SHA
git checkout some-branch
git merge ${commit-sha}

Если вы совершили, а затем проделали дополнительную работу:

git stash
git log --oneline -n1 # this will give you the SHA
git checkout some-branch
git merge ${commit-sha}
git stash pop

16
Это не поможет, если вы уже совершили. Никаких отрицательных голосов, хотя это не было указано в вопросе.
Дин скорее

24
если вы уже зафиксировали: запишите хэш сделанного вами коммита (используйте git showили git rev-parse HEAD), переключитесь на ветку, а затем git cherry-pickдобавьте хеш коммита.
аракнид

7
Если зафиксировано, получите хэш последнего коммита. Оформите отделение, в котором вы хотите быть, иgit merge _hash_
Даниэль

БУДЬТЕ ДЕЙСТВИТЕЛЬНО ОСТОРОЖНЫ. Если вы совершили изменение и выполните следующие действия ... Вы увидите сообщение ... "Ваша ветвь и источник / мастер разошлись".
thinkanotherone

1
@thinkanotherone Если вы уже зафиксировали свои изменения, нечего было бы спрятать, а проверить другую ветку - это не конец света. Коммит, который вы только что сделали, все еще там, и вы можете объединить его с этой веткой, используя git merge <hash-of-the-commit-you-just-made>.
Эрик Б

160

это помогло мне

git checkout -b newbranch
git checkout master
git merge newbranch
git branch -d newbranch

25
Если вы уже сделали несколько коммитов, это то, что вам нужно сделать.
Бенджамин Оукс

Не пробовал, но похоже, что это сработает. Однако я думаю, что это маловероятный сценарий. Я полагаю, что большинство людей поймут, что они не в какой-либо ветке, прежде чем совершить коммит и использовать принятый ответ, чтобы это исправить.
Эрик Б

49
Вы были бы удивлены.
Эрик

@ErikB Я даже не знал, что есть такая вещь, как отсутствие на ветке. Этот ответ был очень полезным для меня.
Константин Шуберт

2
Прекрасный ответ, на самом деле просто набрал его и работал, в отличие от почти всего, с чем сталкиваются как новички в GIT - вы могли бы отметить, что newbranch - произвольное имя и не предназначен для замены хешем коммита
Toni Leigh

22
git checkout master

Это результат примерно так:

Warning: you are leaving 2 commits behind, not connected to
any of your branches:

1e7822f readme
0116b5b returned to clean django

If you want to keep them by creating a new branch, this may be a good time to do so with:
git branch new_branch_name 1e7822f25e376d6a1182bb86a0adf3a774920e1e

Итак, давайте сделаем это:

git merge 1e7822f25e376d6a1182bb86a0adf3a774920e1e

Я не пробовал, но, похоже, все будет работать нормально. Я полагаю, что если вы запустите git gcмежду этими двумя командами, вы потеряете эти коммиты, но если вы не запустите их git gcавтоматически, это должен быть довольно безопасный подход. Я бы все равно согласился с ответом Бабая, но если вы хотите уберечь себя от написания двух дополнительных команд, я думаю, что это правильный путь.
Эрик Б

Я покинул главную ветку в какой-то момент, что я не совсем уверен. Я передал свои изменения, никаких изменений на мастере не было. Эти инструкции привели мои изменения в основную ветку и все хорошо.
Матти Йокипии

+1 Я нервничал из-за того, что проверял другую ветку, оставляя коммиты, потому что это сообщение добавило уверенности, чтобы пойти на это.
J-Dizzle

11

Оставив другой путь здесь

git branch newbranch
git checkout master 
git merge newbranch 

3
@ErikB Возможно, он сделал несколько коммитов. В этом случае, смотрите ответ Бабая.
Бенджамин Оукс

@BenjaminOakes Это может быть так, но эти команды git даже недействительны.
Эрик Б

@ErikB Определенно верно. :) Ответ Бабая является верной формой того, что Алекс, похоже, пытался сделать.
Бенджамин Оукс

9

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

Отредактировано, чтобы добавить:

Одним из способов является извлечение определенной ветви подмодуля, когда вы добавляете его с флагом -b:

git submodule add -b master <remote-repo> <path-to-add-it-to>

Другой способ - просто зайти в каталог подмодулей и просто проверить его.

git checkout master

1
Не могли бы вы сказать мне, как это сделать?
Эрик Б

Есть ли способ обновить существующий субмодуль в этом режиме ветки по умолчанию? обновить gitmodulesвозможно?
Герцель Гиннесс

@HertzelGuinness Не совсем. Подмодуль проверяется при определенном коммите ша. Ветвь - это просто указатель на ша, и тот, на который он указывает, может измениться. Это бесполезно, потому что не останавливает состояние извлеченного субмодуля. Проверка ветки - это просто удобство, если вы вносите изменения в подмодуль.
Абизерн

5

Один из способов оказаться в этой ситуации - выполнить ребаз из удаленной ветки. В этом случае новые коммиты наведены на HEADноmaster не указывает на них - он указывает на то, где он был до того, как вы перебазировали другую ветку.

Вы можете сделать это своим новым master, выполнив:

git branch -f master HEAD
git checkout master

Это принудительно обновляет, masterчтобы указать HEAD(без включения вас master), а затем переключается на master.


Работал отлично, как требуется. Я уже поставил файлы и зафиксировал, но не смог нажать из-за вышеуказанной ошибки. Выше двух строк кода работал отлично и подтолкнул мой код, как ожидалось.
непобедимый

4

Я недавно столкнулся с этой проблемой снова. Прошло много времени с тех пор, как я последний раз работал с подмодулями, и, узнав больше о git, я понял, что достаточно просто проверить ветку, в которой вы хотите выполнить коммит. Git сохранит рабочее дерево, даже если вы его не спрятали.

git checkout existing_branch_name

Если вы хотите работать в новой ветке, это должно работать для вас:

git checkout -b new_branch_name

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

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


2

Может работать следующий метод:

git rebase HEAD master
git checkout master

Это отменит текущие изменения HEAD поверх мастера. Затем вы можете переключить ветку.


Альтернативный способ - сначала оформить заказ:

git checkout master

Затем Git должен отобразить SHA1 ваших отдельных коммитов, затем вы можете выбрать их, например

git cherry-pick YOURSHA1

Или вы также можете объединить последнюю версию:

git merge YOURSHA1

Для того, чтобы увидеть все ваши коммиты из различных отраслей (чтобы убедиться , что вы имеете их), выполните команду: git reflog.


0

Я знаю, что сказал Бабею в 2012 году, что я подумал, что вряд ли кто-то не поймет, что они не на ветке и не совершают. Это только что случилось со мной, поэтому я должен признать, что был неправ, но, учитывая, что до 2016 года это случилось со мной, можно утверждать, что это на самом деле маловероятно.

В любом случае, создание новой ветки, на мой взгляд, излишне. Все, что вам нужно сделать, это:

git checkout some-branch
git merge commit-sha

Если вы не скопировали commit-sha перед проверкой другой ветки, вы можете легко найти ее, выполнив:

git reflog

это редкая (маловероятная) проблема для одного человека. Это не случалось со мной с 2012 года. Но если вы умножите шанс на количество пользователей git ... Это будет очень вероятно. Это может случиться каждый день с кем-то. :)
малыш
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.