CI/CD u Github akcijama za Flask+Angular projekat

CI/CD u Github akcijama za Flask+Angular projekat
U ovom članku ću podijeliti svoje iskustvo postavljanja CI/CD-a koristeći Plesk Control Panel i Github Actions. Danas ćemo naučiti kako implementirati jednostavan projekat s jednostavnim imenom "Helloworld". Napisan je u Flask Python okviru, sa Celery radnicima i Angular 8 frontendom.

Linkovi ka spremištima: backend, frontend.

U prvom dijelu članka osvrnut ćemo se na naš projekt i njegove dijelove. U drugom ćemo shvatiti kako postaviti Plesk i instalirati potrebna proširenja i komponente (DB, RabbitMQ, Redis, Docker, itd.).

U trećem dijelu ćemo konačno shvatiti kako postaviti cevovod za postavljanje našeg projekta na server u dev i prod okruženju. A onda ćemo pokrenuti stranicu na serveru.

I da, zaboravio sam da se predstavim. Moje ime je Oleg Borzov, ja sam fullstack programer u CRM timu za menadžere hipoteka u Domclicku.

Pregled projekta

Prvo, pogledajmo dva projektna spremišta - backend i front - i prođimo preko koda.

Pozadina: Flask+Celery

Za zadnji dio, uzeo sam gomilu koja je prilično popularna među Python programerima: Flask framework (za API) i Celery (za red zadataka). SQLAchemy se koristi kao ORM. Alembic se koristi za migracije. Za JSON validaciju u ručkama - Marshmallow.

В spremišta postoji Readme.md fajl sa detaljnim opisom strukture i uputstvima za pokretanje projekta.

API za web dio prilično nekompliciran, sastoji se od 6 olovaka:

  • /ping - provjeriti dostupnost;
  • ručke za registraciju, autorizaciju, deautorizaciju i dobivanje ovlaštenog korisnika;
  • ručka e-pošte koja stavlja zadatak u red čekanja Celery.

Dio celera još lakše, postoji samo jedan problem send_mail_task.

U mapi /conf postoje dva podfoldera:

  • docker sa dva Docker fajla (base.dockerfile za izgradnju osnovnog imidža koji se rijetko mijenja i Dockerfile za glavne sklopove);
  • .env_files - sa datotekama sa varijablama okruženja za različita okruženja.

Postoje četiri docker-compose datoteke u korijenu projekta:

  • docker-compose.local.db.yml podizanje lokalne baze podataka za razvoj;
  • docker-compose.local.workers.yml za lokalno podizanje radnika, baza podataka, Redis i RabbitMQ;
  • docker-compose.test.yml za pokretanje testova tokom implementacije;
  • docker-compose.yml za raspoređivanje.

I zadnji folder koji nas zanima - .ci-cd. Sadrži shell skripte za implementaciju:

  • deploy.sh — pokretanje migracije i implementacije. Pokreće se na serveru nakon izgradnje i pokretanja testova u Github Actions;
  • rollback.sh - vraćanje kontejnera na prethodnu verziju sklopa;
  • curl_tg.sh - slanje obavještenja o implementaciji Telegramu.

Frontend na Angularu

Repozitorijum sa prednjom stranom mnogo jednostavniji od Beckovog. Prednja strana se sastoji od tri stranice:

  • Glavna stranica sa formom za slanje e-pošte i dugmetom za izlaz.
  • Stranica za prijavu.
  • Stranica za registraciju.

Glavna stranica izgleda asketski:

CI/CD u Github akcijama za Flask+Angular projekat
Postoje dva fajla u korenu Dockerfile и docker-compose.yml, kao i poznati folder .ci-cd sa nešto manje skripti nego u stražnjem spremištu (uklonjene skripte za pokretanje testova).

Pokretanje projekta u Plesku

Počnimo postavljanjem Pleska i kreiranjem pretplate za našu web stranicu.

Instaliranje ekstenzija

U Plesku su nam potrebna četiri proširenja:

  • Docker za upravljanje i vizualni prikaz statusa kontejnera u Plesk admin panelu;
  • Git da konfigurišete korak implementacije na serveru;
  • Let's Encrypt za generiranje (i automatsko obnavljanje) besplatnih TLS certifikata;
  • Firewall da konfigurišete filtriranje dolaznog saobraćaja.

