Привет, мне показалось хорошей идеей начать переводить не только релизные посты из блога ГитЛаба. Для разминки я взял этот пост почти наугад, так что не судите строго. Буду рад, если поможете определиться с выбором статьи для перевода, выбрав один из вариантов в опроснике
Git – это система контроля версий с огромным количеством возможностей. Пытаться изучить их все довольно утомительно, поэтому большинство пользователей ограничивается использованием лишь базового набора команд. В этой статье представлены несколько советов по работе с Git, о которых вы, возможно, не знали. Эти советы помогут вам оптимизировать ваш процесс разработки.
Алиасы
Одним из лучших способов упрощения работы с Git является использование алиасов для часто используемых команд. Это поможет сохранить время при наборе команд в терминале.
Например, алиасы для команд checkout
, commit
и branch
можно создать следующим образом:
git config --global alias.co checkout
git config --global alias.ci commit
git config --global alias.br branch
Теперь вместо git checkout master
достаточно ввести git co master
.
Также можно изменять и добавлять алиасы напрямую редактируя файл ~/.gitconfig
:
[alias]
co = checkout
ci = commit
br = branch
Скрытие (stashing) изменений до коммита
Представим, что в процессе работы над новой фичей возникла срочная необходимость внести изменения в проект. Коммитить незавершенную функциональность — не лучшее решение, но терять все наработки по ней тоже не хочется.
При помощи команды git stash
можно временно отменить внесенные изменения, не удалив их окончательно:
$ git stash
Эта команда временно скрывает внесенные изменения и оставляет чистую рабочую копию. Теперь можно переключиться на другую ветку для внесения срочных изменений, не оформляя уже сделанные изменения как коммиты.
Чтобы вернуть скрытую функциональность, достаточно ввести:
$ git stash pop
Если же скрытая функциональность больше не нужна, ее можно удалить с помощью:
$ git stash drop
Сравнение коммитов из командной строки
Быстрым и легким способом сравнения изменений между коммитами или версиями одного и того же файла является использование команды git diff
.
Для сравнения состояний одного и того же файла между коммитами нужно ввести:
$ git diff $start_commit..$end_commit -- path/to/file
Для сравнения изменений между двумя коммитами:
$ git diff $start_commit..$end_commit
Эти команды выведут результат в текстовом виде прямо в окно терминала. Для более наглядного результата можно использовать git difftool
. Данная команда запускает специальную программу для сравнения изменений. Одной из таких программ является Meld.
Для настройки Meld введите:
$ git config --global diff.tool git-meld
Теперь ее можно использовать:
$ git difftool $start_commit..$end_commit -- path/to/file
# или
$ git difftool $start_commit..$end_commit
Откат изменений
Иногда при работе над кодом становится понятно, что внесенные изменения оказались ненужными/неверными и их необходимо откатить. Вместо того, чтобы делать undo по каждому изменению, достаточно сделать reset файлов на HEAD-коммит ветки:
$ git reset --hard HEAD
Или, для одного конкретного файла:
$ git checkout HEAD -- path/to/file
Далее, если ненужные изменения уже были закоммичены, для их отката нужно ввести:
$ git reset --soft HEAD~1
Более эффективное использование Git blame
Git blame используется для того, чтобы узнать, кто внес изменения в определенную строку файла. Существует набор флагов, которые можно передавать данной команде, в зависимости от того, что вы хотите вывести:
$ git blame -w # игнорировать знаки табуляции
$ git blame -M # игнорировать перемещения текста
$ git blame -C # игнорировать перемещения текста в другие файлы
Помимо описанных выше советов по работе с командами, существует несколько общих советов по работе с Git.
Делайте пулл часто
Если вы используете GitLab Workflow, значит вы работаете в ветках для выделенной функциональности (feature branches). Пока вы работаете над фичей в отдельной ветке, в мастер-ветке может произойти множество изменений, некоторые из которых могут конфликтовать с добавленными фичами.
Для того, чтобы избежать подобных конфликтов, нужно как можно чаще пуллить изменения из мастер-ветки в вашу. Это позволит разрешать возможные конфликты по мере их появления и сделает последующий мерж вашей ветки гораздо более легким.
Частые коммиты, редкие пуши
Частые коммиты логически разделяют добавленную функциональность и позволяют откатывать отдельные ее части при необходимости. Однако нет никакой необходимости пушить каждый коммит на сервер: единственное, к чему это приведет – засорение истории изменений. Пушьте только тогда, когда ваша фича готова.
Пуш только после тестирования изменений
Хорошим знаком того, что изменения готовы к пушу, является успешное прохождение тестов. Также это как правило значит, что данный блок реализуемой функциональности завершен, и можно переключить свои усилия на следующий. Делайте пуш изменений только после прохождения всех тестов, с последующим повторным их прохождением на стороне CI-сервера.
24% (41) |
GitLab CI: Run jobs sequentially, in parallel or build a custom pipeline — https://about.gitlab.com/2016/07/29/the-basics-of-gitlab-ci/ |
16% (28) |
Comparing Confusing Terms in GitHub, Bitbucket, and GitLab — https://about.gitlab.com/2016/01/27/comparing-terms-gitlab-github-bitbucket/ |
5% (9) |
Building an Open Source Company: Interview with GitLab's CEO — https://about.gitlab.com/2016/07/14/building-an-open-source-company-interview-with-gitlabs-ceo/ |
5% (8) |
GitLab Container Registry — https://about.gitlab.com/2016/05/23/gitlab-container-registry/ |
47% (82) |
GitLab Flow — https://about.gitlab.com/2014/09/29/gitlab-flow/ |
3% (5) |
Свой вариант в комментариях |
Проголосовало 173 человека. Воздержалось 150 человек.
Только зарегистрированные пользователи могут участвовать в опросе. Войдите, пожалуйста.
Комментарии (25)
maxru
10.08.2016 17:09С одной стороны всё это можно узнав, прочитав официальную документацию.
С другой стороны, каждый раз лезть в документацию неохота.
Мне кажется лучшим решением было бы дополнительно к статье создать cheat sheet (на cheatography по git уже есть, но того, что описано в статье, там нет).saboteur_kiev
10.08.2016 18:26+5Практически все 8 советов можно прочитать чуть ли не на первой страничке официальной документации по GIT.
https://git-scm.com/doc
Например Git cheat sheet: https://services.github.com/kit/downloads/github-git-cheat-sheet.pdf
inoyakaigor
10.08.2016 17:28Теперь можно переключиться на другую ветку для внесения срочных изменений
Рекомендую использовать для этих целей worktree. Это куда удобнее бесконечных stash > checkout > checkout > stash pop. Единственное что GUI клиенты ещё не научились с этим корректно работать. SmartGit и gitg по крайней мере.develop7
10.08.2016 18:49IDEA относительно недавно умеет worktree, и очень давно — «smart checkout» (stash > checkout > stash pop)
NickKolok
10.08.2016 20:58Чего действительно мне не хватает в stash — это возможности применять его к конкретным файлам, а в идеале — к частям файла, наподобие
git add $filename -p
.
Сейчас приходится извращаться через коммит и его резет. Никто случайно не знает нормального пути?crazylh
10.08.2016 21:48Через консоль наверно такого нет, а вот SourceTree умеет частитчно патчить файлы из stash
everyonesdesign
10.08.2016 21:50+1Можно пользоваться
git stash -p
, правда, без указания имени файла, придется отбирать изменения через все файлы.NickKolok
11.08.2016 17:40Помогло, спасибо! И не думал, что такая штука есть, если пофайлового сташа нет.
Darkside73
11.08.2016 09:44+1Еще можно добавить в индекс то, что не должно в stash попасть:
git add files/to/not/stash git stash --keep-index
domix32
11.08.2016 00:49+2Писать алиасы для однословных комманд так себе план — автодополнение же есть. А вот для чего-нибудь вроде submodule update --init --checkout или rebase master --autostash уже намного более реалистично
dshster
11.08.2016 13:46Для checkout так себе автодополнение — там есть команда check, которая подставляется первой, поэтому co гораздо удобнее.
darthandrew
11.08.2016 12:42-2А еще более эффективная работа (если вы под виндой) — использование TortoiseGit, чтобы не страдать с командной строкой.
aezhko
11.08.2016 13:12+1Не соглашусь с вами:
- GUI реализует не все возможности командной строки.
- Работа с командной строкой — не страдание, если ты знаешь, что делаешь. Кроме того, есть штуки типо Oh-My-Zsh, которые делают процесс работы в командной строке еще более удобным.
- Если говорить о разработке, GUI-интерфейсы интегрированы во все современные IDE.
darthandrew
11.08.2016 14:03Да, возможности может не все, но «минимально-рабочий набор» вам обеспечен. На личном опыте — мои коллеги крайне редко сидят в git в командной строке. Допустим подключается человек — технический писатель, с git ему работать надо, да его можно учить «знать что ты делаешь», но смысла нет. Конечно это дело вкуса, лично одного человека точно знаю кто любит именно командную строку, но вопрос не такой однозначный. Что используем мы: обновись, коммит, пуш, создай ветку. Мерж делают уже далеко не все — это забота тим-лида сложить все воедино. Git ведь дает много чего, когда первое время мы его внедряли — реально пугало сложностью, теперь уже все проще, но уверен что многие возможности ни я ни коллеги просто не знаем и не применяем, но и работать без них тоже можно.
michael_vostrikov
11.08.2016 19:46+1Тоже пользуюсь тортиллой. В консоли удобно делать повторяющиеся действия из нескольких команд, типа checkout/pull/checkout/rebase, можно названия веток вынести в переменные, и копи-пастить весь набор команд в консоль. Или разные хитрые вещи для управления репозиторием, которых нет в GUI.
А вещи, которые требуют внимания, выбора, и работы с текстом, удобнее делать в GUI — diff файлов перед коммитом, разбиение/слияние коммитов, интерактивный rebase, разрешение конфликтов. Дело личных предпочтений, конечно, но при правильном применении GUI помогает сэкономить время.
sumanai
11.08.2016 20:15Не знаю как в Git, но интерфейс в TortoiseHg достаточно удобен, не представляю, как выборочно коммитить части файлов из командной строки, работать с очередями заплаток и тому подобное.
dshster
11.08.2016 15:24TortoiseGit? Пробираться через дебри вложенных меню так себе удовольствие. Тогда уж SmartGit, хотя всё это вкусовщина.
var_bin
12.08.2016 13:28Добрый день! Спасибо за статью!
Пробовал создавать алиасы через
git config --global alias.co checkout
, но они почему-то не сохраняются. И после каждого перезапуска терминала их нужно создавать заново. Поэтому использую для хранения алиасов файл~/.bashrc
. Но вариант с~/.gitconfig
тоже хорошо подходит, просто он у меня не прижился.
rhrn
15.08.2016 22:55git pull --rebase (удобный способ подтянуть обновление, что не нужно было делать дополнительные коммиты)
git diff --staged (показать что пойдёт в коммит)
git status (показать состояния файлов: новые, изменённые, добавленные для коммита)
Delphinum
А разве после пуша пачки коммитов, они каким то магическим образом будут сгруппированы?
Mobyman
Наверное, имеется в виду локальный rebase со squash коммитов в один.
Delphinum
Возможно, только вот коммиты все равно должны быть пачкой. Лучше уж сразу применять модель: функция = ветка.
withoutuniverse
Из коробки нету такого поведения.
С этой командой все изменения можно будет как один коммит добавить.Долго искал грамотное решение, так как считаю rebase опасным в неопытных руках.
Я откатываюсь на коммит, в котором рабочая ветка была создана, делаю новую ветку для мержа с мастером в этом месте и пишу