'git status' репозитория только для извлечения, говорящий о том, что ветка впереди origin / master Зачем? - PullRequest
10 голосов
/ 09 сентября 2011

Итак, вот такая ситуация:

$ git status
# На главном ветке
# Ваша ветвь опережает 'origin / master' по [x] коммитам.
#

В SO уже есть несколько вопросов по этому поводу, но, похоже, ни один из них не касается конкретно того типа сценария, который у меня есть. Этот ответ на один из вопросов ближе всего подходит, но не углубляется в детали.

Я просто процитирую его дословно:

Если вы получитеэто сообщение после выполнения «git pull remote branch», попробуйте добавить «git fetch».

Кажется, что Fetch обновляет локальное представление удаленной ветви, что не обязательно происходит, когда вы делаете"git pull remote branch".

Этот совет действительно работает.Но "не обязательно случится?"Почему бы и нет?Мне нужно это понять.Что такое pull не делает?

Я не хочу отвечать на этот вопрос, поэтому вот мой сценарий в деталях:

Три компьютера задействованы.Mac, на котором я работаю, мой домашний сервер, на котором находится git-репо (то есть origin / master), и учетная запись Webfaction, полученная с этого сервера.

Я совершаю коммиты и git push origin master только на Mac.Единственная команда, которая когда-либо запускается на Webfaction как часть обычного рабочего процесса, это git pull origin master (как часть сценария развертывания Fabric).Я не изменяю код там.Я одинокий разработчик, так что никто другой.

Время от времени я захожу в Webfaction и проверяю некоторые вещи, включая git status.Неизбежно, я всегда получаю сообщение «Ваша ветка впереди ...».Запуск git fetch убирает сообщение.

Я собираюсь добавить git fetch к сценарию Fabric, чтобы решить эту проблему, но я хочу знать, почему это необходимо сделать, особенно втолько клон оригинала / мастера.Я не очень разбираюсь в Git, хотя ежедневно использую базовые функциональные возможности, поэтому приветствуем объяснения, удобные для новичков.

Обновите по запросу, соответствующие биты из config:

[remote "origin"]
    fetch = +refs/heads/*:refs/remotes/origin/*
    url = git@[server_address]:[path/to/repo.git]
[branch "master"]
    remote = origin
    merge = refs/heads/master

Ответы [ 4 ]

9 голосов
/ 09 сентября 2011

Ок, с самого начала вы все делаете правильно. Я думаю, что комментарий, который вы добавили ранее, является довольно хорошим объяснением:

Проще говоря, "git pull" выполняет "git fetch" с последующим "мерзавец слияния"

Вот как я об этом думаю. Таким образом, вам не нужно вызывать git fetch после прямой линии вверх git pull - но, я почти гарантирую вам, это прекрасно работает на всем, кроме ЗАКЛЮЧЕНИЯ master.

В одном из связанных постов сказано удалить следующую строку:

[remote "origin"]
    fetch = +refs/heads/*:refs/remotes/origin/* <--- Remove this

И это должно решить эту проблему - однако я не могу объяснить, почему это работает. Это очень сложно исследовать, но я думаю, что когда вы вызываете fetch, ваш git config фактически указывает, что именно захватить. Когда вы запускаете pull, я не уверен, что он считает, что master синхронизирован.

Я могу гарантировать вам, что если вы сделаете это из другой ветки, не являющейся мастером, вы не увидите эту проблему. Надеюсь, один из git-гуру сможет подробно объяснить строку fetch в конфигурации.

Кроме того, я бы порекомендовал выполнить следующую команду, которая устанавливает HEAD для удаленного репозитория, чтобы обеспечить его синхронизацию с локальным: git push -u origin master


Вот еще один интересный вопрос:

с трудом разбирается в git-fetch


Хорошо, я проверил это на одном из моих рабочих процессов и обнаружил следующее.

Когда вы выполняете git pull origin master на удаленном сервере, в каталоге .git/ есть файл, который указывает, где находится ваш HEAD. Два файла для записи:

ORIG_HEAD

FETCH_HEAD

Вы заметите, что ваш FETCH_HEAD правильный, но ORIG_HEAD показывает старый коммит, следовательно, причина, по которой вы получаете Ahead by x. Когда вы запустите git fetch, вы на самом деле исправите ссылку в ORIG_HEAD, и все вернется к норме. Я смотрю, как изменить строку fetch в конфигурации, чтобы исправить это поведение.

6 голосов
/ 15 сентября 2013

Если вы запустите git pull origin вместо git pull origin master, проблема с сообщением Your branch is ahead of 'origin/master' by ... commits. не возникнет.

1 голос
/ 09 сентября 2011

См. Этот вопрос: В чем разница между 'git pull' и 'git fetch'?

AFAIK git pull будет смотреть на ветку в начале и сбрасывать изменения,Но локальный индекс филиала не актуален.git fetch обновит индекс ветки, чтобы он понимал, что там должно быть.(в основном то, на что ссылался ответ, на который вы ссылались)

Я всегда делаю git fetch перед git pull.На самом деле я делаю git fetch каждый раз, когда собираюсь что-то делать с удаленными ветвями.

С этим вопросом также связано это очень хорошее описание git fetch, pull и merge.http://longair.net/blog/2009/04/16/git-fetch-and-merge/

0 голосов
/ 15 сентября 2015

В моем случае - у меня было две ветви в Origin, и каждый раз, когда я выполнял git pull, это показывало, что я опережал origin / master на x.Даже после жесткого сброса его к источнику / мастеру, как показано в Сброс ветки локального репозитория, чтобы он был похож на удаленный репозиторий HEAD .

Решение возникло, когда я просто запустил git fetch, и оно перенесло мою ветку разработки на мой рабочий сервер.

...