ProHoster > блог > Администрација > Кругови на пеколот со GitHub Actions (градење на CI/CD гасовод за проект Java)
Кругови на пеколот со GitHub Actions (градење на CI/CD гасовод за проект Java)
Честопати треба да изградам гасовод за градежни проекти во Јава. Понекогаш тоа е со отворен код, понекогаш не е. Неодамна решив да се обидам да преместам некои од моите складишта од Travis-CI и TeamCity на GitHub Actions, и еве што произлезе од тоа.
Што ќе автоматизираме?
Прво, ни треба проект што ќе го автоматизираме, ајде да направиме мала апликација во Spring boot / Java 11 / Maven. За потребите на овој напис, воопшто нема да не интересира логиката на апликацијата, важна ни е инфраструктурата околу апликацијата, па затоа ќе ни биде доволен едноставен REST API контролер.
Изворите можете да ги погледнете овде: github.com/antkorwin/github-actions Сите фази на изградба на гасовод се рефлектираат во барањата за повлекување за овој проект.
JIRA и планирање
Вреди да се каже дека ние обично користиме JIRA како следење на проблеми, па ајде да создадеме посебна табла за овој проект и да ги додадеме првите проблеми таму:
Малку подоцна ќе се вратиме на тоа какви интересни работи JIRA и GitHub можат да понудат во комбинација.
Ние го автоматизираме склопувањето на проектот
Нашиот тест-проект е изграден преку maven, така што неговото градење е прилично едноставно, сè што ни треба е mvn чист пакет.
За да го направите ова користејќи Github Actions, ќе треба да создадеме датотека во складиштето што го опишува нашиот работен тек, ова може да се направи со обична yml-датотека, не можам да кажам дека ми се допаѓа „yml програмирање“, но што да правиме - тоа го правиме во .github/ directory workflow/ датотека build.yml во која ќе ги опишеме дејствата при градењето на главната гранка:
on — ова е опис на настанот на кој ќе биде промовирано нашето сценарио.
на: pull_request/push — покажува дека овој работен тек треба да се активира секогаш кога ќе се притисне главниот и ќе се креираат барања за повлекување.
Следното е опис на задачите (работни места) и чекори на извршување (чекори) за секоја задача.
работи-на - овде можеме да го избереме целниот оперативен систем, изненадувачки, можете дури и да изберете Mac OS, но на приватни складишта ова е прилично скапо (во споредба со Linux).
употреба ви овозможува повторно да користите други дејства, на пример, користејќи ја акцијата дејства/setup-java ја инсталираме околината за Java 11.
Со помош на со можеме да ги специфицираме параметрите со кои ја стартуваме акцијата, во суштина тоа се аргументите што ќе се пренесат на акцијата.
Останува само да се изврши изградбата на проектот со Maven: run: mvn -B clean package знаме -B вели дека ни треба неинтеактивен режим, така што мавенот одеднаш не сака да не праша нешто
Одлично! Сега, секој пат кога ќе се посветите на мајсторот, започнува изградбата на проектот.
Автоматизирање на лансирањето на тестовите
Склопувањето е добро, но во реалноста, проектот може безбедно да се состави, но не и да работи. Затоа, следниот чекор е да се автоматизираат тестовите. Дополнително, доста е погодно да ги погледнете резултатите од полагањето на тестовите кога правите преглед за односи со јавноста - сигурно знаете дека тестовите поминуваат и никој не заборавил да ја изврши својата гранка пред да изврши спојување.
Ќе извршиме тестови при креирање на барање за повлекување и ќе се споиме во главниот, а во исто време ќе додадеме креирање на извештај за покриеност со код.
За покривање на тестовите, користам codecov во врска со приклучокот jacoco. codecov има свое дејство, но му треба токен за да работи со нашето барање за повлекување:
${{ secrets.CODECOV_TOKEN }} — ќе ја видиме оваа конструкција повеќе од еднаш, Secrets е механизам за складирање тајни во GitHub, таму можеме да напишеме лозинки/токени/домаќини/урлови и други податоци кои не треба да бидат вклучени во базата на кодови на складиштето.
Можете да додадете променлива во тајните во поставките на складиштето на GitHub:
Може да добиете токен на codecov.io По овластувањето преку GitHub, за да додадете јавен проект, само треба да следите врска како оваа: Корисничко име на GitHub/[име на репо]. Може да се додаде и приватно складиште; за да го направите ова, треба да и дадете права на кодови на апликацијата во Github.
Сега ботот codecov ќе го внесе секое од нашите барања за повлекување и ќе додаде графикон за промена на покриеноста:
Ајде да додадеме статичен анализатор
Во повеќето мои проекти со отворен код користам хидролокатор за анализа на статички код, прилично е лесно да се поврзете со travis-ci. Значи, тоа е логичен чекор кога мигрирате на GitHub Actions да го сторите истото. Акциониот пазар е кул работа, но овој пат ме изневери малку, бидејќи од навика ја најдов акцијата што ми требаше и ја додадов во работниот тек. Но, се покажа дека сонарот не поддржува работа преку акција за анализа на проекти на maven или gradle. Се разбира, ова го пишува во документацијата, но кој го чита?!
Не е возможно преку акција, затоа ќе го направиме преку додатокот mvn:
SONAR_TOKEN - може да се добијат на sonarcloud.io и треба да го регистрирате во тајни. GITHUB_TOKEN - ова е вграден токен што го генерира GitHub, со помош на кој sonarcloud[bot] ќе може да се најави на Git за да ни остави пораки во барањата за повлекување.
Dsonar.projectKey — името на проектот во сонарот, можете да го видите во поставките на проектот.
Дсонар.организација — име на организацијата од GitHub.
Правиме барање за повлекување и чекаме sonarcloud[bot] да дојде во коментарите:
Управување со ослободување
Изградбата е конфигурирана, тестовите се извршени и можеме да објавиме. Ајде да погледнеме како GitHub Actions може многу да го олесни управувањето со изданија.
На работа имам проекти чијашто база на код е во bitbucket (сè е како во приказната „Денот пишувам на bitbucket, ноќе се обврзувам на GitHub“). За жал, bitbucket нема вградени алатки за управување со ослободување. Ова е проблем, бидејќи за секое издание треба рачно да креирате страница во слив и да ги фрлите таму сите функции вклучени во изданието, да пребарувате низ палатите на умот, задачите во џира, обврските во складиштето. Има многу шанси да направите грешка, можете да заборавите нешто или да внесете нешто што е веќе објавено минатиот пат, понекогаш едноставно не е јасно како да се класифицира барањето за повлекување - дали е тоа функција или поправка на грешки, или тестови за уредување или нешто инфраструктурно.
Како можат дејствата на GitHub да ни помогнат? Има одлична акција - изготвувач на ослободување, ви овозможува да поставите шаблон за датотека за белешки за ослободување за да поставите категории на барања за повлекување и автоматски да ги групирате во датотеката за белешки за ослободување:
Пример шаблон за поставување извештај (.github/release-drafter.yml):
name-template: 'v$NEXT_PATCH_VERSION'
tag-template: 'v$NEXT_PATCH_VERSION'
categories:
- title: ' New Features'
labels:
- 'type:features'
# в эту категорию собираем все PR с меткой type:features
- title: ' Bugs Fixes'
labels:
- 'type:fix'
# аналогично для метки type:fix и т.д.
- title: ' Documentation'
labels:
- 'type:documentation'
- title: ' Configuration'
labels:
- 'type:config'
change-template: '- $TITLE @$AUTHOR (#$NUMBER)'
template: |
## Changes
$CHANGES
Додајте скрипта за да генерирате нацрт издание (.github/workflows/release-draft.yml):
Сите барања за повлекување отсега ќе се собираат во белешките за ослободување автоматски - магија!
Тука може да се појави прашањето: што ако програмерите заборават да стават ознаки во ПР? Тогаш не е јасно во која категорија да го ставите, и повторно ќе треба да се справите со тоа рачно, со секој ПР посебно. За да го решиме овој проблем, можеме да користиме друго дејство - проверувач на етикети - го проверува присуството на ознаки на барањето за повлекување. Ако нема потребни ознаки, тогаш проверката ќе биде неуспешна и ќе видиме порака за ова во нашето барање за повлекување.
Сега секое барање за повлекување мора да биде означено со една од ознаките: тип: поправка, тип: карактеристики, тип: документација, тип: тестови, тип: конфигурација.
Автоматска прибелешка на барања за повлекување
Бидејќи допревме на тема како ефективна работа со барања за повлекување, вреди да се зборува за такво дејство како етикетирање, става ознаки во ПР врз основа на кои датотеки се сменети. На пример, можеме да го означиме како [build] секое барање за повлекување што содржи промени во директориумот .github/workflow.
Не успеав да го спарам дејството што автоматски поставува етикети во барањата за повлекување со дејството што проверува присуство на потребни етикети; етикетата за совпаѓање не сака да ги гледа етикетите додадени од ботот. Се чини дека е полесно да напишете своја акција која ги комбинира двете фази. Но, дури и во оваа форма е доста погодно за употреба; треба да изберете етикета од списокот кога креирате барање за повлекување.
Време е за распоредување
Пробав неколку опции за распоредување преку GitHub Actions (преку ssh, преку scp и користејќи docker-hub), и можам да кажам дека, најверојатно, ќе најдете начин да го прикачите бинарното на серверот, без разлика колку е искривен вашиот гасовод е.
Ми се допадна опцијата за чување на целата инфраструктура на едно место, па ајде да погледнеме како да се распоредиме на GitHub пакетите (ова е складиште за бинарни содржини, npm, тегла, докер).
Скрипта за градење докер слика и нејзино објавување во GitHub пакети:
Прво, треба да ја изградиме датотеката JAR на нашата апликација, по што ја пресметуваме патеката до регистарот за докер на GitHub и името на нашата слика. Овде има неколку трикови на кои сè уште не сме сретнале:
конструкција како: echo „::set-output name=NAME::VALUE“ ви овозможува да ја поставите вредноста на променливата во тековниот чекор, за да може потоа да се чита во сите други чекори.
може да ја добиете вредноста на променливата поставена во претходниот чекор преку идентификаторот на овој чекор: ${{ steps.global_env.outputs.DOCKERHUB_IMAGE_NAME }}
Стандардната променлива GITHUB_REPOSITORY го складира името на складиштето и неговиот сопственик („сопственик/репо-име“). За да исечеме сè од оваа линија освен името на складиштето, ќе користиме баш синтакса: ${GITHUB_REPOSITORY#*/}
За да ја означиме верзијата на сликата, ги користиме првите цифри од хашот SHA на задолжението - GITHUB_SHA има и нијанси овде, ако правите такви градби не само кога се спојувате во главниот, туку и според креирањето на барањето за повлекување настан, тогаш SHA може да не се совпаѓа со хашот што го гледаме во историјата на git, бидејќи акцијата дејства/отплата прави свој уникатен хаш за да избегне ќор-сокак дејства во ПР.
Ако сè функционира добро, тогаш отворајќи го делот за пакети (https://github.com/antkorwin/github-actions/packages) во складиштето, ќе видите нова слика на докер:
Таму, исто така, можете да видите список на верзии на сликата на докерот.
Останува само да го конфигурираме нашиот сервер да работи со овој регистар и да ја рестартираме услугата. Веројатно ќе зборувам за тоа како да го направам тоа преку системд друг пат.
Мониторинг
Ајде да погледнеме едноставна опција за тоа како да направите здравствена проверка за нашата апликација користејќи GitHub Actions. Нашата апликација за подигање има активирач, така што не ни треба да пишуваме API за да го провериме нејзиниот статус; ние веќе направивме сè за мрзливите. Само треба да го повлечете домаќинот: SERVER-URL:PORT/actuator/health
Сè што ни треба е да напишеме задача за да го провериме серверот користејќи cron, и ако одеднаш не ни одговори, тогаш ќе испратиме известување преку телеграма.
Прво, ајде да откриеме како да извршиме работен тек на cron:
Ајде да го провериме статусот на серверот рачно преку curl:
jobs:
ping:
runs-on: ubuntu-18.04
steps:
- name: curl actuator
id: ping
run: |
echo "::set-output name=status::$(curl ${{secrets.SERVER_HOST}}/api/actuator/health)"
- name: health check
run: |
if [[ ${{ steps.ping.outputs.status }} != *"UP"* ]]; then
echo "health check is failed"
exit 1
fi
echo "It's OK"
Прво, го зачувуваме во променлива она што серверот одговорил на барањето, во следниот чекор проверуваме дали статусот е UP и, ако не е така, тогаш излегуваме со грешка. Ако треба да „премрднете“ некоја акција со вашите раце, тогаш излез 1 - соодветно оружје.
- name: send alert in telegram
if: ${{ failure() }}
uses: appleboy/telegram-action@master
with:
to: ${{ secrets.TELEGRAM_TO }}
token: ${{ secrets.TELEGRAM_TOKEN }}
message: |
Health check of the:
${{secrets.SERVER_HOST}}/api/actuator/health
failed with the result:
${{ steps.ping.outputs.status }}
Испраќаме телеграма само ако дејството не успеа на претходниот чекор. За да испратиме порака, користиме appleboy/telegram-action; можете да прочитате за тоа како да добиете бот токен и ID за разговор во документацијата: github.com/appleboy/telegram-action
Не заборавајте да напишете во тајните на Github: URL за серверот и токени за ботот на телеграмата.
Бонус патека - JIRA за мрзливите
Ветив дека ќе се вратиме во ЈИРА и се вративме. Стотици пати сум забележал ситуација на стенд-ап кога програмерите направиле функција, споиле гранка, но заборавиле да го одвлечат проблемот во JIRA. Се разбира, ако сето ова беше направено на едно место, ќе беше полесно, но всушност пишуваме код во IDE, спојуваме гранки во bitbucket или GitHub, а потоа ги влечеме задачите во Jira, за ова треба да отвориме нови прозорци , понекогаш повторно најавувајте се и сл. Кога совршено се сеќавате што треба да направите следно, тогаш нема смисла повторно да ја отворите таблата. Како резултат на тоа, наутро на standup треба да потрошите време за ажурирање на таблата со задачи.
GitHub исто така ќе ни помогне во оваа рутинска задача; за почеток, можеме автоматски да ги влечеме проблемите во колоната code_review кога ќе поднесеме барање за повлекување. Сè што треба да направите е да ја следите конвенцијата за именување на филијалата:
[имя проекта]-[номер таска]-название
на пример, ако проектниот клуч „GitHub Actions“ е GA, тогаш GA-8-jira-bot може да биде гранка за спроведување на задачата ГА-8.
Интеграцијата со JIRA функционира преку акции од Atlassian, тие не се совршени, морам да кажам дека некои од нив воопшто не функционираа за мене. Но, ќе разговараме само за оние кои дефинитивно функционираат и активно се користат.
Прво треба да се најавите на JIRA користејќи ја акцијата: atlassian/gajira-login
Го извлекуваме идентификаторот на задачата од името на гранката:
- name: Find Issue
id: find_issue
shell: bash
run: |
echo "::set-output name=ISSUE_ID::$(echo ${GITHUB_HEAD_REF} | egrep -o 'GA-[0-9]{1,4}')"
echo brach name: $GITHUB_HEAD_REF
echo extracted issue: ${GITHUB_HEAD_REF} | egrep -o 'GA-[0-9]{1,4}'
- name: Check Issue
shell: bash
run: |
if [[ "${{steps.find_issue.outputs.ISSUE_ID}}" == "" ]]; then
echo "Please name your branch according to the JIRA issue: [project_key]-[task_number]-branch_name"
exit 1
fi
echo succcessfully found JIRA issue: ${{steps.find_issue.outputs.ISSUE_ID}}
Ако пребарувате на пазарот на GitHub, можете да најдете акција за оваа задача, но морав да го напишам истото користејќи grep користејќи го името на гранката, бидејќи оваа акција од Atlassian не сакаше да работи на мојот проект на кој било начин. , за да дознаете што не е во ред таму - подолго отколку да го правите истото со вашите раце.
Останува само да ја преместите задачата во колоната „Преглед на код“ кога креирате барање за повлекување:
Има специјална акција за ова на GitHub, сè што му треба е ID на проблем добиен во претходниот чекор и овластувањето во JIRA што го направивме погоре.
На ист начин, можете да влечете задачи кога се спојувате во главниот, и други настани од работниот тек на GitHub. Во принцип, сè зависи од вашата имагинација и желба да ги автоматизирате рутинските процеси.
Наоди
Ако го погледнете класичниот DEVOPS дијаграм, ги опфативме сите фази, освен можеби функционирањето, мислам дека ако се обидете, можете да најдете некоја акција на пазарот за интеграција со системот за помош, па ќе претпоставиме дека гасоводот се сврте да биде темелна и може да се извлечат заклучоци врз основа на неговата употреба.
Позитивни:
Пазар со готови акции за сите прилики, ова е многу кул. Во повеќето од нив, можете исто така да го погледнете изворниот код за да разберете како да решите сличен проблем или да објавите барање за функција до авторот директно во складиштето на GitHub.
Изборот на целната платформа за склопување: Linux, mac os, windows е доста интересна карактеристика.
Пакетите Github се одлична работа, погодно е да се задржи целата инфраструктура на едно место, не мора да сурфате низ различни прозорци, сè е во радиус од еден или два кликнувања на глувчето и е совршено интегрирано со GitHub Actions. Поддршката за регистарот Docker во бесплатната верзија е исто така добра предност.
GitHub крие тајни во логовите за изградба, па затоа неговото користење за складирање лозинки и токени не е толку страшно. За време на сите мои експерименти, никогаш не можев да ја видам тајната во нејзината чиста форма во конзолата.
Бесплатно за проекти со отворен код
Конс:
ИМЛ, добро, не ми се допаѓа. Кога работите со таков тек, најчестата порака за commit што ја имам е „поправете го форматот yml“, потоа заборавате да ставите таб некаде или го пишувате на погрешна линија. Во принцип, седењето пред екран со транспортер и линијар не е најпријатното искуство.
DEBUG, дебагирање на протокот со заложби, извршување на обнова и излез на конзолата не е секогаш погодно, но тоа е повеќе од категоријата „претерано сте“; вие сте навикнати да работите со практична IDEA, кога можете да дебагирате што било .
Можете да го напишете вашето дејство на било што ако го завиткате во Docker, но само javascript е природно поддржан, се разбира ова е прашање на вкус, но јас би претпочитал нешто друго наместо js.
Следната недела ќе настапам со извештај на конференцијата Хајзенбуг 2020 Питер. Ќе ви кажам не само како да избегнете грешки при подготовката на податоците за тестирање, туку и да ги споделам моите тајни за работа со збирки податоци во апликациите Java!