ИТ Блог. Администрирование серверов на основе Linux (Ubuntu, Debian, CentOS, openSUSE)

Управление Git-хуком с предварительной фиксацией (Pre-commit)

Управление Git-хуком с предварительной фиксацией

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

Работа с Git не совсем тривиальна. Даже такие простые вещи, как отмена шага, выходят далеко за рамки простого ярлыка отмены, но как только в репозитории работает целая команда, источники проблем вырастают до небес.

Сам Git очень хорошо справляется с простыми “сложными” проблемами, такими как конфликты слияния или отсутствующие обновления, и помогает с удивительно четкими сообщениями об ошибках. Однако, когда дело доходит до более сложных или “мягких” проблем, Git также бессилен.

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

Именно здесь Git-перехватчики могут вступить в действие и принудительно отправлять правильные сообщения о фиксации – или, скорее, поощрять их, как мы покажем позже на конкретном примере.

 

Что такое Git-перехватчики?

Git-перехватчики – это, по сути, нечто очень простое: скрипты, которые автоматически выполняются при определенных событиях рабочего процесса. Скрипты могут быть написаны на любом скриптовом языке, таком как Python для обширных манипуляций или в виде Bash-скрипта для небольших вмешательств. События рабочего процесса относятся к отдельным шагам, таким как фиксация и отправка на стороне клиента или обновления на стороне сервера.

Использование так же просто, как и концепция: все скрипты находятся в каталоге “./git/hooks” под фиксированными описательными именами, такими как “pre-push”. Для удобства многие скрипты по умолчанию содержат файлы примеров в папке hooks.

Для простого теста достаточно просто написать команду типа “echo foobar” в сценарии предварительной фиксации; терминал уже отображает сообщение “foobar” до фактического выполнения инструкции push.

 

Различные типы перехватов

Для отдельных перехватчиков важны три аспекта: когда именно они выполняются, т.e. Запускаются какой командой git? Какие параметры передаются? И выполняется ли скрипт на стороне клиента или в удаленном репозитории? Ниже я показываю наиболее важные перехватчики в обычном рабочем процессе Git. Всего около 28 перехватчиков, здесь обсуждаются только 15, которые используются более регулярно.

Давайте начнем довольно необычно с перехватов, которые запускаются “git am”, то есть при обработке исправлений по электронной почте. Здесь есть три перехвата.:

 

Команда “git commit” вызывает в общей сложности четыре перехватчика:

 

Использование предварительной фиксации

Принцип работы предварительной фиксации довольно прост: фреймворк устанавливается в репозиторий Git и запускается с помощью команды “git commit”. Затем он выполняет установленные перехватчики в соответствующее время, точнее, на определенном этапе (фиксация, нажатие и т.д.).

Сами перехватчики могут быть написаны практически на любом языке или для разных сред, включая Conda, Docker, Dotnet, Node, Lua, Perl, Ruby, Rust, Pygrep и, конечно, Python и shell-код. Предварительная фиксация обычно также обрабатывает любые зависимости, которые требуются среде для запуска сценариев. В некоторых случаях, например, с помощью shell script, пользователи должны и могут позаботиться об этом сами.

Вы получаете еще большую гибкость за счет хранения перехватчиков: хотя они могут храниться локально и непосредственно в соответствующем репозитории, по умолчанию они извлекаются из собственного репозитория – как это обычно бывает с менеджерами пакетов.

Сама функция предварительной фиксации указывает Pip, Brew и Conda для установки – однако пакеты Snap и Apt также показаны в Ubuntu, которые не обновлены. Мы рекомендуюем устанавливать через Pip:

pip install pre-commit

 

Важно обращать внимание на любые сообщения об ошибках; в нашем случае установка была установлена в каталог “~/.local/”, которого нет в path. Версия Apt, в свою очередь, была установлена в path как обычно. Если все работает, в “pre-commit –version” должен быть указан номер версии.

Теперь перейдите к нужному репозиторию. Вся настройка выполняется в файле “pre-commit-config.yaml”, который вы можете поместить в корневой каталог вашего репозитория. Для начала вы можете создать простой пример конфигурации, использующей несколько перехватчиков из репозитория перехватчиков предварительной фиксации:

pre-commit sample-config > .pre-commit-config.yaml

 

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

