Иногда git предлагает git rm --cached
удалить файл, иногда git reset HEAD file
. Когда я должен использовать что?
РЕДАКТИРОВАТЬ:
D:\code\gt2>git init
Initialized empty Git repository in D:/code/gt2/.git/
D:\code\gt2>touch a
D:\code\gt2>git status
# On branch master
#
# Initial commit
#
# Untracked files:
# (use "git add <file>..." to include in what will be committed)
#
# a
nothing added to commit but untracked files present (use "git add" to track)
D:\code\gt2>git add a
D:\code\gt2>git status
# On branch master
#
# Initial commit
#
# Changes to be committed:
# (use "git rm --cached <file>..." to unstage)
#
# new file: a
#
D:\code\gt2>git commit -m a
[master (root-commit) c271e05] a
0 files changed, 0 insertions(+), 0 deletions(-)
create mode 100644 a
D:\code\gt2>touch b
D:\code\gt2>git status
# On branch master
# Untracked files:
# (use "git add <file>..." to include in what will be committed)
#
# b
nothing added to commit but untracked files present (use "git add" to track)
D:\code\gt2>git add b
D:\code\gt2>git status
# On branch master
# Changes to be committed:
# (use "git reset HEAD <file>..." to unstage)
#
# new file: b
#
git rm
может как этап удаления , а также убрать из буфера в дополнение )rm
ли отменитьadd
? Как вы думаете, какrm
себя вести?git init
нетHEAD
сброса.rm
подразумевает удаление в контексте unix. Это не противоположность добавления в индекс. Функция удаления файлов не должна быть перегружена функциями изменения промежуточного состояния. Если есть детали реализации, которые делают их удобными для объединения, это просто указывает на отсутствие вдумчивого уровня абстракции в git, что сделало бы понятным юзабилити.Ответы:
git rm --cached <filePath>
не удаляет файл, он фактически удаляет файл (ы) из репозитория (при условии, что он уже был зафиксирован ранее), но оставляет файл в рабочем дереве (оставляя файл без отслеживания).git reset -- <filePath>
будет отменять любые поэтапные изменения для данного файла (ов).Тем не менее, если вы используете
git rm --cached
новый файл, который является промежуточным, он будет выглядеть так, как будто вы только что установили его, поскольку он никогда не был зафиксирован ранее.Обновление git 2.24
В этой новой версии git вы можете использовать
git restore --staged
вместоgit reset
. Смотрите Git Docs .источник
git rm --cached
unstages файл, но не удаляет его из рабочего каталога.git rm --cached <filePath>
для удаления некоторых файлов из репо после того, как они осознали, что их никогда не должно быть в репо: так что, скорее всего, запустите эту команду и затем добавите соответствующие файлыgitignore
. Я прав?unstage
командуgit
.git rm --cached
используется для удаления файла из индекса. В случае, если файл уже находится в репо,git rm --cached
он удалит файл из индекса, оставив его в рабочем каталоге, а коммит теперь также удалит его из репо. По сути, после коммита вы бы развернули файл и сохранили локальную копию.git reset HEAD file
(который по умолчанию использует--mixed
флаг) отличается тем, что в случае, когда файл уже находится в репо, он заменяет индексную версию файла на версию из репозитория (HEAD), фактически не внося изменений в него.В случае неверсионного файла он собирается удалить весь файл, поскольку его не было в HEAD. В этом аспекте
git reset HEAD file
и тоgit rm --cached
же самое, но они не совпадают (как объяснено в случае файлов уже в репо)К вопросу о
Why are there 2 ways to unstage a file in git?
- в git никогда не бывает только одного способа что-либо сделать. в этом вся прелесть :)источник
there is never really only one way to do anything in git. that is the beauty of it
- Хм ... почему? это всегда здорово, когда есть только один очевидный путь. это экономит много нашего времени и памяти в мозгу))Довольно просто:
git rm --cached <file>
заставляет git полностью прекратить отслеживание файла (оставляя его в файловой системе, в отличие от простогоgit rm
*)git reset HEAD <file>
unstages любые изменения, сделанные в файле с момента последнего коммита (но не отменяет их в файловой системе, в отличие от того, что может указывать имя команды **). Файл остается под контролем ревизии.Если файл ранее не контролировался ревизиями (то есть, вы растягиваете файл, который вы только что отредактировали
git add
в первый раз), тогда эти две команды имеют одинаковый эффект, следовательно, это «два способа сделать что-то» ».* Имейте в виду предостережение, которое @DrewT упоминает в своем ответе относительно
git rm --cached
файла, который был ранее передан в хранилище. В контексте этого вопроса о файле, который был только что добавлен и еще не зафиксирован, не о чем беспокоиться.** Мне было страшно долгое время использовать команду git reset из-за ее названия - и до сих пор я часто просматриваю синтаксис, чтобы убедиться, что я не облажался. ( обновление : я наконец-то нашел время, чтобы подвести итоги использования
git reset
страницы tldr , так что теперь у меня есть лучшая ментальная модель того, как это работает, и краткий справочник, когда я забываю некоторые детали.)источник
git rm <file> --cached
rm --cached
и нажатии любой, кто тянет одну и ту же ветку, будут фактически удалены файлы из их рабочего дерева.Этот поток немного староват, но я все же хочу добавить небольшую демонстрацию, так как это все еще не интуитивная проблема:
git reset HEAD
(без-q
) выдает предупреждение об измененном файле и его код выхода равен 1, что будет считаться ошибкой в скрипте.Edit:
git checkout HEAD to-be-modified to-be-removed
также работает для unstaging, но полностью удаляет изменения из рабочей областиОбновление git 2.23.0: время от времени команды меняются. Теперь
git status
говорит:... который работает для всех трех типов изменений
источник
Если вы случайно создали файлы, которые не хотели бы фиксировать, и хотите быть уверены, что сохраните изменения, вы также можете использовать:
это выполнит сброс в HEAD и повторно применяет ваши изменения, позволяя вам повторно подготовить отдельные файлы для фиксации. это также полезно, если вы забыли создать функциональную ветвь для запросов на извлечение (
git stash ; git checkout -b <feature> ; git stash pop
).источник
git stash
имеет другие связанные преимущества, потому что он создает записи в reflog, которые будут доступны в будущем. если сомневаетесь, продолжайте и сделайтеgit stash
(напримерgit stash save -u "WIP notes to self"
('-u' включает любые новые / неотслеживаемые файлы в коммите stash) ... затем попытайтесьgit reflog show stash
просмотреть список коммитов stash и их sha. Я рекомендую оболочку псевдоним какalias grs="git reflog show stash"
Эти 2 команды имеют несколько тонких отличий, если рассматриваемый файл уже находится в репозитории и находится под контролем версий (ранее зафиксирован и т. Д.):
git reset HEAD <file>
unstages файл в текущем коммите.git rm --cached <file>
будет также разархивировать файл для будущих коммитов. Это unstaged, пока это не будет добавлено снова сgit add <file>
.И есть еще одно важное отличие:
git rm --cached <file>
и отправки ветки на удаленный компьютер любой пользователь, извлекающий ветку с пульта, получит ФАКТИЧЕСКИ удаленный файл из своей папки, даже если в вашем локальном рабочем наборе файл просто не будет отслежен (то есть физически не удален из папки).Это последнее различие важно для проектов, которые включают в себя конфигурационный файл, в котором у каждого разработчика в команде разные настройки (т. Е. Разные базовые url, ip или настройки порта), поэтому, если вы используете
git rm --cached <file>
кого-то, кто тянет вашу ветку, придется вручную повторно создайте конфигурацию, или вы можете отправить их своим, и они смогут повторно отредактировать его обратно в свои настройки ip (и т. д.), потому что удаление влияет только на людей, которые тянут вашу ветку с пульта.источник
Допустим, вы прошли
stage
через весь каталогgit add <folder>
, но вы хотите исключить файл из поэтапного списка (т. Е. Список, который генерируется при запускеgit status
) и сохранить изменения в исключенном файле (вы работали над чем-то, и он не готов к фиксации, но Вы не хотите потерять свою работу ...). Вы можете просто использовать:git reset <file>
Когда вы запустите
git status
, вы увидите, что какие бы файлы вы ниreset
находились,unstaged
а остальные файлы выadded
все еще вstaged
списке.источник
1.
(используйте "git rm --cached ..." для удаления)
Git это система указателей
у вас еще нет коммита, чтобы изменить указатель на
Единственный способ «извлечь файлы из корзины, на которую указывают», - это удалить файлы, которые вы сказали git, чтобы следить за изменениями.
2.
git commit -ma
3.
(используйте «git reset HEAD ...» для удаления)
источник
git init
в первый раз.Я удивлен, что никто не упомянул git reflog ( http://git-scm.com/docs/git-reflog ):
Reflog - это история git, которая не только отслеживает изменения в репозитории, но также отслеживает действия пользователя (например, извлечение, возврат в другую ветку и т. Д.) И позволяет отменить эти действия. Таким образом, вместо того, чтобы unstaging файл, который был ошибочно подготовлен, где вы можете вернуться к точке, где вы не ставили файлы.
Это похоже на,
git reset HEAD <file>
но в некоторых случаях может быть более детальным.Извините - на самом деле не отвечаю на ваш вопрос, а просто указываю еще один способ нестандартных файлов, которые я использую довольно часто (например, мне очень нравятся ответы Райана Стюарта и Вальдириуса.);) Надеюсь, это поможет.
источник
Просто используйте:
git reset HEAD <filename>
Это unstages файл и сохраняет изменения, которые вы сделали в нем, так что вы можете, в свою очередь, изменить ветви, если хотите, и
git add
эти файлы вместо другой ветви. Все изменения сохранены.источник
Мне кажется, что
git rm --cached <file>
файл удаляется из индекса, не удаляя его из каталога, в котором обычная программаgit rm <file>
будет выполнять оба действия, точно так же, как ОСrm <file>
удаляет файл из каталога без удаления версий.источник
Только для версий 2.23 и выше,
Вместо этих предложений, вы можете использовать
git restore --staged <file>
для того, чтобыunstage
файл (ы).источник
--stage
а также--staged
.