Automatización de HotFix en proxectos Maven usando TeamCity
Esta publicación describirá a configuración da automatización HotFix en proxectos Maven usando Teamcity.
Para facer HotFix, adoitan facerse moitos pasos manuais:
Crea un brunch para a versión á que queres lanzar HotFix
Corrixir un erro na versión
Cambia a versión de corrección de erros na rama de versión
Lanza a etiqueta de versión de corrección de erros
Os puntos 1,3,4 pódense automatizar.
Antes de pasar ao tema, gustaríame tocar un tema importante e complexo: versionado software. Podes entender brevemente Semver nesta captura de pantalla.
No desenvolvemento baseado en troncos, cómpre crear a súa propia rama para cada versión. Todos os cambios (correccións rápidas) nesta versión están comprometidos nesta rama.
Como parte desta publicación, automatizaremos as seguintes cousas:
Servidor e axente de Teamcity. Podes aumentar o teu servidor e axente local de Teamcity usando atracador-compoñer
Onde teña o axente de Teamcity, debe estar instalado java, maven e git
Creemos o proxecto "Automation Maven Hotfix" en Teamcity e creemos alí 4 tarefas.
Construción CI
Crear rama para o lanzamento
Corrección de erros de incremento de Maven (Cambiar versión de corrección de erros))
Versión de Maven (creando unha nova versión)
Captura de pantalla do proxecto:
Configuración xeral
En todas as tarefas debes marcar a caixa "Compilación limpa: elimina todos os ficheiros do directorio de verificación antes da compilación", porque sen esta caixa de verificación recibín erros.
Creamos un único VCS. As funcións VCS están rodeadas en vermello.
Normalmente os VCS usan o esquema HTTPS. EN Especificación da rama: indicado para ver todos os brunchs e todas as etiquetas:
+:refs/heads/*
+:refs/tags/*
É necesario crear 4 Parámetros de Configuración.
BRANCH_FOR_INCREMENT
TAG_FROM_VERSION
TEAM_USER
TEAM_USER_EMAIL
O campo de valor en BRANCH_FOR_INCREMENT e TAG_FROM_VERSION debe quedar baleiro.
Debes cargar/engadir unha chave privada. Todas as tarefas, excepto CI Build, requiren unha clave privada.
En cada tarefa, excepto CI Build, na sección Funcións de compilación cómpre conectar unha chave privada.
Exemplo para Lanzamento de Maven
CI Build**.
Nunha tarefa Construción CI só un paso proba mvn limpa
Lanzamento de Maven
Nunha tarefa Lanzamento de Maven 2 pasos. O primeiro paso é comprobar que é o brunch mestre. Se o brunch non é mestre, entón a tarefa cae.
BRANCH=$(git branch | grep * | cut -d ' ' -f2)
echo "$BRANCH"
if [[ "$BRANCH" != "master" ]]; then
echo 'Branch is not master';
echo 'Aborting';
exit 1;
fi
O segundo paso é estándar mvn release:preparar con opción --modo por lotes
Crear rama para o lanzamento
Para crear un hotfix para unha versión, cómpre crear unha rama. Isto é o que fai a taska Crear rama para o lanzamento. Ela ten 2 chanzos.
O primeiro paso comproba que o brunch non o é mestre, e o segundo comproba que a versión está no ficheiro pom.xml non contiña a palabra INSTANTÁNEA
BRANCH=$(git branch | grep * | cut -d ' ' -f2)
echo "$BRANCH"
if [[ "$BRANCH" == "master" ]]; then
echo 'Branch is master';
echo 'Aborting';
exit 1;
fi
echo "Get version package from pom.xml"
version=`python -c "import xml.etree.ElementTree as ET; print(ET.parse(open('pom.xml')).getroot().find('{http://maven.apache.org/POM/4.0.0}version').text)"`
echo "Check SNAPSHOT"
if [[ $version == "*SNAPSHOT*" ]]; then
echo "******************* W A R N I N G *************************"
echo "************ You are create branch for SNAPSHOTS ******************"
echo "***********************************************************"
exit 1
fi
O segundo paso cambia o esquema de conexión en developerConnection de HTTPS a GIT.
# Здесь получаем developerConnection из файла pom.xml
developerConnection=$(xmllint -xpath "/*[local-name() = 'project' ]//*[local-name() = 'developerConnection']/text()" pom.xml | sed 's|scm:git:ssh://||')
echo developerConnection
echo $developerConnection
# Здесь меняем / на : в URL для git_remote_url
git_remote_url=$(echo $developerConnection| sed 's/gitlab.com//gitlab.com:/g')
echo git_remote_url
echo $git_remote_url
git remote set-url origin $git_remote_url
# Если вы не используете ввстроенную возможность Teamcity получения user и email из ~/.gitconfig, то можно указать их здесь
echo 'git config user.name %TEAM_USER%'
git config user.name %TEAM_USER%
echo 'git config user.email %TEAM_USER_EMAIL%'
git config user.email %TEAM_USER_EMAIL%
# Здесь получаем версию из файла pom.xml
echo "Get version package from pom.xml"
version=`python -c "import xml.etree.ElementTree as ET; print(ET.parse(open('pom.xml')).getroot().find('{http://maven.apache.org/POM/4.0.0}version').text)"`
echo $version
# Почему-то без fetch выдавало ошибку.
git fetch
if [ `git branch -a | egrep "${version}$"` ]
then
echo "Branch exists"
exit 1
fi
# Создаем бранч той версии, который был в файле pom.xml
echo "Create branch"
git checkout -b $version
# Чистый git всегда предлагает настроить политику отправки.
git config --global push.default simple
# Пушим в ветку совпадающую с версией в pom.xml
echo "Push release branch"
git push --set-upstream origin $version
Corrección de erros de incremento de Maven
A tarefa consta de 6 partes. Podería ser refactorizado, pero aínda funciona.
O primeiro paso é comprobar que o brunch non está mestre. Se brunch mestre a tarefa cae.
BRANCH=$(git branch | grep * | cut -d ' ' -f2)
echo "$BRANCH"
if [[ "$BRANCH" == "master" ]]; then
echo 'Branch is master';
echo 'Aborting';
exit 1;
fi
# Здесь получаем версию из файла pom.xml
echo "Get version package from pom.xml"
BRANCH=`python -c "import xml.etree.ElementTree as ET; print(ET.parse(open('pom.xml')).getroot().find('{http://maven.apache.org/POM/4.0.0}version').text)"`
# Приходится делать checkout на нужный бранч.
# Иначе git status показывает detached к нужному бранчу.
# Нужно чтобы git status показывал просто бранч
git checkout $BRANCH
# Экспортируем переменную bash в переменную Teamcity для дальнейшего использования.
echo "##teamcity[setParameter name='BRANCH_FOR_INCREMENT' value='$BRANCH']"
O segundo paso de Maven é cambiar a versión de corrección de erros no ficheiro pom.xml.
O cuarto paso cambia o esquema de conexión en developerConnection de HTTPS a GIT.
E empurra os cambios na rama especificada en Teamcity pola variable %BRANCH_FOR_INCREMENT%.
# Здесь получаем developerConnection из файла pom.xml
developerConnection=$(xmllint -xpath "/*[local-name() = 'project' ]//*[local-name() = 'developerConnection']/text()" pom.xml | sed 's|scm:git:ssh://||')
echo developerConnection
# Здесь меняем / на : в URL для git_remote_url
git_remote_url=$(echo $developerConnection| sed 's/gitlab.com//gitlab.com:/g')
echo git_remote_url
echo $git_remote_url
git remote set-url origin $git_remote_url
# Если вы не используете ввстроенную возможность Teamcity получения user и email из ~/.gitconfig, то можно указать их здесь
echo 'git config user.name %TEAM_USER%'
git config user.name %TEAM_USER%
echo 'git config user.email %TEAM_USER_EMAIL%'
git config user.email %TEAM_USER_EMAIL%
echo 'git add .'
git add .
echo 'git commit -m "Increment bugfix"'
git commit -m "Increment bugfix"
git push --set-upstream origin %BRANCH_FOR_INCREMENT%
O quinto paso é obter a partir do ficheiro pom.xml versión e instálao Teamcity variable TAG_FROM_VERSION. Teña en conta que a versión do ficheiro pom.xml sen a letra v diante. E a etiqueta, baseada nesta versión, xa ten a letra v ao principio.
echo "Get version package from pom.xml"
VERSION_AFTER_CHANGE=`python -c "import xml.etree.ElementTree as ET; print(ET.parse(open('pom.xml')).getroot().find('{http://maven.apache.org/POM/4.0.0}version').text)"`
echo $VERSION_AFTER_CHANGE
echo "##teamcity[setParameter name='TAG_FROM_VERSION' value='v$VERSION_AFTER_CHANGE']"
Sexto paso: etiquetado corrección de erros versións. Isto faise usando Maven coa opción requirida en Obxectivo.