И снова, здравствуйте. Неделю (эта статья о-очень долго мариновалась в бэклоге) Какое-то время назад я рассказал, как использовать rcm для обычного управления конфигурацией. У нас в компании есть модуль puppet, распространяющий персональные настройки пользователя по всем хостам, на которые у него есть доступ. Соответственно, хочется следующего:
- Иметь собственные настройки для всего, чем я пользуюсь (vim, zsh, git, etc..)
- Обновлять их по мере обновления в репозитории dotfiles
- Всё это — без лишних телодвижений
Инструменты
Всё, что нужно, уже используется мною, а именно:
Формат, используемый для деплоя файлов на хосты
Здесь ничего хитрого нету: мы деплоим tar-ball'ы, распаковывая их содержимое на хостах. Управляются только файлы и директории из конкретного списка, полностью перетираясь при каждом деплое по крону. Соответственно, если изменился тарболл, то перетирается всё в $HOME по списку. Если нет — содержимое $HOME остаётся без изменений. За (пере)упаковку папки с исходниками персональных файлов отвечает отдельный скрипт, он выглядит достаточно тривиально:
#!/bin/bash -e # Repack each personal directory into a tarball, use gtar on mac/*BSD and tar on linux TAR=$(command -v gtar tar | head -1) cd "$(dirname "$0")" for file in *; do if [ -d "${file}" ]; then printf '\033[0;32mArchiving of \033[1;33m%s\033[0m\n' "$file" # to avoid differences in an archive because of different mtime # hard coded 2003-01-01 CET XZ_OPT=-e9 $TAR --mtime="@1041375600" -cJf "${file}.tar.xz" "${file}" fi done
Как создать новый tar-ball по коммиту
Деплоим dotfiles не в $HOME
Раз уж у меня уже есть инструмент, которым я деплою конфиги на различные хосты, то, очевидно, использовать я буду его же. Надо просто кое-что подправить и заставить rcm копировать файлы туда, куда мне надо. Однако rcm всегда устанавливает дот-файлы в $HOME, аргументов командной строки для изменения этого поведения нет.
После некоторых экспериментов и ковыряния в исходниках, я понял, что можно изменить непосредственно $HOME, тогда поведение утилит всех команд rcm поменяется следующим образом: каждая из утилит lsrc, mkrc, rcdn, rsup будет считывать ${HOME}/.rcrc и использовать ${HOME}/.dotfiles по умолчанию. Соответственно, достаточно создать тот самый ${HOME}/.rcrc со всеми необходимыми параметрами.
Проще всего сделать "болванку" домашней папки и заполнять её с нуля при каждом коммите. Пример того, как она выглядит можно увидеть в репозитории. Эта папка игнорируется на всех хостах без тега personal, соответственно, не помешает основной конфигурации. Один единственный файл .rcrc содержит все параметры для логики копирования файлов, сделаю только некоторые ремарки:
- Без
$SYMLINK_DIRSrcupотрабатывает безнадёжно долго, создавая полный список файлов, которые надо копировать. При наличии данного параметра совместно с$COPY_ALWAYSутилита просто копирует всю папку какcp -rбез лишней мороки - Очевидно, что многое не нужно на удалённых серверах, всё это перечислено в
$EXCLUDES(за исключением плагинов vim, их приходится удалять в хуке, потому что используется$SYMLINK_DIRS) - Так как
${HOME}/.dotfilesперестаёт работать по очевидным причинам, необходимо также переопределить$DOTFILES_DIRS
Вот и всё. Теперь можно скопировать папку tag-personal куда угодно, переопределить на время ${HOME} и выполнить rcup
WORK_DIR="${HOME}/.dotfiles/tag-personal" _OLD_HOME=$HOME HOME="${HOME}/some/long/custom/path" cp -r "${WORK_DIR}" "${HOME}" rcup -v HOME=$_OLD_HOME
Здорово! Но хочется чего-то ещё…
Автоматизируем "деплоймент" конфигов в кастомный $HOME
Сделать это "что-то" просто, git в этом месте поможет своими хуками. Имеется исполняемый файл .git/hooks/post-commit следующего содержания:
#!/bin/sh set -e WORK_DIR="tag-personal" HOME="${HOME}/some/long/custom/path/final_directory/USERNAME" # Some unnecessary and very heavy plugins EXCLUDED_VIM_PLUGINS='YouCompleteMe vimtex' rm -rf "${HOME}" cp -r "${WORK_DIR}" "${HOME}" rcdn -v rcup -v for plugin in ${EXCLUDED_VIM_PLUGINS}; do rm -rf "${HOME}/.vim/plugged/${plugin}" done # cleanup for .git dirs, compiled py and pictures find "${HOME}" \( \ \( -type d -iname '.git' \) -o \ \( -type f \ \( -iname '*.pyc' -o -iname '*.gif' -o -iname '*.png' \) \ \) \ \) -exec rm -rf {} + # final repack for files "${HOME}/../repack.sh"
Теперь после каждого коммита в репозиторий с дот-файлами будет запускаться этот скрипт.
Всё, после этого остаётся сделать коммит+пуш в репозитории с персональными данными и дождаться, пока магия автоматизации довезёт мои конфиги до рабочих хостов.
Зачем всё так усложнять?
Дело в том, что пока в компании не было инструментов для деплоя персональной конфигурации на хосты, не было необходимости и в подобном обвесе. Но как только появлется возможность, аппетит растёт моментально. Кое кто из моих коллег остался доволен и тем, что привёз на хосты три файлика, допустим, .vimrc .bashrc .gitconfig. Однако у меня уже довольно долго любовно точился, подправлялся и подвергался полировке целый набор различных инструментов. Одна только папка ~/.vim после установки всех плагинов весит 427MB (да, 218 из них это YCM, и его я на серверы не тащу, а после чистки и упаковки это всё худеет до 3MB).
Наверное, кому-то покажется, что это уж как-то слишком и можно было бы и руками. Пожалуй, не все с этим согласятся.
Надеюсь, что у кого-то ещё есть почти физическая потребность чувствовать себя на рабочих станциях комфортно, почти как дома, и ему позволяет это инструментарий. Пользуйтесь на здоровье и да пребудет с нами автоматизация!
