August 22, 2022

Конвенция текста коммитов

Чтобы сохранить единообразие коммитов и не путаться при поиске по репозиторию, можно подключить к проекту линтер коммитов, который проверяет текст коммитов на соответствие правилам разработки. Проверка происходит на хуке commit-msg с помощью husky, simple-git-hooks или git-hooks.

Мотивация

  • Единый стиль и понятность: Используя одинаковый формат коммитов, мы сделаем историю изменений более понятной. Каждый коммит будет иметь ясное обозначение типа изменения, области и краткое описание, что сразу даст представление о его смысле.
  • Легкость поиска и навигации: Стандартизированные коммиты помогут быстрее находить связанные изменения и легче перемещаться по истории разработки. Проще отслеживать, что и когда менялось.
  • Поддержка сотрудничества: Благодаря четким коммитам команда будет лучше понимать, что делает каждый разработчик. Это улучшает коммуникацию и управление проектом.
  • Упрощение автоматизации: Стандартизированные коммиты помогут автоматизировать процессы сборки, тестирования и развертывания. Меньше возможности для ошибок и быстрее выпускать новые версии.
  • Автоматическая документация: Коммиты могут быть использованы для создания автоматической документации. Так пользователи и разработчики быстро узнают, что нового в каждой версии проекта. Можно использовать standard-changelog.

Даже при условии сквоша коммитов в МР это полезно, потому что в истории МР будет структурированная история изменений, что упрощает код-ревью и отслеживание разработки фич. Также в Gitlab можно настроить шаблон для тела коммита.

Примеры стандартов

Предлагаемый формат коммитов

  • type(scope): subject

Где:

  • type — тип изменения, fix/feat/build/etc.
  • scope — область, которую затронуло изменения, либо номер заявки. Если несколько, писать через запятую. Если вне заявок, пропустить.
  • subject — краткое описание проделанной работы. С заглавной буквы. Описание коммитов должно отвечать на вопрос: «Что делает коммит?».

Тип изменения:

  • feat - используется при добавлении новой функциональности приложения
  • fix - если исправили какую-то багу
  • refactor - рефакторинг кода приложения
  • style - исправляем опечатки, исправляем форматирования
  • chore - обычное обслуживание кода
  • revert - отмена изменений
  • perf - оптимизация кода, улучшение производительности
  • docs - всё, что касается документации
  • test - всё, что связано с тестированием
  • build - всё, что связано с билдом
  • ci - всё, что связано с процессом деплоя
  • any - не входящее ни в одну из категорий

Пример коммитов, которые пройдут проверку

  • feat(front): Внедрение проверки коммитов TASK-####
  • fix(back): Исправил дедлок в репозитории TASK-####

Примеры коммитов, которые не пройдут проверку:

  • Зарефакторил компонент к заявке 35487
  • Удаление изменений по модальному окну

Пример настройки

Создать файл package.json в корне проекта (рядом с папкой .git), установить менеджер гит-хуков (husky, simple-git-hooks или git-hooks).

git init
npm i @commitlint/cli @commitlint/config-conventional husky --save-dev

Добавить в секцию с хуками хук "commit-msg": "commitlint -E HUSKY_GIT_PARAMS"

Пример package.json

{
  "name": "project-name",
  "version": "1.0.0",
  "description": "",
  "husky": {
    "hooks": {
      "commit-msg": "commitlint -E HUSKY_GIT_PARAMS"
    }
  },
  "devDependencies": {
    "@commitlint/cli": "^17.0.0",
    "@commitlint/config-conventional": "^17.0.0",
    "husky": "^8.0.0"
  }
}

Настроить формат коммитов в commitlint.config.js или оставить по умолчанию.

module.exports = {
	extends: ['@commitlint/config-conventional'],
	rules: {
		'body-leading-blank': [1, 'never'],

		'type-case': [2, 'always', 'lower-case'],
		'type-empty': [2, 'never'],
		'type-enum': [
			2,
			'always',
			[
				'build',
				'chore',
				'ci',
        			'devops',
				'docs',
				'feat',
				'fix',
				'perf',
				'refactor',
				'revert',
				'style',
				'test',
				'any'
			]
		],

		'scope-case': [2, 'always', 'lower-case'],

		'subject-case': [
			2,
			'always',
			['sentence-case']
		],
		'subject-empty': [2, 'never']
	}
};

Шаблоны Merge Requests

Также можно добавить шаблоны к Merge Requests. Это упростит процесс ревью и убедит всех участников, что необходимые проверки и тесты были выполнены перед слиянием

Мотивация

  • Стандартизация и единообразие: Шаблоны для МР позволяют установить общие стандарты и правила для всех МР в проекте. Это способствует единообразию в оформлении, структуре и требованиях к каждому МР, что облегчает их понимание и улучшает качество кода.
  • Улучшение коммуникации: Хорошо структурированные шаблоны помогают разработчикам четко описывать суть изменений в МР. Это улучшает коммуникацию в команде и снижает возможность недопонимания.
  • Облегчение код-ревью: Шаблоны позволяют уточнить, какой код и какой функционал должны быть протестированы перед отправкой МР на ревью. Это сокращает время, которое уходит на ревью кода, и помогает избежать пропуска критических проверок.
  • Повышение качества кода: Использование шаблонов позволяет включить в чеклист необходимые требования к коду, такие как правила форматирования, проверка наличия тестов и документации. Это способствует повышению качества кодовой базы.
  • Улучшение прозрачности процесса: Шаблоны дают возможность ясно определить, какие шаги и требования должны быть выполнены перед слиянием МР. Это упрощает процесс слияния и делает его более прозрачным для всех участников.

Для Gitlab можно использовать шаблоны МР. Пример файла .gitlab/merge_request_templates/Default.md. Также в шаблоне настроен автоматический выбор Assignee и создание МР в Draft.

## Описание изменений

Опишите, что было сделано в этом МР.

## Чеклист

Пожалуйста, убедитесь, что все пункты ниже выполнены перед отправкой МР:
- [ ] Проставлены контексты ревью
- [ ] Добавлен Assignee
- [ ] На момент создания в МР подлит свежий develop или feature-ветка
- [ ] Все комментарии и документация актуальны и информативны
- [ ] Изменения протестированы на локальной среде разработки

Если какой-то пункт из чеклиста не выполняется, пожалуйста, исправьте это перед слиянием МР.

/assign me /draft