Зафиксировать только часть файла в Git
-
23-08-2019 - |
Вопрос
Когда я вношу изменения в файл в Git, как я могу зафиксировать только некоторые изменения?
Например, как я могу зафиксировать только 15 строк из 30, которые были изменены в файле?
Решение
Вы можете использовать git add --patch <filename>
(или -p
короче), и git начнет разбивать ваш файл на, по его мнению, разумные «куски» (части файла).Затем он задаст вам такой вопрос:
Stage this hunk [y,n,q,a,d,/,j,J,g,s,e,?]?
Вот описание каждого варианта:
- й подготовить этот кусок для следующего коммита
- н не загружайте этот кусок для следующего коммита
- д покидать;не ставьте этот кусок или любой из оставшихся кусков
- а подготовить этот кусок и все последующие фрагменты в файле
- д не размещайте этот фрагмент или любой из последующих фрагментов в файле
- г выберите кусок, к которому нужно перейти
- / найти кусок, соответствующий данному регулярному выражению
- дж оставьте этот кусок нерешенным, посмотрите следующий нерешенный кусок
- Дж оставьте этот кусок нерешенным, посмотрите следующий кусок
- к оставьте этот кусок нерешенным, см. предыдущий нерешенный кусок
- К оставьте этот кусок нерешенным, см. предыдущий кусок
- с разделить текущий фрагмент на более мелкие фрагменты
- е вручную отредактировать текущий кусок
- ? распечатать помощь
Если файла еще нет в репозитории, вы можете сначала сделать git add -N <filename>
.После этого вы можете продолжить git add -p <filename>
.
После этого вы можете использовать:
git diff --staged
чтобы проверить, что вы внесли правильные измененияgit reset -p
удалить ошибочно добавленные фрагментыgit commit -v
для просмотра вашего коммита во время редактирования сообщения о коммите.
Обратите внимание, что это сильно отличается от git format-patch
команда, целью которой является анализ данных фиксации в .patch
файлы.
Ссылка на будущее: Инструменты Git — интерактивная подготовка
Другие советы
Вы можете использовать git add --interactive
или git add -p <файл>
, а потом git commit
(нет git commit -a
);видеть Интерактивный режим в git-добавить man-страницу или просто следуйте инструкциям.
Современный Git также имеет git commit --interactive
(и git commit --patch
, который является ярлыком для параметра исправления в интерактивной фиксации).
Если вы предпочитаете делать это из графического интерфейса, вы можете использовать git-gui.Вы можете просто отметить фрагменты, которые хотите включить в коммит.Лично мне это проще, чем использовать git add -i
.Другие графические интерфейсы git, такие как QGit или GitX, также могут иметь эту функциональность.
мерзавец графический интерфейс обеспечивает эту функциональность в представлении различий.Просто щелкните правой кнопкой мыши интересующую вас строку(и), и вы увидите пункт меню «подготовить эту строку для фиксации».
я полагаю, что git add -e myfile
это самый простой способ (по крайней мере, я предпочитаю), поскольку он просто открывает текстовый редактор и позволяет вам выбрать, какую строку вы хотите проиндексировать, а какую нет.Что касается команд редактирования:
добавленный контент:
Добавленный контент представлен строками, начинающимися с «+».Вы можете предотвратить создание дополнительных строк, удалив их.
удаленный контент:
Удаленный контент представлен строками, начинающимися с «-».Вы можете предотвратить их поэтапное удаление, преобразуя «-» в « » (пробел).
измененное содержимое:
Измененный контент представлен строками «-» (удаление старого контента), за которыми следуют строки «+» (добавление заменяющего контента).Вы можете предотвратить постановку модификации путем преобразования "-" линий в "" и удаления строк "+".Помните, что изменение только половины пары может привести к запутанным изменениям в индексе.
Все подробности о git add
доступны на git --help add
Если вы используете vim, вы можете попробовать отличный плагин под названием беглец.
Вы можете увидеть разницу файла между рабочей копией и индексом с помощью :Gdiff
, а затем добавьте в индекс строки или фрагменты, используя классические команды vim diff, такие как dp
.Сохраните изменения в индексе и зафиксируйте их с помощью :Gcommit
, и вы сделали.
Очень хорошие вступительные скринкасты здесь (см. особ. часть 2).
Я настоятельно рекомендую использовать Исходное дерево из Атласиан.(Это бесплатно.) Это делает это тривиальным.Вы можете быстро и легко создавать отдельные фрагменты кода или отдельные строки кода.
Стоит отметить, что использовать git add --patch
для новый файл вам нужно сначала добавить файл в индекс с помощью git add --intent-to-add
:
git add -N file
git add -p file
Если у меня много изменений и в конечном итоге я создам несколько коммитов из этих изменений, я хочу временно сохранить свою отправную точку, прежде чем приступать к промежуточной подготовке.
Так:
$ git stash -u
Saved working directory and index state WIP on master: 47a1413 ...
$ git checkout -p stash
... step through patch hunks
$ git commit -m "message for 1st commit"
$ git checkout -p stash
... step through patch hunks
$ git commit -m "message for 2nd commit"
$ git stash pop
Ответ Почемумарра — это то, что я обычно делаю, за исключением того, что иногда происходит много изменений, и я могу сказать, что могу допустить ошибку при постановке вещей, и мне нужно состояние фиксации, к которому я могу вернуться для второго прохода.
Если вы используете emacs, взгляните на Магит, который предоставляет интерфейс git для emacs.Он поддерживает постановка красавчиков (части файлов) вполне хорошо.
Интеллидж ИДЕЯ (и я думаю, что все остальные продукты этой серии) имеют встроенную поддержку частичных коммитов, начиная с версии 2018.1.
Как и в случае с ответом jdsumsion, вы также можете спрятать свою текущую работу, но затем использовать инструмент difftool, например meld, чтобы извлечь выбранные изменения из тайника.Таким образом, вы даже можете очень легко редактировать куски вручную, что немного затруднительно, когда вы git add -p
:
$ git stash -u
$ git difftool -d -t meld stash
$ git commit -a -m "some message"
$ git stash pop
Использование метода stash дает вам возможность проверить, работает ли ваш код, прежде чем зафиксировать его.
Для тех, кто использует Расширения Git:
В окне «Зафиксировать» выберите файл, который вы хотите частично зафиксировать, затем выберите текст, который вы хотите зафиксировать, на правой панели, затем щелкните правой кнопкой мыши по выделенному фрагменту и выберите «Поместить выбранные строки» в контекстное меню.
vim-gitgutter Плагин может создавать фрагменты, не выходя из редактора Vim, используя
:GitGutterStageHunk
Помимо этого, он предоставляет другие интересные функции, такие как столбец знаков различий, как в некоторых современных IDE.
Если только часть куска должна быть поставлена Вим-беглец
:Gdiff
позволяет выбрать диапазон видимости, затем :'<,'>diffput
или :'<,'>diffget
для поэтапного/отмененного изменения отдельных строк.
Опробовал git add -p filename.x
, но на Mac я нашел gitx (http://gitx.frim.nl/ или https://github.com/pieter/gitx), чтобы было намного проще зафиксировать именно те строки, которые я хотел.
С TortoiseGit:
щелкните правой кнопкой мыши по файлу и используйте
Context Menu → Restore after commit
.Это создаст копию файла в том виде, в каком он есть.Затем вы можете отредактировать файл, например.в TortoiseGitMerge и отмените все изменения, которые вы не хотите фиксировать.После сохранения этих изменений вы можете зафиксировать файл.
Добавляя к предыдущему ответу, если вы предпочитаете использовать командную строку, введите git add -e myfile
дает вам возможность выбирать построчно то, что вы хотите зафиксировать, поскольку эта команда откроет редактор с различиями, например:
Как вы знаете, строки, начинающиеся с +
являются дополнениями, строками, начинающимися с -
являются удалениями.Так:
- Чтобы не создавать дополнение, просто удалите эту строку.
- Чтобы не инициировать удаление, просто замените
-
с пространством.
Это то, что git add -h
говорит о добавлении файлов таким способом (исправление файлов):
добавленный контент Добавленный контент представлен строками, начинающимися с «+».Вы можете предотвратить постановку любых линий добавления, удаляя их.
удаленный контент:Удаленный контент представлен строками, начинающимися с «-».Вы можете предотвратить постановку их удаления, преобразуя «-» в «» (пространство).
измененное содержимое: Модифицированный контент представлен с помощью линий «-» (удаление старого контента), за которыми следуют строки «+» (добавление содержимого замены).Вы можете предотвратить постановку модификации путем преобразования "-" линий в "" и удаления строк "+".Остерегайтесь, что изменение только половины пары, вероятно, внесет запутанные изменения в индексе.
Осторожность: не меняйте содержимое файла, это не лучшее место для этого.Просто измените операторы удаленных или добавленных строк.
Для Атом пользователи, пакет github включает в себя интерактивную постановку в стиле git gui
.Ярлыки см. в пакете документация.
Использование Atom позволяет работать с темой, имеющей темный фон (по умолчанию git gui
имеет белый фон).
Прошло 10 лет с тех пор, как был задан этот вопрос.И я надеюсь, что этот ответ будет кому-то полезен.Как указано в ответе здесь, где графический интерфейс невозможен, Эндрю Шадура расширение крекорда помогает открыть окно ncurses, в котором мы можем выбрать строки для фиксации.
Настройте расширение следующим образом:
git clone https://github.com/andrewshadura/git-crecord
cd git-crecord
./setup.py install
ln -s $PWD/git-crecord ~/.local/bin/git-crecord
перейдите в ваш репозиторий git и вызовите его следующим образом:
git crecord
Это приведет к появлению интерфейса ncurses, который можно использовать, как показано ниже.Нажатие следующих клавиш в окне ncurses приведет к определенным действиям:
f hunk toggle fold (arrow keys can also be used)
space toggle hunk selection
a toggle commit or amend
c confirm and open commit window
Скринкаст, показывающий пример использования
Для emacs также есть гисум
git-meld-индекс -- цитата с сайта:
git-meld-index запускает meld или любой другой инструмент git difftool (kdiff3, Diffuse и т. д.), чтобы вы могли в интерактивном режиме вносить изменения в индекс git (также известный как область подготовки git).
Это похоже на функциональность git add -p и git add --interactive.В некоторых случаях использовать Meld проще/быстрее, чем git add -p.Это потому, что объединение позволяет вам, например:
- увидеть больше контекста
- посмотреть внутристрочные различия
- редактируйте вручную и смотрите «живые» обновления различий (обновляются после каждого нажатия клавиши)
- перейдите к изменению, не говоря «н» каждому изменению, которое вы хотите пропустить
Применение
В репозитории git запустите:
git meld-index
Вы увидите всплывающее окно meld (или настроенного вами git difftool):
ЛЕВЫЙ:временный каталог, содержащий файлы, скопированные из вашего рабочего дерева
ВЕРНО:временный каталог с содержимым index.Сюда также входят файлы, которых еще нет в индексе, но которые изменены или не отслеживаются в рабочей копии — в этом случае вы увидите содержимое файла из HEAD.
Редактируйте индекс (правая часть), пока не будете довольны.Не забывайте сохраняться, когда это необходимо.
Когда вы закончите, закройте объединение, и git-meld-index обновит индекс, чтобы он соответствовал содержимому временного каталога в правой части объединения, которое вы только что отредактировали.
Как один ответ выше показано, вы можете использовать
git add --patch filename.txt
или краткая форма
git add -p filename.txt
...но для файлов, уже находящихся в вашем репозитории, в s гораздо лучше использовать флаг --patch непосредственно в команде фиксации (если вы используете достаточно последнюю версию git):
git commit --patch filename.txt
...или, опять же, краткая форма
git commit -p filename.txt
...а затем с помощью упомянутых клавиш (y/n и т. д.) для выбора строк, которые будут включены в фиксацию.
Если он включен Windows
платформа, на мой взгляд git gui
очень хороший инструмент для stage
/commit
несколько строк из unstaged
файл
1.Ханк мудрый:
- Выберите файл из
unstagged Changes
раздел - Щелкните правой кнопкой мыши фрагмент кода, который необходимо подготовить.
- Выбирать
Stage Hunk for commit
2.Линия мудрая:
- Выберите файл из
unstagged Changes
раздел - Выберите линию/строки для подготовки
- Щелкните правой кнопкой мыши и выберите
Stage Lines for commit
3.Если вы хотите подготовить весь файл, за исключением пары строк:
- Выберите файл из
unstagged Changes
раздел - Нажимать
Ctrl+T (Stage file to commit)
- Выбранный файл теперь перемещается в
Staged Changes
Раздел - Выберите линию/строки для подготовки
- Щелкните правой кнопкой мыши и выберите
UnStage Lines for commit
мерзавец-кола это отличный графический интерфейс, в который также встроена эта функция.Просто выберите строки для постановки и нажмите С.Если выбор не сделан, создается полный фрагмент.