Možete ih instalirati preko Plesk admin panela u odjeljku Ekstenzije:

CI/CD u Github akcijama za Flask+Angular projekat
Nećemo uzeti u obzir detaljne postavke za ekstenzije, zadane postavke će poslužiti za naše demo svrhe.

Kreirajte pretplatu i web lokaciju

Zatim moramo kreirati pretplatu za našu web stranicu helloworld.ru i tamo dodati poddomen dev.helloworld.ru.

  1. Kreirajte pretplatu za domen helloworld.ru i navedite lozinku za prijavu za korisnika sistema:

    CI/CD u Github akcijama za Flask+Angular projekat
    Označite kvadratić na dnu stranice Osigurajte domenu pomoću Let's Encryptako želimo da postavimo HTTPS za sajt:

    CI/CD u Github akcijama za Flask+Angular projekat

  2. Zatim, u ovoj pretplati, kreirajte poddomenu dev.helloworld.ru (za koju također možete izdati besplatni TLS certifikat):

    CI/CD u Github akcijama za Flask+Angular projekat

Instaliranje serverskih komponenti

Imamo server sa OS Debian Stretch 9.12 i instaliran kontrolni panel Plesk Obsidian 18.0.27.

Moramo da instaliramo i konfigurišemo za naš projekat:

  • PostgreSQL (u našem slučaju, postojaće jedan server sa dve baze podataka za dev i prod okruženja).
  • RabbitMQ (ista, ista instanca sa različitim vhostovima za okruženja).
  • Dvije Redis instance (za dev i prod okruženja).
  • Docker Registry (za lokalno skladištenje izgrađenih Docker slika).
  • UI za Docker registar.

PostgreSQL

Plesk već dolazi sa PostgreSQL DBMS, ali ne i najnovijom verzijom (u vrijeme pisanja Plesk Obsidian podržano Postgres verzije 8.4–10.8). Želimo najnoviju verziju za našu aplikaciju (12.3 u vrijeme pisanja ovog teksta), pa ćemo je ručno instalirati.

Postoji mnogo detaljnih uputa za instalaciju Postgresa na Debian na mreži (primer), pa ih neću detaljno opisivati, samo ću dati naredbe:

wget -q https://www.postgresql.org/media/keys/ACCC4CF8.asc -O - | sudo apt-key add -
sudo sh -c 'echo "deb http://apt.postgresql.org/pub/repos/apt/ stretch-pgdg main" >> /etc/apt/sources.list.d/pgdg.list'

sudo apt-get update
sudo apt-get install postgresql postgresql-contrib

S obzirom da PostgreSQL ima prilično osrednje podrazumevane postavke, potrebno je ispraviti konfiguraciju. Ovo će nam pomoći kalkulator: potrebno je da unesete parametre vašeg servera i zamijenite postavke u datoteci /etc/postgresql/12/main/postgresql.confonima koji su ponuđeni. Ovdje treba napomenuti da ovakvi kalkulatori nisu čarobni metak, te da bazu treba preciznije podesiti, na osnovu vašeg hardvera, aplikacije i složenosti upita. Ali ovo je dovoljno za početak.

Pored postavki koje je predložio kalkulator, mijenjamo se i u postgresql.confpodrazumevani port 5432 na drugi (u našem primeru - 53983).

Nakon promjene konfiguracijske datoteke, ponovo pokrenite postgresql-server naredbom:

service postgresql restart

Instalirali smo i konfigurisali PostgreSQL. Sada kreirajmo bazu podataka, korisnike za dev i prod okruženja i dajmo korisnicima prava za upravljanje bazom podataka:

$ su - postgres
postgres:~$ create database hw_dev_db_name;
CREATE DATABASE
postgres:~$ create user hw_dev_db_user with password 'hw_dev_db_password';
CREATE ROLE
postgres:~$ grant ALL privileges ON database hw_dev_db_name to hw_dev_db_user;
GRANT
postgres:~$ create database hw_prod_db_name;
CREATE DATABASE
postgres:~$ create user hw_prod_db_user with password 'hw_prod_db_password';
CREATE ROLE
postgres:~$ grant ALL privileges ON database hw_prod_db_name to hw_prod_db_user;
GRANT

Rabbit MQ

Prijeđimo na instaliranje RabbitMQ-a, posrednika poruka za Celery. Instalacija na Debian je prilično jednostavna:

