все форумы все темы добавить тему
Автоматическое изменение номера версии
Номер версии LabCMS состоит из трех частей: X.Y.ZZZ
где
X - главный номер
Y - вспомогательный номер
ZZZ- номер ревизии
 
Если X и Y меняются относительно редко и поменять их руками проблемы не составляет, то ZZZ должна меняться при каждом изменении репозитория. Делать это руками перспектива не очень заманчивая, поэтому встал вопрос об автоматизации.
Итак, задача следующая:
1. Автоматически менять номер версии в коде.
2. Поместить номер версии а архив с кодом.
3. Выложить обновленный архив на сайте.
4. Обновить номер версии на странице загрузки сайта.
 
Будем решать проблемы по порядку:
 
Прежде всего, необходимо в файле с номером версии автоматически менять номер ревизии. Вспоминаем что у subversion есть замечательное свойство svn:keywords! Указываем это свойство для файла с версией, в файле вместо номера ревизии пишем "$Rev: 1 $", пробуем - работает! Отлично! Пробуем еще раз - не работает... Совсем не отлично... В чем же дело? Оказывается, номер ревизии подставляется только при коммите самого файла... То есть перед комитом файл надо хоть немного изменить. Опять ручная работа?
 
Снова лезем изучать мануал по svn, находим раздел про хуки. Хуки (hooks), это такие программы, которые выполняются по наступлению определенного события в репозитории. Нас в первую очередь интересует хук pre-commit, то есть программа, которая должна выполнится непосредственно перед началом анализа изменений в коде. Казалось бы, что может быть проще - изменяй при помощи *.bat файла в коде одну строчку и он будет постоянно обновляться. Все бы так и работало, если бы не... если бы не windows, консоль которого предназначена для чего угодно, только не для работы с файлами. НАйти в файле и заменить фрагмент текста оказалось весьма нетривиальной задачей. В итоге, на просторах сети встретилось решение, позволяющее производить поиск и замену теста в файле приямо из bat файла. Правда, при этом bat файл создавал временный исполняемый бинарник, но решение вполне рабочее.
 
И вот когда решение, наконец, было найдено, оказалось что стоило так же заглянуть в руководство по TortoiseSVN (svn-клиент под windows). Оказалось что в его составе есть очень полезная утилитка SubWCRev.exe, которая именно тем и занимается, что подставляет в различные файлы информацию из репозитория. В результате законченное решение приняло следующий вид:
 
start-commit-hook вызывает файл update.bat следующего содержания
 
Text
"C:\Program Files\TortoiseSVN\bin\SubWCRev.exe" path\to\working\copy path\to\working\copy\revision.tpl.php path\to\working\copy\revision.php
exit 0

где
path\to\working\copy - путь рабочей копии проекта
revision.tpl.php - шаблон файла для замены
revision.php - файл для сохранения результатов
 
файл revision.tpl.php имеет следующее содержание
PHP
<?
        $revision=$WCREV$+1;
где вместо $WCREV$ подставляется текущий номер ревизии, а +1 потому что после коммита номер ревизии увеличится на единицу.
Для реализации остальных пунктов можно, наконец, перенестись на серверную сторону.
Снова нас интересуют хуки. На этот раз нам нужен post-commit (то есть тот, который выполняется после окончания коммита).
Создаем для него bash скрипт
 
Bash

#!/bin/sh
 
# отсюда берем рабочий код
trunk=svn://localhost/repos/flex/trunk
# отсюда берем стабильную версию
stable=svn://localhost/repos/flex/tags/stable
# куда кладем итоговый архив
place=/var/www/storage/File
 
# удаляем временный каталог для экспорта, если таковой почему-то существует
rm -rf /tmp/svn
# создаем временный каталог для экспорта
mkdir --mode=0700 /tmp/svn
# экспортируем код из trunk ветки в подкаталог tmp/upload
svn export --force $trunk /tmp/svn/tmp/upload
# переходим в подкаталог tmp
cd /tmp/svn/tmp
# получаем из файлов номер версии
version=`grep -o '[0-9]\+\.[0-9]\+' ./upload/kernel/install/version.php`
# и номер ревизии
revision=`grep -o '[0-9]\+.1' ./upload/kernel/install/revision.php`
# так как номер ревизии представляет собой выражение,
# то делаем так, чтобы оно выполнилось
revision=$(($revision))
# а вот и наш номер версии
t_ver=$version'.'$revision
# создаем текстовый файл с номером версии в названии
touch 'version_'$t_ver'.txt'
# упаковываем все подготовленные файлы в архив
zip -r /tmp/svn/labcms_trunk_full.zip *
 
# проделываем аналогичные манипуляции для стабильной версии
...
 
# переносим полученные архивы на сайт
mv -f /tmp/svn/*.zip $place
# удаляем временный каталог
rm -rf /tmp/svn
exit 0
 

Готово, теперь у нас на сайте выложены актуальные версии кода, оформленные соответсвующим образом. Осталось дело за малым - надо обновить информацию о версии на странице загрузки. Страница загрузки хранится в БД и в кэше. Лезть в БД из консоли а потом оттуда же очищать кэш мне показалось не лучшей идеей. Поэтому был написан простенький модуль, который принимал в качестве параметров номера версий, вносил исправления в БД и сбрасывал кэш. Чтобы всякие шутники не баловались обновлением версий, обновление срабатывает только по паролю. Добавляем в конец скрипта вызов специальной страницы и передаем ей номера версий
 
Bash

...
wget -O /dev/null -q 'http://labcms.ru/secret/path/?trunk='$t_ver'&relese='$r_ver'&secret=password'
exit 0
 

Что из этого получилось, можно увидеть здесь.
Аналогичным образом можно было бы добавить размер файла или еще какую-нибудь бесполезную но, безусловно, занимательную информацию