derfenix 05.02.2011 22:47

СкриптыХранение конфигов (и не только) в git - автоматизация

Не знаю, насколько оправдано то, что я написал и есть ли смысл в том, чтобы хранить конфиги в git, но вот захотелось мне сделать... :) Правда сам этим скриптом уже почти не пользуюсь (поигрался и надоело =) ), но может кому-то он пригодится... :)
В общем, суть скрипта (на bash) в том, чтобы коммитить, пушить и добавлять конфиги (да и в принципе и любые другие файлы), разбросанные по фс в разных местах, без необходимости собирать их в одном месте или в ручную делать симлинки.

В двух словах скрипт работает так:
1
script add filename <newfilename></newfilename>

- перемещаем указанный файл в указанную в скрипте директорию репозитория (если указан newfilename - переименовываем в newfilename), добавляем файл в репозиторий, по старому адресу кидаем симлинк на файл, записываем в специальный файл в репозитории строку вида "имя_файла_в_репозитории||исходный_путь_до_файла_относительно_$HOME" (это сделано на будущее, когда у меня дойдут руки до дополнения скрипта новой функцией - быстрого разворачивания конфигов из гита на новой машине).
1
script commit

- ну тут понятно, делаем коммит
1
script push

- тоже понятно - заливаем коммит(ы) на сервер

Все операции можно выполнять из любого места фс, без необходимости переходить в директорию с git. Т.е. можно отредактировав какой-то файл, тут же его и закоммитить, не парясь по поводу перехода куда надо :)
Прежде чем делать push, конечно, надо будет добавить в репозиторий "куда пушить" :) Всё остальное, скрипт сделает сам при добавлении первого же файла или просто при запуске без параметров.

Сам код скрипта ниже
  1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
#!/bin/bash

#Параметры------------
REPOPATH="$HOME/.repo" #Место хранения репозитория
REPOINIT="git init" #Команда инициализации репозитория
ADDCMD="git add" #Команда на добавление файла в репозиторий
CHECKOUTCMD="git checkout master" #Комманда переключения на текущую ветку
COMMITCMD="git commit -a" #Комманда для коммита
COMMITCOMMENT="-m" #Добавление комментария к коммиту
PUSHCMD="git push" #Выгрузка изменений в удалённый репозиторий
#---------------------

CURDIR="$PWD" #Сохраняем текущий путь для дальнейшего использования


#Инициализация нового репозитория
function init_repo(){
eval "mkdir -p $REPOPATH" #создаём дирректорию
eval "touch $REPOPATH/.files" #Создаём файл с исходными путями
cd "$REPOPATH"
eval "$REPOINIT" #Инициализируем репозиторий
eval "$ADDCMD .files" #Добавляем в него .files
eval "$COMMITCMD $COMMITCOMMENT 'Iitial commit'" #Делаем первый коммит
return 0
}

#Коммит сделанных изменений
function commit(){
if test ! -z "$1" #Если комментарий указан в параметрах
then
COMMENT="$COMMITCOMMENT '$1'" #то добавляем автоматически
else
COMMENT="" #Иначе будет вызвано стандартное добавление комменатрия
fi
eval "$COMMITCMD $COMMENT"
}

#Если дирректории с репозиторием не существует
if test ! -d "$REPOPATH"
then
init_repo #То создаём и инициализируем
fi

#Если указан первый параметр
if ! test -z "$1"
then
ACTION="$1" #То он является необходимой операцией
else
echo "No Action!" #Иначе выходим. Без указания операции нам нечего делать
exit 2
fi

# Если указан второй параметр
if test ! -z "$2"
then
TARGET="$2" #То это цель для операции

#Если указан ещё и третий параметр
if test ! -z "$3"
then
TARGET_="$3" #То это имя файла для хранения в репозитории, при добавлении нового файла
else
TARGET_=`basename "$TARGET"|sed "s/^\.//"` #Иначе именем файла будет имя добавляемого файла без предшедствующей точки (если есть такая)
fi
else
#Если второй параметр не указан и операция - добавление файла в репозиторий
if test "$ACTION" == "add"
then
echo "No targret!"
exit 3 #То выходим, т.к. не указано, что добавлять
else
TARGET="" #Для других операций - просто создаём пустую переменную.
fi
fi


cd "$REPOPATH" #Переходим в репозиторий

case "$ACTION" in
"commit") #Commit
commit "$TARGET"
;;

"push") #Push
eval "$PUSHCMD"
;;

"add") #Adding
eval "$CHECKOUTCMD" #Переключаемся в основной репозиторий

#Если файл с указанным именем уже сущестует в репозитории
if test -f "$REPOPATH/$TARGET_"
then
#Предлагаем его переименовать
echo "File exists! Rename? (Blank for cancel):"
read TARGET_
if test -z "$TARGET_" #Если нет нового имени
then
exit 4 #Выходим
fi
fi

COMMENT="Added $CURDIR/$TARGET as $TARGET_" #Создаём комментарий для будущего коммита
eval "mv '$CURDIR/$TARGET' '$REPOPATH/$TARGET_'" #Перемещаем файл в дирректорию репозитория
eval "ln -s '$REPOPATH/$TARGET_' '$CURDIR/$TARGET'" #Создаём на него ссылку по исходному пути
eval "$ADDCMD $TARGET_" #Добавляем файл в репозиторий
eval "$COMMITCMD $COMMITCOMMENT '$COMMENT'" #Коммитим изменения

echo "$TARGET_||$CURDIR/$TARGET">>$REPOPATH/.files #Записываем в файл исходный путь для файла
;;

*)
echo "No action!"
exit 5
;;
esac


exit 0


Последняя версия скрипта - всегда здесь.
В принципе, скрипт легко переделать под работу с любой другой системой контроля версий, но я хорошо знаком только с git.

Пинайте! =)


Тэги: bash git автоматизация
+ 11 -
Похожие Поделиться

Shtsh 05.02.2011 23:02 #
Круто. Смысл есть. Особено, если что-то вроде конфигов awesome, которые со временем усложняются.
kovtunos 05.02.2011 23:28 #
Спасибо, как раз хотел сделать нечто подобное для hg. Теперь осталось просто переделать.
DEViANCE 05.02.2011 23:34 #
Ммм... А etckeeper отменили? :)
derfenix 05.02.2011 23:36 #
а он разве не только для конфигов в /etc?
к тому же, если есть инструмент, это не значит, что аналогов ему не должно быть :)
kstep 07.02.2011 14:19 #
Только про него напомнить хотел.
lockie 06.02.2011 00:12 #
Хм. Я сделал по-другому: в свой реп с конфигами добавил скриптик install.sh, чтобы быстро развернуть конфиги на свежеустановленной системе. Обычно у тех конфигов, которые в домашней директории, больше приоритет, чем у тех, что в /etc, поэтому конфиги из /etc я в репе не храню.
derfenix 06.02.2011 00:41 #
Тоже вариант :)
ну тут я тоже конфиги из /etc/ и не подразумевал трогать..