wget https://packages.erlang-solutions.com/erlang-solutions_1.0_all.deb
sudo dpkg -i erlang-solutions_1.0_all.deb

sudo apt-get update
sudo apt-get install erlang erlang-nox

sudo add-apt-repository 'deb http://www.rabbitmq.com/debian/ testing main'
wget -O- https://www.rabbitmq.com/rabbitmq-release-signing-key.asc | sudo apt-key add -

sudo apt-get update
sudo apt-get install rabbitmq-server

Nakon instalacije, moramo kreirati vhosts, korisnicima i dodijelite potrebna prava:

sudo rabbitmqctl add_user hw_dev_amqp_user hw_dev_amqp_password 
sudo rabbitmqctl set_user_tags hw_dev_amqp_user administrator
sudo rabbitmqctl add_vhost hw_dev_vhost
sudo rabbitmqctl set_permissions -p hw_dev_vhost hw_dev_amqp_user ".*" ".*" ".*"

sudo rabbitmqctl add_user hw_prod_amqp_user hw_prod_amqp_password 
sudo rabbitmqctl set_user_tags hw_prod_amqp_user administrator
sudo rabbitmqctl add_vhost hw_prod_vhost
sudo rabbitmqctl set_permissions -p hw_prod_vhost hw_prod_amqp_user ".*" ".*" ".*"

Redis

Sada instalirajmo i konfiguriramo posljednju komponentu za našu aplikaciju - Redis. Koristit će se kao backend za pohranjivanje rezultata Celery zadataka.

Podići ćemo dva Docker kontejnera sa Redis-om za dev i prod okruženja koristeći ekstenziju Docker za Plesk.

  1. Idemo na Plesk, idemo na odjeljak Extensions, tražimo ekstenziju Docker i instaliramo je (treba nam besplatna verzija):

    CI/CD u Github akcijama za Flask+Angular projekat

  2. Idite na instaliranu ekstenziju, pronađite sliku kroz pretragu redis bitnami i instalirajte najnoviju verziju:

    CI/CD u Github akcijama za Flask+Angular projekat

  3. Ulazimo u preuzeti kontejner i prilagođavamo konfiguraciju: specificiramo port, maksimalnu dodijeljenu veličinu RAM-a, lozinku u varijablama okruženja i montiramo volumen:

    CI/CD u Github akcijama za Flask+Angular projekat

  4. Izvodimo korake 2-3 za prod kontejner, u postavkama mijenjamo samo parametre: port, lozinku, veličinu RAM-a i putanju do foldera volumena na serveru:

    CI/CD u Github akcijama za Flask+Angular projekat

Docker Registry

Pored osnovnih usluga, bilo bi dobro da na server stavite i sopstveno Docker spremište slika. Srećom, prostor na serveru je sada prilično jeftin (sigurno jeftiniji od pretplate na DockerHub), a proces postavljanja privatnog spremišta je vrlo jednostavan.

želimo da imamo:

Da biste to uradili:

  1. Kreirajmo dvije poddomene u Plesku u našoj pretplati: docker.helloworld.ru i docker-ui.helloworld.ru, i konfigurirajmo Let's Encrypt certifikate za njih.
  2. Dodajte datoteku u mapu poddomena docker.helloworld.ru docker-compose.yml sa ovakvim sadržajem:
    version: "3"
    
    services:
      docker-registry:
        image: "registry:2"
        restart: always
        ports:
          - "53985:5000"
        environment:
          REGISTRY_AUTH: htpasswd
          REGISTRY_AUTH_HTPASSWD_REALM: basic-realm
          REGISTRY_AUTH_HTPASSWD_PATH: /auth/.htpasswd
          REGISTRY_STORAGE_FILESYSTEM_ROOTDIRECTORY: /data
        volumes:
          - ./.docker-registry.htpasswd:/auth/.htpasswd
          - ./data:/data
    
      docker-registry-ui:
        image: konradkleine/docker-registry-frontend:v2
        restart: always
        ports:
          - "53986:80"
        environment:
          VIRTUAL_HOST: '*, https://*'
          ENV_DOCKER_REGISTRY_HOST: 'docker-registry'
          ENV_DOCKER_REGISTRY_PORT: 5000
        links:
          - 'docker-registry'
    

  3. Pod SSH-om ćemo generirati .htpasswd datoteku za osnovnu autorizaciju u Docker spremištu:
    htpasswd -bBc .htpasswd hw_docker_admin hw_docker_password
  4. Sakupite i podignite kontejnere:
    docker-compose up -d
  5. I moramo preusmjeriti Nginx na naše kontejnere. Ovo se može uraditi preko Pleska.