repos:  
- repo: https://github.com/Pre-Commit/Pre-Commit-hooks  
rev: v3.2.0  
hooks:  
- id: trailing-whitespace

 

Итак, необходимы три элемента информации: репозиторий с перехватами, тег для желаемого выпуска и идентификаторы желаемых перехватов – подробнее об этом позже. Загруженный здесь перехватчик, что неудивительно, удалит ненужные пробелы в концах строк.

Теперь конфигурация готова, и вы можете установить pre-commit:

pre-commit install

 

С помощью этой команды файл “pre-commit” просто сохраняется в каталоге ”.git /hooks” – таким образом, перехватчик предварительной фиксации активируется и выполняет предварительную фиксацию с созданной конфигурацией во время “git commit”. И да, немного сбивает с толку тот факт, что фреймворк, Git-хук и сам файл имеют одно и то же имя “Pre-Commit”.

Вместо новой фиксации перехватчики также могут запускаться вручную, для отдельных файлов или просто для всех файлов, что, конечно, имеет смысл для новых перехватчиков:

pre-commit run --all-files

 

Это означает, что выполняются все перехватчики , указанные в конфигурации YAML, и при необходимости изменяются файлы – каждый подтверждается красиво отформатированным выводом в форме:

`Trim Trailing Whitespace.................................................Passed  
- hook id: trailing-whitespace  
exit code: 1  
- files were modified by this hook`

 

Репозиторий Fork-хук

Репозиторий перехватов, по сути, должен содержать только две вещи: сами скрипты перехватов и другую конфигурацию YAML, здесь файл “pre-commit-hooks.yaml”. Лучший способ сделать это – просто разветвить уже используемое репозиторий подключений из проекта предварительной фиксации – напрямую через интерфейс GitHub:

repos:  
- repo: https://github.com/IHR-REPO/pre-commit-hooks  
rev: v1.0.0  
hooks:  
- id: trailing-whitespace
- 

 

Затем конфигурация в рабочем репозитории требует обновления:

pre-commit autoupdate

 

Это устанавливает для записи rev в pre-commit.yaml значение последней версии. Если использование предопределенных и разветвленных хуков из вашего собственного репозитория хуков работает, вы можете протестировать свои собственные скрипты.

 

Использование ваших собственных перехватчиков

Этот перехватчик представляет собой очень простой сценарий оболочки, который просто заменяет “foo” на “bar– – в файле “test.sh” в главном каталоге репозитория перехватчиков:

#!/bin/bash sed -i ' s/foo/bar/ ' *

 

Затем этот хук должен быть известен “pre-commit-hooks.yaml” – для этого вы просто копируете часть хука “завершающий пробел”, показанную выше, и соответствующим образом адаптируете ее:

- id: test  
name: test  
description: testing stuff  
entry: ./test.sh  
language: script  
types: [text]  
stages: [commit, push, manual]

 

В дополнение к имени и идентификатору, здесь необходимо изменить две записи: “script” указывается как “язык”, а для “entry” должен быть указан путь к скрипту относительно основного каталога репозитория подключений; Здесь, например, test.sh сам находится в главном каталоге.

Другие записи для ”типов” и “этапов” необязательны; на этом этапе вы можете указать, что перехватчик учитывает только текстовые файлы и какими этапами это должно быть ограничено.

И снова теперь необходимо создать новый релиз в репозитории hooks. Теперь не хватает последнего шага: новый пользовательский перехватчик должен быть добавлен в pre-commit-config.yaml в рабочем репозитории:

repos:  
- repo: https://github.com/IHR-REPO/pre-commit-hooks  
rev: v1.0.1  
hooks:  
- id: trailing-whitespace  
- id: test

 

После окончательного обновления появляется доступ к тестовому перехвату.

pre-commit autoupdate

 

Очень важно, хотя и не зависит от предварительной фиксации: скрипт должен быть исполняемым – и, конечно, об этом также необходимо сообщить в git. Это работает при добавлении скрипта с помощью “git add”, но также и после:

git update-index --chmod=+x test.sh

 

Заключение

Два репозитория, две конфигурации YAML, релизы в одном, обновления в другом репозитории, документация, которая на самом деле использует Python только в качестве примера – предварительная фиксация не совсем интуитивно понятна, и первый час может быть довольно неприятным, но после этого это отличный инструмент.

Exit mobile version