Git diff говорит, что подпроект грязный

Я только что запустил git diff, и я получаю следующий вывод для всех моих 10 подмодулей

diff --git a/.vim/bundle/bufexplorer b/.vim/bundle/bufexplorer
--- a/.vim/bundle/bufexplorer
+++ b/.vim/bundle/bufexplorer
@@ -1 +1 @@
-Subproject commit 8c75e65b647238febd0257658b150f717a136359
+Subproject commit 8c75e65b647238febd0257658b150f717a136359-dirty

Что это значит? Как это исправить?

Ответ 1

Как упоминалось в сообщении блога Mark Longair Git Объяснение субмодулей,

Версии 1.7.0 и более поздние из git содержат раздражающие изменения в поведении подмодуля git.
Субмодули теперь считаются грязными, если у них есть модифицированные файлы или файлы без следа, тогда как раньше это было бы только в том случае, если HEAD в подмодуле указал на неправильную фиксацию.

Значение знака плюса (+) в выходе подмодуля git изменилось, и в первый раз, когда вы сталкиваетесь с этим, требуется немного времени, чтобы понять, что происходит не так, например, глядя через изменения или используя git bisect в git.git, чтобы найти изменение. Было бы гораздо добрее, чтобы пользователи вводили другой символ для "в указанной версии, но грязный".

Вы можете исправить это:

  • либо совершать или отменять изменения/эволюции в каждом из ваших подмодулей, прежде чем возвращаться к родительскому репо (где diff не должен сообщать "грязные" файлы больше). Чтобы отменить все изменения вашего подмодуля только cd в корневой каталог вашего подмодуля и сделать git checkout .

    dotnetCarpenter комментарии, которые вы можете сделать: git submodule foreach --recursive git checkout .

  • или добавьте --ignore-submodules к вашему git diff, чтобы временно игнорировать эти "грязные" подмодули.

Новое в git версии 1.7.2

Как Noam комментарии ниже, этот вопрос упоминает, что, поскольку git версия 1.7.2, вы можете игнорировать грязные подмодули с помощью:

git status --ignore-submodules=dirty

Ответ 2

Также удаление подмодуля, а затем запуск git submodule init и git submodule update, очевидно, сделает трюк, но может не всегда быть подходящим или возможным.

Ответ 3

РЕДАКТИРОВАТЬ: Этот ответ (и большинство других) устарели; см. ответ Devpool вместо этого.


Первоначально не было опций конфигурации, чтобы сделать "git diff --ignore-submodules" и "git status --ignore-submodules" глобальным значением по умолчанию (но см. Также " Установка флагов git default в командах"). Альтернативой является установка параметра конфигурации ignore умолчанию для каждого отдельного подмодуля, который вы хотите игнорировать (как для git diff и для git status), либо в файле .git/config (только локальный), либо в .gitmodules (будет .gitmodules git), Например:

[submodule "foobar"]
    url = [email protected]:foo/bar.git
    ignore = untracked

ignore = untracked чтобы игнорировать только неотслеживаемые файлы, ignore = dirty чтобы также игнорировать измененные файлы, и ignore = all чтобы игнорировать также коммиты. По-видимому, нет способа подстановить его для всех подмодулей.

Ответ 4

Это так, потому что указатель, который у вас есть для подмодуля, не является тем, что действительно находится в каталоге подмодулей. Чтобы исправить это, вы должны снова запустить git submodule update:

Ответ 5

git submodule foreach --recursive git checkout .

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

Таким образом, я мог бы перейти к подмодулю, и статус git показал мне, что мой HEAD был отсоединен → git checkout master, git status, чтобы снова просмотреть измененный файл, git checkout > filename <, git тянуть и все отлично.

Ответ 6

Я закончил удаление каталога подмодулей и снова инициализировал его

cd my-submodule
git push
cd ../
rm -rf my-submodule
git submodule init
git submodule update

Ответ 7

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

git config --global diff.ignoreSubmodules dirty

Это добавит следующую конфигурационную опцию в вашу локальную конфигурацию git:

[diff]
  ignoreSubmodules = dirty

Дополнительную информацию можно найти здесь

Ответ 8

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

Чтобы отключить файловый режим в подмодуле, вы можете отредактировать /.git/modules/path/to/your/submodule/config и добавить

[core]
  filemode = false

Если вы хотите игнорировать все грязные состояния, вы можете установить свойство ignore = dirty в файле /.gitmodules, но я думаю, что лучше отключить только файл файл.

Ответ 9

В моем случае я не был уверен, что вызвало это, но я знал, что просто хотел, чтобы подмодули были reset до их последней удаленной фиксации и выполнялись с ним. Это включало в себя объединение ответов от пары разных вопросов:

git submodule update --recursive --remote --init

Источники:

Как вернуть мои изменения в подмодуль git?

Простой способ получить последние из всех подмодулей git