Za poddomene docker.helloworld.ru i docker-ui.helloworld.ru potrebno je uraditi sljedeće korake:

odjeljak Dev Tools idite na našu stranicu Docker proxy pravila:

CI/CD u Github akcijama za Flask+Angular projekat
I dodajte pravilo za proxy dolazni promet u naš kontejner:

CI/CD u Github akcijama za Flask+Angular projekat

  1. Provjeravamo da se možemo prijaviti u naš kontejner sa lokalne mašine:
    $ docker login docker.helloworld.ru -u hw_docker_admin -p hw_docker_password
    WARNING! Using --password via the CLI is insecure. Use --password-stdin.
    Login Succeeded
  2. Provjerimo i rad poddomena docker-ui.helloworld.ru:

    CI/CD u Github akcijama za Flask+Angular projekat
    Kada kliknete na Pregledaj spremišta, pretraživač će prikazati prozor za autorizaciju u koji ćete morati da unesete korisničko ime i lozinku za spremište. Nakon toga ćemo biti prebačeni na stranicu sa listom spremišta (za sada će vam ona biti prazna):

    CI/CD u Github akcijama za Flask+Angular projekat

Otvaranje portova u Plesk Firewall-u

Nakon instalacije i konfiguracije komponenti, moramo otvoriti portove kako bi komponente bile dostupne iz Docker kontejnera i vanjske mreže.

Pogledajmo kako to učiniti koristeći proširenje Firewall za Plesk koje smo ranije instalirali.

  1. Idi Alati i postavke > Postavke > Zaštitni zid:
    CI/CD u Github akcijama za Flask+Angular projekat
  2. Idi Izmijenite pravila Plesk Firewall > Dodaj prilagođeno pravilo i otvorite sljedeće TCP portove za Docker podmrežu (172.0.0.0 / 8):
    RabbitMQ: 1883, 4369, 5671-5672, 25672, 61613-61614
    Redis: 32785, 32786

    CI/CD u Github akcijama za Flask+Angular projekat

  3. Također ćemo dodati pravilo koje će otvoriti PostgreSQL portove i RabbitMQ upravljačke ploče prema vanjskom svijetu:

    CI/CD u Github akcijama za Flask+Angular projekat

  4. Primijenite pravila pomoću dugmeta Primijeni promjene:

    CI/CD u Github akcijama za Flask+Angular projekat

Postavljanje CI/CD-a u Github Actions

Prijeđimo na najzanimljiviji dio – postavljanje kontinuiranog integracionog cjevovoda i isporuku našeg projekta na server.

Ovaj cevovod će se sastojati od dva dela:

  • pravljenje slike i pokretanje testova (za pozadinu) - na Github strani;
  • pokretanje migracija (za pozadinu) i postavljanje kontejnera - na serveru.

Postavite u Plesk

Hajde da se prvo pozabavimo drugom tačkom (jer prva zavisi od toga).

Mi ćemo konfigurirati proces implementacije koristeći Git ekstenziju za Plesk.

