Git Pull, игнорируя локальные изменения?


489

Есть ли способ сделать, git pullчто игнорирует любые локальные изменения файла, не удаляя каталог и не выполняя git clone?


17
Под "игнорирует" вы подразумеваете "перезаписывает"?
Каскабель

@Cascabel Это означает отменить все локальные изменения, отменить все локальные коммиты, удалить все локальные новые файлы и каталоги, восстановить все локально удаленные файлы и каталоги и т. Д. Короче, просто запустите команду, как будто rm -rf local_repo && git clone remote_url.
Виктор

Ответы:


820

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

git reset --hard
git pull

Если есть неотслеживаемые локальные файлы, вы можете использовать их git cleanдля удаления. Используется git clean -fдля удаления неотслеживаемых файлов, -dfдля удаления неотслеживаемых файлов и каталогов, а также -xdfдля удаления неотслеживаемых или игнорируемых файлов или каталогов.

С другой стороны, если вы хотите как-то сохранить локальные модификации, вы бы использовали stash, чтобы скрыть их перед извлечением, а затем повторно применить их:

git stash
git pull
git stash pop

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


4
Если после того, как git resetваши файлы по-прежнему отличаются от удаленного, прочитайте stackoverflow.com/questions/1257592/…
полковник Паник

3
Git - самая странная вещь. Git сбросить - трудно сделано. Тогда статус git: Ваша ветка впереди на 2 коммита.
Шайлен

21
@shailenTJ «Локальные изменения» здесь означают незафиксированные изменения, а не локальные изменения. git reset --hardвлияет на первое, а не второе. Если вы хотите полностью восстановить состояние пульта, git reset --hard origin/<branch>- но часто и в этом случае эти два коммита, по которым вы опережаете источник, - это работа, которую вы сделали, а не то, что вы хотите выбросить.
Каскабель

2
Так что это то же самое, что уничтожение локального репозитория и повторная загрузка, верно? Я просто хочу быть в состоянии заставить тянуть и переписать изменения для удобства. В 99% случаев я получаю это сообщение об ошибке, когда я случайно что-то испортил локально и просто хочу начать заново с репо.
Судо

Что делать, если вы не можете не иметь локального изменения против головы? Например, репо было сделано в чувствительной к регистру файловой системе и клонировано в нечувствительной к регистру файловой системе, и есть 2 файла с одинаковым именем в другом корпусе?
xster

305

Для меня сработало следующее:

(1) Сначала получите все изменения:

$ git fetch --all

(2) Затем сбросьте мастер:

$ git reset --hard origin/master

(3) Извлечение / обновление:

$ git pull

22
Отлично работал для меня, когда было много проблем с топ-ответом. Спасибо!
0x0

6
это работает даже тогда, когда вы совершаете локальные изменения, но все же хотите вернуться
agsachin

16
Это должен быть главный ответ :)
Purus

5
@Marco Servetto: Сначала вы получаете все изменения в git, но пока не применяете их. Затем вы сбрасываете мастер до последнего состояния (обновлено). Если вы пропустите первый шаг, вы вернете изменения к старому мастеру (локальному). Из моего опыта, как я это описал, никогда не возникает проблем. Все остальные попытки делаю в конце.
Артур Барсегян

1
Это сработало для меня, я хотел игнорировать все свои локальные изменения, включая восстановление удаленных файлов
Нери

28

Вы просто хотите команду, которая дает точно такой же результат, как rm -rf local_repo && git clone remote_url, верно? Я тоже хочу эту функцию. Интересно, почему git не предоставляет такую ​​команду (например, git recloneили git sync), а svn не предоставляет такую ​​команду (например, svn recheckoutили svn sync).

Попробуйте следующую команду:

git reset --hard origin/master
git clean -fxd
git pull

Это то, что действительно работает, даже если у вас уже есть локальные коммиты, которые вы хотите удалить.
Юрий Генсев

5
Предупреждение, ребята! git clean -fxdудаляет файлы .gitignoreтакже.
Рамеш Нави

@RameshNavi Конечно. Это именно то, что нужно. Нужно иметь более быстрый способ его клонирования, то есть удалить весь локальный репозиторий, а затем клонировать его.
Виктор

27

Команда ниже не будет работать всегда . Если вы просто:

$ git checkout thebranch
Already on 'thebranch'
Your branch and 'origin/thebranch' have diverged,
and have 23 and 7 different commits each, respectively.

$ git reset --hard
HEAD is now at b05f611 Here the commit message bla, bla

$ git pull
Auto-merging thefile1.c
CONFLICT (content): Merge conflict in thefile1.c
Auto-merging README.md
CONFLICT (content): Merge conflict in README.md
Automatic merge failed; fix conflicts and then commit the result.

и так далее...

Чтобы действительно начать, загрузив thebranch и перезаписывать все ваши локальные изменения, просто сделать:


$ git checkout thebranch
$ git reset --hard origin/thebranch

Это будет работать просто отлично.

$ git checkout thebranch
Already on 'thebranch'
Your branch and 'origin/thebranch' have diverged,
and have 23 and 7 different commits each, respectively.

$ git reset --hard origin/thebranch
HEAD is now at 7639058 Here commit message again...

$ git status
# On branch thebranch
nothing to commit (working directory clean)

$ git checkout thebranch
Already on 'thebranch'

4
ДА. Это то, что мне нужно для окончательного подхода «не представляй, что такое локальный». Спасибо. :)
Adambean


8

Посмотрите на git stash, чтобы поместить все ваши локальные изменения в «stash-файл» и вернуться к последнему коммиту. В этот момент вы можете применить свои скрытые изменения или отменить их.


8

Если вы используете Linux:

git fetch
for file in `git diff origin/master..HEAD --name-only`; do rm -f "$file"; done
git pull

Цикл for удалит все отслеживаемые файлы, которые были изменены в локальном репо, поэтому git pullбудет работать без проблем.
Самое приятное в этом то, что только файлы отслеживания будут перезаписаны файлами в репо, все остальные файлы останутся нетронутыми.


Я думаю, что вы имели в виду "отслеживаемые файлы", что именно то, что мне нужно, спасибо.
Али

любой эквивалент для Powershell?
Earlee

8

Кратчайший способ сделать это:

git pull --rebase --autostash

не знал --autostashраньше, спасибо!
Широ

7

это сработало для меня

git fetch --all
git reset --hard origin/master
git pull origin master

с принятым ответом я получаю конфликтные ошибки


Это очень похоже на ответ Артура Барсегяна 2015 года ... но я все же хотел бы знать, какова цель 3-й команды: рабочие файлы изменились после 2-й команды, а 3-я команда говорит: «Уже в курсе» "
Майк Грызун

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

Интересно. Может быть, версия вещь. Я на GIT 2.7.4. Но я также только что увидел новый комментарий от Артура Барсегяна: «В противном случае вы могли бы работать над случайно устаревшим мастером».
Майк Грызун

возможно, но единственное, что я могу сказать, это «это работало для меня, когда не было другого решения», так что это могло бы помочь другим
Пабло Пазос


2

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

git fetch && git merge --ff-only origin/master

Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.