Комментарий к коммиту до коммита

16 января 2013 г.

Вы встречались с проблемой, когда вы пишите много кода, нажимаете коммит и не знаете как сформулировать комментарий? Такое случается, когда во время кодинга было сделано несколько подзадач, еще рефакторинг, еще code cleanup небольшой и т.п. Приходится писать либо очень большой комментарий, либо опустить руки и написать «fixes» или «big changes» или подобный комментарий, который ничего не значит. При работе в команде такие комментарии наносят большой вред, т.к. становится сложно понять, что происходит с кодом:

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

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

  1. Для начала открываем Workbench и пишем комментарий на задачу, которую мы сделаем за ближайшие 10-30 минут. Здесь надо привыкнуть писать комментарий в прошедшем времени, как будто задачу уже реализовали:
  2. Переходим в IDE и начинаем печатать код
  3. Когда задача реализована, возвращаемся в Workbench, комментарий к коммиту у нас уже есть, обновляем список измененных файлов и жмем коммит:

Получается, что мы сначала пишем комментарий к будущим изменениям, потом эти изменения делаем.

Плюсы

  • Делаем только одну задачу. Захотели порефакторить или отвлечься? Уже нельзя, коммитом четко обозначена небольшая задача;
  • Моделируем будущее у себя в сознании и думаем как бы быстрее до него дойти;
  • Когда вы привыкните работать в таком стиле, то без готового комментария уже будете испытывать дискомфорт, появится стремление написать себе мини-задачу;
  • Очень частые коммиты (не буду объяснять почему это хорошо);
  • Если вы отвлеклись, то легко вернуться в поток, прочитав мини-задачу, которую в данный момент решаем;
  • Равномерная нагрузка в течение дня. Мы ставим маленькие задачи и получаем постоянные легкие «победы» после их завершения.

Минусов нет, это отлично работает для обычных повседневных задач, когда можно декомпозировать большую User Story. Есть единственное ограничение: если вы будете работать с VCS (VSS, SVN и т.п.), то вам нужно будет использовать feature branching, иначе не получится делать такие маленькие коммиты.

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

Опробовано на нескольких проектах в нашей компании, приводит к крайне положительным результатам.