Razmotrite primjer sa Prod okruženjem za Backend spremište.

  1. Idemo na pretplatu naše Helloworld web stranice i idemo u pododjeljak Git:

    CI/CD u Github akcijama za Flask+Angular projekat

  2. Umetnite vezu do našeg Github spremišta u polje "Remote Git repository" i promijenite zadanu mapu httpdocs drugome (npr. /httpdocs/hw_back):

    CI/CD u Github akcijama za Flask+Angular projekat

  3. Kopirajte SSH javni ključ iz prethodnog koraka i dodati nalazi se u Github postavkama.
  4. Kliknite OK na ekranu u koraku 2, nakon čega ćemo biti preusmjereni na stranicu spremišta u Plesku. Sada treba da konfigurišemo spremište da se ažurira prilikom urezivanja na glavnu granu. Da biste to učinili, idite na Postavke spremišta i sačuvajte vrijednost Webhook URL (trebat će nam kasnije prilikom postavljanja Github Actions):

    CI/CD u Github akcijama za Flask+Angular projekat

  5. U polje Akcije na ekranu iz prethodnog paragrafa unesite skriptu za pokretanje implementacije:
    cd {REPOSITORY_ABSOLUTE_PATH}
    .ci-cd/deploy.sh {ENV} {DOCKER_REGISTRY_HOST} {DOCKER_USER} {DOCKER_PASSWORD} {TG_BOT_TOKEN} {TG_CHAT_ID} 

    gde:

    {REPOSITORY_ABSOLUTE_PATH} - put do prod foldera pozadinskog spremišta na serveru;
    {ENV} - okruženje (dev/prod), u našem slučaju prod;
    {DOCKER_REGISTRY_HOST} - domaćin našeg docker repozitorija
    {TG_BOT_TOKEN} — Telegram bot token;
    {TG_CHAT_ID} — ID ćaskanja/kanala za slanje obavještenja.

    Primjer skripte:

    cd /var/www/vhosts/helloworld.ru/httpdocs/hw_back/
    .ci-cd/deploy.sh dev docker.helloworld.ru docker_user docker_password 12345678:AAbcdEfghCH1vGbCasdfSAs0K5PALDsaw -1001234567890
  6. Dodajte korisnika iz naše pretplate u Docker grupu (kako bi mogli upravljati kontejnerima):
    sudo usermod -aG docker helloworld_admin

Razvojno okruženje za backend spremište i frontend su postavljeni na isti način.

Cjevovod za implementaciju u Github Actions

Pređimo na postavljanje prvog dijela našeg CI/CD cevovoda u Github Actions.

backend

Cjevovod je opisan u deploy.yml fajl.

Ali prije nego što ga analiziramo, popunimo Secret varijable koje su nam potrebne u Githubu. Da biste to učinili, idite na Postavke -> Tajne:

  • DOCKER_REGISTRY - domaćin našeg Docker repozitorija (docker.helloworld.ru);
  • DOCKER_LOGIN - prijavite se na Docker spremište;
  • DOCKER_PASSWORD - lozinku za njega;
  • DEPLOY_HOST — host na kojem je dostupna Plesk admin panel (primjer: helloworld.com: 8443 ili 123.4.56.78:8443);
  • DEPLOY_BACK_PROD_TOKEN - token za implementaciju u prod-repozitorijum na serveru (dobili smo ga u Deployment in Plesk str. 4);
  • DEPLOY_BACK_DEV_TOKEN - token za postavljanje u dev spremište na serveru.

Proces postavljanja je jednostavan i sastoji se od tri glavna koraka:

  • izrada i objavljivanje slike u našem spremištu;
  • izvođenje testova u kontejneru na osnovu svježe napravljene slike;
  • implementacija u željeno okruženje ovisno o grani (dev/master).

frontend

Deploy.yml fajl za prednje spremište malo drugačiji od Beckovog. Nedostaje korak s pokretanjem testova i promjenama imena tokena za implementaciju. Tajne za prednji repozitorij, inače, treba popuniti zasebno.

Postavljanje stranice

Proxy promet putem Nginxa

Pa, došli smo do kraja. Ostaje samo konfigurirati proxying dolaznog i odlaznog prometa u naš kontejner preko Nginxa. Već smo pokrili ovaj proces u koraku 5 podešavanja Docker Registry-a. Isto bi trebalo ponoviti za stražnje i prednje dijelove u dev i prod okruženjima.

Dat ću snimke ekrana postavki.

backend

CI/CD u Github akcijama za Flask+Angular projekat

frontend

CI/CD u Github akcijama za Flask+Angular projekat
Važnoe utočnenie. Svi URL-ovi će biti poslani u frontend kontejner, osim onih koji počinju sa /api/ - oni će biti poslani u zadnji kontejner (tako u zadnjem kontejneru, svi rukovaoci moraju početi sa /api/).

Ishodi

Sada bi naša stranica trebala biti dostupna na helloworld.ru i dev.helloworld.ru (prod- i dev-environments, respektivno).

Ukupno smo naučili kako pripremiti jednostavnu aplikaciju u Flask-u i Angular-u i postaviti cjevovod u Github Actions-u da bismo je postavili na server koji pokreće Plesk.

Duplicirat ću veze do spremišta sa kodom: backend, frontend.

izvor: www.habr.com

Dodajte komentar