Ne kemi folur tashmĂ« pĂ«r mjetin tonĂ« GitOps , dhe kĂ«tĂ« herĂ« do tĂ« dojmĂ« tĂ« ndajmĂ« pĂ«rvojĂ«n e ndĂ«rtimit tĂ« faqes sĂ« internetit me dokumentacionin e projektit vetĂ« â (versioni i tij nĂ« gjuhĂ«n ruse â ). Kjo Ă«shtĂ« njĂ« faqe statike e zakonshme, megjithatĂ« ndĂ«rtimi i saj Ă«shtĂ« interesant sepse Ă«shtĂ« realizuar me njĂ« numĂ«r dinamik artefaktesh.

Nuk do tĂ« thellohemi nĂ« nuancat e strukturĂ«s sĂ« faqes: gjenerimin e menusĂ« sĂ« pĂ«rbashkĂ«t pĂ«r tĂ« gjitha versionet, faqet me informacion mbi lĂ«shimet etj. â do tĂ« qĂ«ndrojmĂ« mĂ« mirĂ« te pyetjet dhe veçoritĂ« e ndĂ«rtimit dinamik dhe pak mbi proceset pĂ«rkatĂ«se CI/CD.
Hyrja: si është ndërtuar faqeja
Të fillojmë me faktin se dokumentacioni për werf ruhet së bashku me kodin e tij. Kjo kërkon disa kërkesa për zhvillimin, që në përgjithësi dalin jashtë përmbajtjes së këtij artikulli, por të paktën mund të thuhet se:
- Funksionet e reja të werf nuk duhet të publikohen pa rinovimin e dokumentacionit dhe, anasjelltas, çdo ndryshim në dokumentacion nënkupton lëshimin e një versioni të ri të werf;
- Projekti ka zhvillim të intensifikuar: versionet e reja mund të lëshohen disa herë në ditë;
- Ădo operacion manual pĂ«r ndarjen e faqes me versionin e ri tĂ« dokumentacionit Ă«shtĂ« tĂ« paktĂ«n i lodhshĂ«m;
- Në projekt është pranuar qasja e versionimit , me 5 kanale stabiliteti. Procesi i lëshimit nënkupton kalimin e versioneve përmes kanaleve në renditjen e rritjes së stabilitetit: nga alpha deri në rock-solid;
- Faqja ka një version në gjuhën ruse, i cili "jeton dhe zhvillohet" (dmth. përmbajtja e saj përditësohet) paralelisht me versionin kryesor (dmth. versionin në anglisht).
PĂ«r tĂ« fshehur nga pĂ«rdoruesi tĂ« gjithĂ« kĂ«tĂ« "kuzhinĂ« tĂ« brendshme", duke i ofruar atij atĂ« qĂ« "funksionon thjesht", ne krijuam njĂ« mjet tĂ« veçantĂ« pĂ«r instalimin dhe pĂ«rditĂ«simin e werf â Ă«shtĂ« . Mjafton tĂ« tregoni numrin e lĂ«shimit dhe kanalin e stabilitetit qĂ« jeni tĂ« gatshĂ«m tĂ« pĂ«rdorni, dhe multiwerf do tĂ« kontrollojĂ« nĂ«se ka njĂ« version tĂ« ri nĂ« kanal dhe do ta shkarkojĂ« atĂ« nĂ« rast nevoje.
NĂ« menunĂ« e zgjedhjes sĂ« versioneve nĂ« faqe janĂ« tĂ« disponueshme versionet mĂ« tĂ« fundit tĂ« werf nĂ« çdo kanal. NĂ« mĂ«nyrĂ« qĂ«, adresa hap versionin e kanalit mĂ« tĂ« stabilizuar pĂ«r lĂ«shimin mĂ« tĂ« fundit â ai gjithashtu indeksohet nga motorĂ«t e kĂ«rkimit. Dokumentacioni pĂ«r kanalin Ă«shtĂ« i disponueshĂ«m nĂ« adresa tĂ« veçanta (pĂ«r shembull, pĂ«r lĂ«shimin beta 1.0).
Në përfundim, faqja e internetit është e disponueshme në versionet e mëposhtme:
- root (hapet si parazgjedhje),
- për çdo kanal aktiv të azhurnimeve për çdo version (p.sh., ).
Për të gjeneruar një version specifik të faqes së internetit, zakonisht mjafton të kryhet kompilimi i tij me ndihmën e , duke ekzekutuar në katalogun /docs e depozitës werf komandën përkatëse (jekyll build), pas kalimit në Git-tag-un e versionit të nevojshëm.
Nuk mbetet tjetër veçse të shtohet se:
- për ndërtim përdoret vetë utilitari (werf);
- proceset CI/CD janë të ndërtuara mbi bazën e GitLab CI;
- dhe, sigurisht, gjithë kjo funksionon në Kubernetes.
Detyrat
Tani do të formulojmë detyrat, duke marrë parasysh të gjitha këto karakteristika të përshkruara:
- Pas ndërrimit të versionit të werf në çdo kanal azhurnimi dokumentacioni në faqen e internetit duhet të azhurnohet automatikisht.
- Për zhvillim, duhet të kemi mundësinë ndonjëherë të shqyrtojmë versionet paraprak të faqes.
Rikompilimi i faqes duhet të kryhet pas ndërrimit të versionit në çdo kanal nga Git-tagat përkatëse, por në procesin e ndërtimit të imazhit do të marrë formën e mëposhtme:
- Duke marrë parasysh se lista e versioneve në kanale ndryshon, duhet të rikompilohet vetëm dokumentacioni për kanalet ku ka ndryshuar versioni. Sepse rikompilimi i gjithçkaje nga e para nuk është shumë i bukur.
- VetĂ« grupi i kanaleve pĂ«r lĂ«shimet mund tĂ« ndryshojĂ«. NĂ« njĂ« moment, pĂ«r shembull, mund tĂ« mos ketĂ« version nĂ« kanalet mĂ« tĂ« qĂ«ndrueshme se lĂ«shimi i aksesit tĂ« hershĂ«m 1.1, por me kalimin e kohĂ«s ato do tĂ« shfaqen â a duhet ta ndryshojmĂ« ndĂ«rtimin manualisht nĂ« kĂ«tĂ« rast?
Kështu që ndërtimi varet nga të dhëna të jashtme në ndryshim.
Implementimi
Zgjedhja e qasjes
Si një opsion, mund të ekzekutojmë çdo version të nevojshëm si një pod të veçantë në Kubernetes. Ky opsion parashikon një numër më të madh objektesh në klaster, i cili do të rritet me rritjen e numrit të lëshimeve stabile të werf. Dhe kjo nga ana e saj parashikon një mirëmbajtje më të komplikuar: për çdo version ka një server HTTP të vetin, madje me ngarkesë të vogël. Sigurisht, kjo sjell gjithashtu dhe kosto më të larta për burimet.
Ne kemi shkuar nĂ« rrugĂ«n e ndĂ«rtimit tĂ« tĂ« gjitha versioneve tĂ« nevojshme nĂ« njĂ« imazh. Statika e kompiliuar e tĂ« gjitha versioneve tĂ« faqes Ă«shtĂ« nĂ« kontejnerin me NGINX, dhe trafiku nĂ« pĂ«rkatĂ«shin Deployment vjen pĂ«rmes NGINX Ingress. StrukturĂ« e thjeshtĂ« â aplikacion pa gjendje â lejon tĂ« lehtĂ«sojĂ« skalimin e Deployment-it (nĂ« pĂ«rputhje me ngarkesĂ«n) me ndihmĂ«n e Kubernetes-it.
Duke të qenë më të saktë, ne mbledhim dy pamje: një për konturin e prodhimit, dhe një tjetër, për konturin dev. Pamja shtesë përdoret (nisët) vetëm në konturin dev së bashku me të parën dhe përmban versionin e faqes nga komiti i rishikimit, ndërsa routing-u midis tyre bëhet përmes burimeve Ingress.
werf vs git clone dhe artefakte
Siç u përmend, për të gjeneruar statikën e faqes për një version të caktuar të dokumentacionit, është e nevojshme të kryeni një ndërtim, duke u kaluar në etiketën përkatëse të depozitës. Do të ishte e mundur ta bënit këtë duke klonuar depozitën çdo herë gjatë ndërtimit, duke zgjedhur etiketat përkatëse nga lista. Megjithatë, kjo është një operacion mjaft i burimeve dhe, për më tepër, kërkon shkrimin e udhëzimeve të ndërlikuara⊠Një minus tjetër i rëndësishëm është se me këtë qasje nuk ka mundësi për të bërë ndonjë keƥim gjatë ndërtimit.
Këtu na vjen në ndihmë vetë utilitari werf, i cili implementon cache të mençur dhe lejon të përdorim . Përdorimi i werf për të shtuar kod nga depozita do ta përshpejtojë ndërtimin, sepse werf në thelb e klonon depozitën një herë dhe pastaj kryen të fetch kur është e nevojshme. Përveç kësaj, gjatë shtimit të të dhënave nga depozita mund të zgjedhim vetëm direktoritë e nevojshme (në rastin tonë është katalogu docs), e cila do të ulë ndjeshëm volumin e të dhënave të shtuar.
Duke qenë se Jekyll është një mjet i destinuar për kompilimin e statikës dhe nuk është e nevojshme në pamjen përfundimtare, do ishte logjike të kryhej kompilimi në , ndërsa në pamjen përfundimtare të importohet vetëm rezultati i kompilimit.
Shkruajmë werf.yaml
Pra, ne u përcaktuam që do të kompilojmë çdo version në një artefakt të veçantë werf. Megjithatë, ne nuk e dimë se sa artefakte do të ketë gjatë ndërtimit, prandaj nuk mund të shkruajmë një konfiguratë të fiksuar të ndërtimit (në të vërtetë mund të bëjmë, por nuk do të jetë efikase).
werf lejon përdorimin e në dosjen e tij të konfigurimit (werf.yaml), dhe kjo jep mundësinë për të gjeneruar konfigurimin "në flakë" në varësi të të dhënave të jashtme (ato që na nevojiten!). Të dhënat e jashtme në rastin tonë janë informacioni mbi versionet dhe lëshimet, mbi të cilin ne ndërtuam numrin e nevojshëm të artefakteve dhe morëm në rezultat dy pamje: werf-doc dhe werf-dev për të nisur në konture të ndryshme.
Të dhënat e jashtme dërgohen nëpërmjet variablave të mjedisit. Këtu është përbërja e tyre:
-
RELEASESâ njĂ« rrjesht me listĂ«n e lĂ«shimeve dhe versionit aktual pĂ«rkatĂ«s tĂ« werf, nĂ« formĂ«n e njĂ« liste pĂ«rmes hapĂ«sirĂ«s sĂ« vlerave nĂ« formatin%. Shembull:1.0%v1.0.4-beta.20 -
CHANNELSâ njĂ« rrjesht me listĂ«n e kanaleve dhe versionit aktual pĂ«rkatĂ«s tĂ« werf, nĂ« formĂ«n e njĂ« liste pĂ«rmes hapĂ«sirĂ«s sĂ« vlerave nĂ« formatin%. Shembull:1.0-beta%v1.0.4-beta.20 1.0-alpha%v1.0.5-alpha.22 -
ROOT_VERSIONâ versioni i lĂ«shimit tĂ« werf pĂ«r t'u shfaqur si parazgjedhje nĂ« faqe (nuk Ă«shtĂ« gjithmonĂ« e nevojshme tĂ« shfaqet dokumentacioni pĂ«r numrin mĂ« tĂ« lartĂ« tĂ« lĂ«shimit). Shembuj:v1.0.4-beta.20 -
REVIEW_SHAâ hash i commit-it tĂ« rishikimit, nga i cili duhet tĂ« ndĂ«rtohet versioni pĂ«r konturin testues.
KĂ«ta variabla do tĂ« plotĂ«sohen nĂ« pipeline-in GitLab CI, dhe si pikĂ«risht â Ă«shtĂ« shkruar mĂ« poshtĂ«.
Së pari, për lehtësi, do të përcaktojmë në werf.yaml variablat e Go-shablloneve, duke u dhënë atyre vlera nga variablat e mjedisit:
{{ $_ := set . "WerfVersions" (cat (env "CHANNELS") (env "RELEASES") | splitList " ") }}
{{ $Root := . }}
{{ $_ := set . "WerfRootVersion" (env "ROOT_VERSION") }}
{{ $_ := set . "WerfReviewCommit" (env "REVIEW_SHA") }} PĂ«rshkrimi i artefaktit pĂ«r kompilimin e statikĂ«s sĂ« versionit tĂ« faqes Ă«shtĂ« nĂ« thelb i njĂ«jtĂ« pĂ«r tĂ« gjitha rastet qĂ« na nevojiten (pĂ«rfshirĂ«, gjenerimin e versionit themelor, si dhe versionin pĂ«r konturin dev). Prandaj, do ta nxjerrim atĂ« nĂ« njĂ« bllok tĂ« veçantĂ« me ndihmĂ«n e funksionit define â pĂ«r ripĂ«rdorim tĂ« mĂ«tejshĂ«m me ndihmĂ«n e include. Shabllonit do t'i kalojmĂ« argumentĂ«t e mĂ«poshtĂ«m:
-
Versionâ versionin e gjeneruar (emri i etiketĂ«s); -
Channelâ emri i kanaleve tĂ« azhurnimit, pĂ«r tĂ« cilin gjenerohet artefakti; -
Commitâ hash i commit-it, nĂ«se artefakti gjenerohet pĂ«r commit-in e rishikimit; - konteksti.
Përshkrimi i shabllonit të artefaktit
{{- define "doc_artifact" -}}
{{- $Root := index . "Root" -}}
artifact: doc-{{ .Channel }}
from: jekyll/builder:3
mount:
- from: build_dir
to: /usr/local/bundle
ansible:
install:
- shell: |
export PATH=/usr/jekyll/bin/:$PATH
- name: "Instalo Mjetet"
shell: bundle install
args:
executable: /bin/bash
chdir: /app/docs
beforeSetup:
{{- if .Commit }}
- shell: echo "Rishikoni SHA - {{ .Commit }}."
{{- end }}
{{- if eq .Channel "root" }}
- name: "releases.yml HASH: {{ $Root.Files.Get "releases.yml" | sha256sum }}"
copy:
content: |
{{ $Root.Files.Get "releases.yml" | indent 8 }}
dest: /app/docs/_data/releases.yml
{{- else }}
- file:
path: /app/docs/_data/releases.yml
state: touch
{{- end }}
- file:
path: "{{`{{ item }}`}}"
state: directory
mode: 0777
with_items:
- /app/main_site/
- /app/sq_site/
- file:
dest: /app/docs/pages_sq/cli
state: link
src: /app/docs/pages/cli
- shell: |
echo -e "werfVersion: {{ .Version }}
werfChannel: {{ .Channel }}" > /tmp/_config_additional.yml
export PATH=/usr/jekyll/bin/:$PATH
{{- if and (ne .Version "review") (ne .Channel "root") }}
{{- $_ := set . "BaseURL" ( printf "v%s" .Channel ) }}
{{- else if ne .Channel "root" }}
{{- $_ := set . "BaseURL" .Channel }}
{{- end }}
jekyll build -s /app/docs -d /app/_main_site/{{ if .BaseURL }} --baseurl /{{ .BaseURL }}{{ end }} --config /app/docs/_config.yml,/tmp/_config_additional.yml
jekyll build -s /app/docs -d /app/_sq_site/{{ if .BaseURL }} --baseurl /{{ .BaseURL }}{{ end }} --config /app/docs/_config.yml,/app/docs/_config_sq.yml,/tmp/_config_additional.yml
args:
executable: /bin/bash
chdir: /app/docs
git:
- url: https://github.com/flant/werf.git
to: /app/
owner: jekyll
group: jekyll
{{- if .Commit }}
commit: {{ .Commit }}
{{- else }}
tag: {{ .Version }}
{{- end }}
stageDependencies:
install: ['docs/Gemfile','docs/Gemfile.lock']
beforeSetup: '**/*'
includePaths: 'docs'
excludePaths: '**/*.sh'
{{- end }} Emri i artefaktit duhet të jetë unik. Ne mund ta arrijmë këtë, për shembull, duke shtuar emrin e kanalit (vlera e variablit .Channel) si një sufiks të emrit të artefaktit: artifact: doc-{{ .Channel }}. Por duhet të kuptojmë se gjatë importit nga artefaktet, do të duhet të referohemi në emra të tillë.
Kur përshkruhet artefakti, përdoret një mundësi e tillë e werf si . Montimi me specifikimin e katalogut të shërbimit build_dir lejon ruajtjen e caches së Jekyll midis rasteve të pipeline-it, çka e përshpejton ndjeshëm rindërtimin.
Po ashtu, mund tĂ« keni vĂ«nĂ« re pĂ«rdorimin e skedarit releases.yml â ky Ă«shtĂ« njĂ« skedar YAML me tĂ« dhĂ«nat mbi lĂ«shimet, i kĂ«rkuar nga (artefakti, i marrĂ« nga ekzekutimi i pipeline-it). Ai Ă«shtĂ« i nevojshĂ«m gjatĂ« kompilimit tĂ« faqes, por nĂ« kontekstin e kĂ«tij artikulli, na intereson se nga gjendja e tij varet rindĂ«rtimi i vetĂ«m njĂ« artefakti â artefakti i versionit rrĂ«njor (nĂ« artefakte tĂ« tjera nuk Ă«shtĂ« i nevojshĂ«m).
Kjo realizohet nëpërmjet operatorit kusht të nëse shablloneve Go dhe konstrukcionit {{ $Root.Files.Get "releases.yml" | sha256sum }} në fazën . Kjo funksionon kështu: kur është në proces ndërtimi artefakti për versionin rrënjor (variabla .Channel është root) hash-i i skedarit releases.yml ka ndikim në nënshkrimin e të gjithë fazës, pasi përbën një komponent të emrit të punës Ansible (parametri emri). Kështu, kur ndryshon përmbajtja skedare releases.yml artefakti përkatës do të rindërtohet.
Kujdes gjithashtu me punën me repositorin e jashtëm. Në imazhin e artefaktit nga , shtohet vetëm katalogu /docs, dhe në varësi të parametrave të kaluar, të dhënat e nevojshme të tags ose komiteteve të rishikimit shtohen menjëherë.
Për të përdorur modelin e artefaktit për të gjeneruar përshkrimin e artefaktit për versionet e kanaleve dhe rreleaseve të kaluara, organizojmë një cikël mbi variablën .WerfVersions në werf.yaml:
{{ range .WerfVersions -}}
{{ $VersionsDict := splitn "%" 2 . -}}
{{ dict "Version" $VersionsDict._1 "Channel" $VersionsDict._0 "Root" $Root | include "doc_artifact" }}
---
{{ end -}} Dhe pĂ«r shkak se cikli do tĂ« gjenerojĂ« disa artefakte (shpresojmĂ« tĂ« jetĂ« kĂ«shtu), Ă«shtĂ« e nevojshme tĂ« merren parasysh ndarĂ«sit midis tyre â sekuenca --- (pĂ«r mĂ« shumĂ« rreth sintaksĂ«s sĂ« skedarit tĂ« konfigurimit shihni nĂ« ). Siç u pĂ«rcaktua mĂ« parĂ«, kur thĂ«rrasim modelin nĂ« cikĂ«l, ne kalojmĂ« parametrat e versionit, URL-nĂ« dhe kontekstin rrĂ«njor.
Njësoj, por tashmë pa cikël, thërrasim modelin e artefaktit për «rastet speciale»: për versionin rrënjor, si dhe versionin nga komiteti i rishikimit:
{{ dict "Version" .WerfRootVersion "Channel" "root" "Root" $Root | include "doc_artifact" }}
---
{{- if .WerfReviewCommit }}
{{ dict "Version" "review" "Channel" "review" "Commit" .WerfReviewCommit "Root" $Root | include "doc_artifact" }}
{{- end }} Kujdesi, se artefakti për komitetin e rishikimit do të ndërtohet vetëm në rast se është vendosur variabla .WerfReviewCommit.
Artefaktet janĂ« gati â Ă«shtĂ« koha pĂ«r t'u marrĂ« me importimin!
Imazhi përfundimtar, i destinuar për të funksionuar në Kubernetes, përbën një NGINX të zakonshëm, në të cilin është shtuar skedari i konfigurimit të serverit nginx.conf dhe statika nga artefaktet. Përveç artefaktit të versionit rrënjor të faqes, ne kemi nevojë të përsërisim ciklin mbi variablën .WerfVersions për importimin e artefakteve të versioneve të kanaleve dhe rreleaseve + të respektojmë rregullin e emërtesës së artefakteve që kemi pranuar më parë. Duke qenë se çdo artefakt ruan versionet e faqes për dy gjuhë, i importojmë ato në vendet e paraqitura nga konfigurimi.
Përshkrimi i imazhit përfundimtar werf-doc
image: werf-doc
from: nginx:stable-alpine
ansible:
setup:
- name: "Setup /etc/nginx/nginx.conf"
copy:
content: |
{{ .Files.Get ".werf/nginx.conf" | indent 8 }}
dest: /etc/nginx/nginx.conf
- file:
path: "{{`{{ item }}`}}"
state: directory
mode: 0777
with_items:
- /app/main_site/assets
- /app/ru_site/assets
import:
- artifact: doc-root
add: /app/_main_site
to: /app/main_site
before: setup
- artifact: doc-root
add: /app/_ru_site
to: /app/ru_site
before: setup
{{ range .WerfVersions -}}
{{ $VersionsDict := splitn "%" 2 . -}}
{{ $Channel := $VersionsDict._0 -}}
{{ $Version := $VersionsDict._1 -}}
- artifact: doc-{{ $Channel }}
add: /app/_main_site
to: /app/main_site/v{{ $Channel }}
before: setup
{{ end -}}
{{ range .WerfVersions -}}
{{ $VersionsDict := splitn "%" 2 . -}}
{{ $Channel := $VersionsDict._0 -}}
{{ $Version := $VersionsDict._1 -}}
- artifact: doc-{{ $Channel }}
add: /app/_ru_site
to: /app/ru_site/v{{ $Channel }}
before: setup
{{ end -}}Një imazh shtesë, i cili së bashku me të parin nis në kontur dev, përmban vetëm dy versione të faqes: versionin nga commit-i i shqyrtimit dhe versionin rrënjësor të faqes (aty janë asetet e përbashkëta dhe, nëse e mbani mend, të dhënat për lëshimet). Prandaj, imazhi shtesë do të dallojë nga i pari vetëm për seksionin e importit (dhe, sigurisht, emri):
image: werf-dev
...
import:
- artifact: doc-root
add: /app/_main_site
to: /app/main_site
before: setup
- artifact: doc-root
add: /app/_ru_site
to: /app/ru_site
before: setup
{{- if .WerfReviewCommit }}
- artifact: doc-review
add: /app/_main_site
to: /app/main_site/review
before: setup
- artifact: doc-review
add: /app/_ru_site
to: /app/ru_site/review
before: setup
{{- end }} Siç u vërejt më parë, artefakti për commit-in e shqyrtimit do të gjenerohet vetëm kur variabli i mjedisit të jetë i vendosur. REVIEW_SHA. Mund të mos e gjeneronim fare imazhin werf-dev, nëse nuk ka variabël të mjedisit. REVIEW_SHA, por për të të imazheve Docker në werf do të funksiononte për imazhin werf-dev, do ta lëmë atë të ndërtohet vetëm me artefaktin e versionit rrënjor (pavarësisht se ai është tashmë ndërtuar), për të thjeshtuar strukturën e pipeline-it.
Ndërtimi është përfunduar! Tani kalojmë te CI/CD dhe detajet e rëndësishme.
Pipeline në GitLab CI dhe veçoritë e ndërtimit dinamik.
Kur fillojmë ndërtimin, është e nevojshme të vendosim variablat e mjedisit që përdoren në werf.yaml. Kjo nuk i përket variablit REVIEW_SHA, të cilin do ta vendosim kur thërrasim pipeline-in nga hook-u i GitHub.
Formimin e të dhënave të nevojshme do ta hedhim në një skenë Bash generate_artifacts, i cili do të gjenerojë dy artefakte për pipeline-in GitLab:
- skeda
releases.ymlme të dhënat për lëshimet, - skeda
common_envs.sh, që përmban variablat e mjedisit për eksport.
Përmbajtja e skedarit generate_artifacts do t'i gjeni në . Marrja e të dhënave nuk është subjekti i artikullit, por skedari common_envs.sh na intereson, pasi prej tij varet funksionimi i werf. Një shembull i përmbajtjes së tij:
export RELEASES='1.0%v1.0.6-4'
export CHANNELS='1.0-alpha%v1.0.7-1 1.0-beta%v1.0.7-1 1.0-ea%v1.0.6-4 1.0-stable%v1.0.6-4 1.0-rock-solid%v1.0.6-4'
export ROOT_VERSION='v1.0.6-4' Implementimi i një skenari të tillë mund të bëhet, për shembull, me një funksion në Bash source.
Tani vjen pjesa më interesante. Që ndërtimi dhe implementimi i aplikacionit të funksionojnë siç duhet, është e nevojshme që werf.yaml ishte të njëjtë të paktën brenda një pipeline. Nëse ky kusht nuk përmbushet, atëherë firmat e fazave që werf llogarit gjatë ndërtimit dhe, për shembull, implementimit, do të jenë të ndryshme. Kjo do të çojë në një gabim të implementimit, sepse imazhi i nevojshëm për implementim do të mungojë.
Me fjalë të tjera, nëse gjatë ndërtimit të imazhit të faqes informacioni mbi versionet dhe rishikimet është njësoj, ndërsa në momentin e implementimit lëshohet një version i ri dhe variablat e mjedisit kanë vlera të tjera, atëherë implementimi do të përfundojë me gabim: sepse artefakti i versionit të ri ende nuk është ndërtuar.
Nëse krijimi werf.yaml varet nga të dhëna të jashtme (për shembull, lista e versioneve të duhura, si në rastin tonë), atëherë përmbajtja dhe vlerat e këtyre të dhënave duhet të regjistrohen brenda pipeline. Kjo është veçanërisht e rëndësishme, nëse parametrat e jashtëm ndryshojnë mjaft shpesh.
Ne do të marrim dhe regjistrojmë të dhëna të jashtme në fazën e parë të pipeline në GitLab (Prebuild) dhe do t'i kalojmë ato më tej si artefakte GitLab CI. Kjo do të mundësojë që të ekzekutojmë dhe rishikojmë detyrat e pipeline-it (ndërtim, implementim, pastrim) me konfigurim të njëjtë në werf.yaml.
Përmbajtja e fazës Prebuild skedare .gitlab-ci.yml:
Prebuild:
stage: prebuild
script:
- bash .\/generate_artifacts 1> common_envs.sh
- cat .\/common_envs.sh
artifacts:
paths:
- releases.yml
- common_envs.sh
expire_in: 2 weeksPas regjistrimit të të dhënave të jashtme në artefakt, është e mundur të ekzekutohet ndërtimi dhe implementimi, duke përdorur fazat standarde të pipeline-it GitLab CI: Build dhe Deploy. Ne startojmë pipeline-in përmes hook-eve nga depozitës GitHub të werf (dmth. gjatë ndryshimeve në depozitën në GitHub). Të dhënat për to mund të merren në pronat e projektit në GitLab në seksionin CI / CD Settings -> Pipeline triggers, pastaj do të krijojmë në GitHub Webhook-un përkatës (Settings -> Webhooks).
Faza e ndërtimit do të duket si më poshtë:
Build:
stage: build
script:
- type multiwerf && . $(multiwerf use 1.0 alpha --as-file)
- type werf && source <(werf ci-env gitlab --tagging-strategy tag-or-branch --verbose)
- source common_envs.sh
- werf build-and-publish --stages-storage :local
except:
refs:
- schedules
dependencies:
- Prebuild GitLab do t'i shtojĂ« dy artefakte nĂ« fazĂ«n e ndĂ«rtimit nga faza Prebuild, kĂ«shtu qĂ« ne do tĂ« eksportojmĂ« variablat me tĂ« dhĂ«nat e pĂ«rgatitura pĂ«r hyrje pĂ«rmes strukturĂ«s source common_envs.sh. AktivizojmĂ« fazĂ«n e ndĂ«rtimit nĂ« tĂ« gjitha rastet, pĂ«rveç aktivizimit tĂ« pipeline sipas orarit. Sipas orarit, do tĂ« aktivizohet pipeline pĂ«r pastrimin â nuk Ă«shtĂ« e nevojshme tĂ« kryhet ndĂ«rtimi nĂ« kĂ«tĂ« rast.
NĂ« fazĂ«n e deploy-it do tĂ« pĂ«rshkruajmĂ« dy detyra â veçmas pĂ«r deploy nĂ« prodhim- dhe dev-contours, duke pĂ«rdorur njĂ« shabllon YAML:
.base_deploy: &base_deploy
stage: deploy
script:
- type multiwerf && . $(multiwerf use 1.0 alpha --as-file)
- type werf && source <(werf ci-env gitlab --tagging-strategy tag-or-branch --verbose)
- source common_envs.sh
- werf deploy --stages-storage :local
dependencies:
- Prebuild
except:
refs:
- schedules
Deploy to Production:
<<: *base_deploy
variables:
WERF_KUBE_CONTEXT: prod
environment:
name: production
url: werf.io
only:
refs:
- master
except:
variables:
- $REVIEW_SHA
refs:
- schedules
Deploy to Test:
<<: *base_deploy
variables:
WERF_KUBE_CONTEXT: dev
environment:
name: test
url: werf.test.flant.com
except:
refs:
- schedules
only:
variables:
- $REVIEW_SHA Detyrat në thelb vetëm dallohen nga specifikimi i kontekstit të klasterit në të cilin werf duhet të kryejë deploy (WERF_KUBE_CONTEXT), dhe vendosja e variablave të ambientit (environment.name dhe environment.url), të cilat përdoren pastaj në shabllonat e Helm-chart. Nuk do të paraqesim përmbajtjen e shablloneve, pasi nuk ka asgjë interesante për temën e shqyrtuar, por mund t'i gjeni ato në .
Përfundimi i fundit
Duke pasur parasysh se versionet e werf dalin mjaft shpesh, do tĂ« krijohen shpesh edhe imazhe tĂ« reja, dhe Docker Registry do tĂ« caktohet nĂ« rritje tĂ« vazhdueshme. Prandaj Ă«shtĂ« e domosdoshme tĂ« konfigurohet pastrimi automatik i imazheve sipas politikave. ĂshtĂ« shumĂ« e thjeshtĂ« ta bĂ«sh kĂ«tĂ«.
Për realizimin e kësaj do të nevojitet:
- Shtoni një fazë pastrimi në
.gitlab-ci.yml; - Shtoni një ekzekutim periodik të detyrës për pastrim;
- Konfiguroni një variabël ambienti me token e aksesit për shkrim.
Shtojmë fazën e pastrimit në .gitlab-ci.yml:
Cleanup:
stage: cleanup
script:
- type multiwerf && . $(multiwerf use 1.0 alpha --as-file)
- type werf && source <(werf ci-env gitlab --tagging-strategy tag-or-branch --verbose)
- source common_envs.sh
- docker login -u nobody -p ${WERF_IMAGES_CLEANUP_PASSWORD} ${WERF_IMAGES_REPO}
- werf cleanup --stages-storage :local
only:
refs:
- schedules
Ajo qĂ« kemi parĂ« tashmĂ« mĂ« lart â vetĂ«m pĂ«r pastrim Ă«shtĂ« e nevojshme tĂ« autorizohemi paraprakisht nĂ« Docker Registry me njĂ« token qĂ« ka tĂ« drejta pĂ«r tĂ« fshirĂ« imazhet nĂ« Docker Registry (tokeni i lĂ«shuar automatikisht pĂ«r detyrat GitLab CI nuk ka kĂ«to tĂ« drejta). Tokeni duhet tĂ« ruhet nĂ« GitLab mĂ« parĂ« dhe tĂ« tregoni vlerĂ«n e tij nĂ« variablin e ambientit WERF_IMAGES_CLEANUP_PASSWORD i projektit (CI/CD Settings -> Variables).
Shtimi i një detyre pastrimi me një orar të nevojshëm bëhet në CI/CD ->
Oraret.
Të gjitha: projekti në Docker Registry nuk do të rritet më për shkak të imazheve të papërdorura.
Në përfundim të pjesës praktike, do t'ju rikujtoja se listimet e plota nga artikulli janë të disponueshme në :
- ;
- .
Rezultati
- Kemi marrë një strukturë logjike ndërtimi: një artefakt për një version.
- Ndërtimi është universale dhe nuk kërkon ndryshime manuale kur dalin versionet e reja të werf: dokumentacioni në faqe përditësohet automatikisht.
- Ndërtohen dy imazhe për konturet e ndryshme.
- Funksionon shpejt, pasi maksimalisht përdor caching - kur dalin versionet e reja të werf ose kur thirret GitHub webhook për review-commit - rinndërtohet vetëm artefakti përkatës me versionin e ndryshuar.
- Nuk është nevoja të mendoni për fshirjen e imazheve të papërdorura: pastrimi sipas politikave të werf do të mbajë rregull në Docker Registry.
Përfundimet
- Përdorimi i werf lejon që ndërtimi të funksionojë shpejt falë caching-ut si të ndërtimit ashtu edhe caching-ut gjatë punës me depo të jashtme.
- Puna me depo të jashtme Git e shmang nevojën për të klonuar sërish depozitën çdo herë plotësisht ose për të izmjëkuar me logjikën e optimizimit. werf përdor caching dhe bën klonimin vetëm një herë, pastaj përdor
fetchdhe vetĂ«m sipas nevojĂ«s. - MundĂ«sia e pĂ«rdorimit tĂ« ŃабlonĂ«ve Go nĂ« dosjen e konfigurimit tĂ« ndĂ«rtimit
werf.yamllejon të përshkruhet ndërtimi, rezultati i të cilit varet nga të dhëna të jashtme. - Përdorimi i montimit në werf përshpejton ndërtimin e artefakteve në mënyrë të konsiderueshme - falë cache-it që është i përbashkët për të gjitha pipeline-t.
- werf lejon lehtësisht të konfigurohet pastrimi, që është veçanërisht i rëndësishëm gjatë ndërtimit dinamike.
P.S.
Lexoni gjithashtu në blogun tonë:
- «»;
- «»;
- «»;
- «».
Burimi: habr.com