35 комментариев:

  1. К единовременному минусу, я думаю, можно отнести долгое привыкание.

    ОтветитьУдалить
  2. Как быть если в процессе написания кода видно, что в процессе будет выполнен так же и рефакторинг?

    ОтветитьУдалить
  3. Андрей Валяев16 января 2013 г. в 18:50

    Лучше коммитить по отдельности...
    Не всегда видно сразу, но надо стараться...

    Александр: Техника очень интересная.. А как можно в hg с командной строки заранее указать коммит месседж?

    ОтветитьУдалить
  4. Александр, Вы пробовали применять Mikado Method для рефакторинга? Если да, то удаётся ли сочетать его с подходом "комментарий до коммита"?


    На мой взгляд, Mikado достаточно хорош для проведения крупных рефакторингов, но вступает в определённое противоречие с описанной здесь практикой на шаге переключения задач. Непоятно, удаётся ли его как-то разрешить?

    ОтветитьУдалить
  5. Согласен, что надо коммиты делать отдельно. Если надо сделать рефакторинг (больше чем rename), то можно оставить TODO и через 15 минут вернуться к нему.

    Вот я думал на счет командной строки и пока ничего не придумал, может у вас будут идеи :)

    ОтветитьУдалить
  6. Не пробовал, спасибо за ссылку на новое для меня, буду смотреть.

    ОтветитьУдалить
  7. > Здесь надо привыкнуть писать комментарий в прошедшем времени, как будто задачу уже реализовали

    распространена практика написания коммит-мессаджей в виде инфинитивов, таким образом перестраиваться даже не придется

    ОтветитьУдалить
  8. >Здесь надо привыкнуть писать комментарий в прошедшем времени, как будто задачу уже реализовали

    В гайдлайнах для Git говорится, что описание коммита нужно писать в настоящем времени.

    ОтветитьУдалить
  9. В гайдлайнах для какого именно проекта?


    Очень сложно поверить в то, что инструмент должен диктовать как именно должны писать комментарии в нём.

    ОтветитьУдалить
  10. Да, можно и в настоящем. Дело в том, что мы изначально писали задачу так, как будто ее еще надо сделать, было не привычно писать о задаче, как о готовой.

    ОтветитьУдалить
  11. Уже 4 года как это стандарт дефакто. Вот к примеру описание с гитхаба https://github.com/blog/926-shiny-new-commit-styles


    вот оригинальное предложение http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html

    ОтветитьУдалить
  12. Что делать, когда в процессе выясняется что нужно сделать рефакторинг или исправить ошибку?

    ОтветитьУдалить
  13. :-S

    Это не стандарт де-факто, это предложение от разработчиков одного из гит-хостингов.

    Возводить в абсолют стандарт комментирования как-то дико для меня.

    Соглашения по поводу соглашений насчёт комментов и прочей культуры вокруг репозитория - проблемы отдельно взятой команды или проекта.

    ОтветитьУдалить
  14. Погуглите по тексту описания и вы поймете, что не правы.

    ОтветитьУдалить
  15. Неправы в чём? Что я не могу писать комменты, как я хочу? И что я для своего проекта не могу придумать собственного конвеншна?

    Так недолго до того, чтобы де-факто заставили всех выучить английский язык и писать комментарии только на нём.

    ОтветитьУдалить
  16. Кстати, из примера этого стандарта - а как вы переведёте "Fix bug" на русский?

    ОтветитьУдалить
  17. Это недостаток русского языка. Я не вижу никакого смысла писать комментарии на русском, кроме эстетического и потакания тем, кому лень выучить английский.

    ОтветитьУдалить
  18. ответ пиши @ комментарий не читай.


    PS: разработчик должен знать английский.

    ОтветитьУдалить
  19. Ну и всё таки? Как перевести эту строку? Она вообще грамматически корректна?

    ОтветитьУдалить
  20. Грамматически корректна. По-русски "исправить жука"

    ОтветитьУдалить
  21. Исправить жука это таки "To fix a/the bug".

    ОтветитьУдалить
  22. Уговорили. Буду писать комментарии на русском.

    ОтветитьУдалить
  23. Да не, я не уговаривал никого :-) Я просто удивлён, что "Fixed foo", которое корректно (за исключением артикля, но их много где опускают), предлагается заменить на "Fix foo", в котором вообще непонятно, что выполняет роль глагола.


    Причём аргументация строится на создании консистентного с автоматически генерируемыми текстами, которые хз кто как, но я всегда меняю на более осмысленные.

    ОтветитьУдалить
  24. Ivan Kurnosov , hazzik Грамматически оба варианта правильные и имеют смысл.

    "If you’re saying what you did today, then fixed bug is fine. If you’re saying what you’re doing tomorrow, it would be normal to write fix bug, as a note, in imperative form, to remind yourself and others what you’ll be doing."
    (Подробнее тут http://english.stackexchange.com/questions/51399/fixed-vs-fixes-when-things-are-already-done )

    Т.е. если последовательность commit'ов для команды представляется набором императивов, то лучше писать "fix bug". Если последовательностью репортов, то "fixed bug"

    ОтветитьУдалить
  25. Пример более автоматизированной работы с помощью phpstorm и redmine: http://www.zagirov.name/phpstorm-redmine-changelist-workflow

    ОтветитьУдалить
  26. Класс))
    Универсальное решение:

    $ curl http://whatthecommit.com/ | grep -P "^.*$" | xargs git commit -m

    ОтветитьУдалить
  27. а если до решения задачи конкретно неизвестно, что в итоге будет предпринято в качестве решения? я конечно могу обобщить свое описание к задаче максимум кратко и не париться, но это ни есть хорошо

    ОтветитьУдалить
  28. В любом случае понятно, что надо получить. Комментарий к коммите содержит результат, а не способ его достижения.

    ОтветитьУдалить
  29. из описания таска то же можно получить информацию о требуемом результате. Например, моя задача: добавить новый сервис для доплат по путевке. Мой результат: добавлен новый сервис для доплат. И в чем прикол? Другое дело, если я опишу, какое решение было выбрано в процессе выполнения задачи. А если просто напишу, что добавил новый сервис, никому легче не станет. Так вот, заранее не всегда прозрачно решение задачи, поэтому заранее все описать, как с заранее написанным тестом по технологии TDD - не всегда возможно.

    ОтветитьУдалить
  30. Андрей Валяев21 января 2013 г. в 00:31

    http://mercurial.selenic.com/wiki/MqExtension
    Позволяет делать не один а несколько подряд идущих отложенных коммитов... без модификации репозитория.
    Это позволяет писать код, одновременно проводя рефакторинг в предварительном коммите.
    Или всякие похожие вещи..

    Это я уточнил собственно, взял себе не вооружение :)

    ОтветитьУдалить
  31. В git когда происходит ситуация, подобная описанной в начале, хорошо использовать git add -p и добавлять код в коммит "патчами". Хорошо это еще и тем, что перед коммитом просматривается весь измененный код, чтоб не закоммитить то, что на самом деле там не должно быть.

    http://johnkary.net/blog/git-add-p-the-most-powerful-git-feature-youre-not-using-yet/

    ОтветитьУдалить
  32. hg collapse (http://mercurial.selenic.com/wiki/CollapseExtension). обычный воркфлоу - коммит раз 2-5-10 минут, с понятным для себя сообщением (типа rename method blaBlaBla, minor refactoring, trying one more time). потом, при завершении задачи, через час-день - collapse - перечитываешь коммит сообщения, переосмысливаешь изменения, пишешь нормальный коммит мессадж.. коммиты сливаются... и коллегам в паблик отдается только один красивый коммит (ну или сколько хочешь).

    ОтветитьУдалить

Моя книга «Антихрупкость в IT»

Как достигать результатов в IT-проектах в условиях неопределённости. Подробнее...