CI/CD во Github Actions за проект Flask+Angular

CI/CD во Github Actions за проект Flask+Angular
Во оваа статија, ќе го споделам моето искуство за поставување CI/CD со користење на контролниот панел Plesk и Github Actions. Денес ќе научиме како да распоредиме едноставен проект со некомплицирано име „Helloworld“. Напишано е во рамката на Flask Python, со работници на Celery и Angular 8 преден дел.

Врски до складишта: задниот дел, предниот крај.

Во првиот дел од статијата ќе го разгледаме нашиот проект и неговите делови. Во втората, ќе сфатиме како да го поставиме Plesk и да ги инсталираме потребните екстензии и компоненти (DB, RabbitMQ, Redis, Docker, итн.).

Во третиот дел, конечно ќе откриеме како да поставиме цевковод за распоредување на нашиот проект на сервер во околина на dev и prod. И тогаш ќе ја стартуваме страницата на серверот.

И да, заборавив да се претставам. Моето име е Олег Борзов, јас сум fullstack програмер во тимот на CRM за менаџери со хипотеки во Domclick.

Преглед на проектот

Прво, ајде да погледнеме во две складишта на проекти - задни и предни - и да го разгледаме кодот.

Заден крај: колба + целер

За задниот дел, зедов куп што е доста популарен меѓу развивачите на Python: рамката Flask (за API) и Celery (за редот за задачи). SQLAchemy се користи како ORM. Alembic се користи за миграции. За валидација на JSON во рачки - Marshmallow.

В складишта има датотека Readme.md со детален опис на структурата и инструкции за водење на проектот.

Web Part API доста некомплицирано, се состои од 6 пенкала:

  • /ping - да се провери достапноста;
  • се справува со регистрација, овластување, деовластување и добивање овластен корисник;
  • рачка за е-пошта што става задача во редот за целер.

Дел од целер уште полесно, има само еден проблем send_mail_task.

Во папката /конф има две подпапки:

  • docker со две Docker-датотеки (base.dockerfile да се изгради основна слика која ретко се менува и Dockerfile за главни склопови);
  • .env_files - со датотеки со променливи на животната средина за различни средини.

Постојат четири датотеки со докер-компонирање во коренот на проектот:

  • docker-compose.local.db.yml да се подигне локална база на податоци за развој;
  • docker-compose.local.workers.yml за локално подигање на работникот, база на податоци, Redis и RabbitMQ;
  • docker-compose.test.yml да се извршат тестови за време на распоредувањето;
  • docker-compose.yml за распоредување.

И последната папка за која сме заинтересирани - .ci-cd. Содржи скрипти на школка за распоредување:

  • deploy.sh — започнување на миграцијата и распоредувањето. Работи на серверот по градење и извршување тестови во Github Actions;
  • rollback.sh - враќање на контејнерите на претходната верзија на склопот;
  • curl_tg.sh - испраќање известувања за распоредување на Telegram.

Frontend во Angular

Складиште со предна страна многу поедноставно од онаа на Бек. Предниот дел се состои од три страници:

  • Главна страница со формулар за испраќање е-пошта и копче за излез.
  • Страница за најавување.
  • Страница за регистрација.

Главната страница изгледа аскетски:

CI/CD во Github Actions за проект Flask+Angular
Во коренот има две датотеки Dockerfile и docker-compose.yml, како и познатата папка .ci-cd со малку помалку скрипти отколку во задното складиште (отстранети скрипти за извршување тестови).

Започнување на проект во Плеск

Да почнеме со поставување на Plesk и создавање претплата за нашата страница.

Инсталирање на екстензии

Во Plesk ни требаат четири екстензии:

  • Docker за управување и визуелно прикажување на статусот на контејнерите во административниот панел на Plesk;
  • Git да го конфигурирате чекорот за распоредување на серверот;
  • Let's Encrypt за генерирање (и автоматско обновување) бесплатни TLS сертификати;
  • Firewall да го конфигурирате филтрирањето на дојдовниот сообраќај.

Можете да ги инсталирате преку административниот панел на Plesk во делот Екстензии:

CI/CD во Github Actions за проект Flask+Angular
Ние нема да ги разгледаме деталните поставки за екстензии, стандардните поставки ќе служат за нашите демо цели.

Креирање на претплата и веб-страница

Следно, треба да создадеме претплата за нашата веб-страница helloworld.ru и да го додадеме поддоменот dev.helloworld.ru таму.

  1. Направете претплата за доменот helloworld.ru и наведете ја лозинката за најава за корисникот на системот:

    CI/CD во Github Actions за проект Flask+Angular
    Проверете го полето на дното на страницата Обезбедете го доменот со Let's Encryptако сакаме да поставиме HTTPS за страницата:

    CI/CD во Github Actions за проект Flask+Angular

  2. Следно, во оваа претплата, креирајте поддомен dev.helloworld.ru (за кој исто така можете да издадете бесплатен TLS сертификат):

    CI/CD во Github Actions за проект Flask+Angular

Инсталирање на серверски компоненти

Имаме сервер со ОС Debian Stretch 9.12 и инсталиран контролен панел Плеск обсидијан 18.0.27.

Треба да инсталираме и конфигурираме за нашиот проект:

  • PostgreSQL (во нашиот случај, ќе има еден сервер со две бази на податоци за dev и prod околини).
  • RabbitMQ (ист, ист пример со различни vhost за околини).
  • Два примери на Redis (за dev и prod околини).
  • Docker Registry (за локално складирање на вградени Docker слики).
  • UI за Docker регистарот.

PostgreSQL

Plesk веќе доаѓа со PostgreSQL DBMS, но не и најновата верзија (во моментот на пишување Plesk Obsidian поддржан Постгрес верзии 8.4–10.8). Ја сакаме најновата верзија за нашата апликација (12.3 во моментот на пишување), па ќе ја инсталираме рачно.

Има многу детални упатства за инсталирање Postgres на Debian на мрежата (пример), затоа нема да ги опишам детално, само ќе ги дадам командите:

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

Имајќи предвид дека PostgreSQL има прилично просечни стандардни поставки, неопходно е да се поправи конфигурацијата. Ова ќе ни помогне калкулатор: треба да ги внесете параметрите на вашиот сервер и да ги замените поставките во датотеката /etc/postgresql/12/main/postgresql.confна понудените. Овде треба да се забележи дека таквите калкулатори не се волшебна точка, а основата треба да се намести попрецизно, врз основа на вашиот хардвер, апликација и сложеност на барањето. Но, ова е доволно за да започнете.

Покрај поставките предложени од калкулаторот, ние исто така се менуваме postgresql.confстандардната порта 5432 на друга (во нашиот пример - 53983).

Откако ќе ја смените конфигурациската датотека, рестартирајте го postgresql-серверот со командата:

service postgresql restart

Инсталиравме и конфигуриравме PostgreSQL. Сега ајде да создадеме база на податоци, корисници за средини за развој и прод, и да им дадеме на корисниците права да управуваат со базата на податоци:

$ 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

Зајакот MQ

Ајде да продолжиме со инсталирање на RabbitMQ, брокер за пораки за Celery. Инсталирањето на Debian е прилично едноставно:

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

По инсталацијата, треба да креираме vhosts, корисници и да ги доделат потребните права:

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

Сега да ја инсталираме и конфигурираме последната компонента за нашата апликација - Redis. Ќе се користи како заднина за складирање на резултатите од задачите на Целер.

Ќе подигнеме два Docker контејнери со Redis за средини за развој и производство со користење на наставката Docker за Плеск.

  1. Одиме во Plesk, одиме во делот Extensions, ја бараме екстензијата Docker и ја инсталираме (ни треба бесплатна верзија):

    CI/CD во Github Actions за проект Flask+Angular

  2. Одете до инсталираната екстензија, пронајдете ја сликата преку пребарувањето redis bitnami и инсталирај ја најновата верзија:

    CI/CD во Github Actions за проект Flask+Angular

  3. Влегуваме во преземениот контејнер и ја прилагодуваме конфигурацијата: наведете ја портата, максималната доделена големина на RAM меморијата, лозинката во променливите на околината и монтирајте ја јачината на звукот:

    CI/CD во Github Actions за проект Flask+Angular

  4. Ги извршуваме чекорите 2-3 за контејнерот за производи, во поставките ги менуваме само параметрите: порта, лозинка, големина на RAM и патека до папката за јачина на звук на серверот:

    CI/CD во Github Actions за проект Flask+Angular

Докер регистар

Покрај основните услуги, би било убаво да поставите сопствено складиште за слики на Docker на серверот. За среќа, просторот на серверот сега е прилично евтин (секако поевтин од претплатата на DockerHub), а процесот на поставување приватно складиште е многу едноставен.

Сакаме да имаме:

Да го направите ова:

  1. Ајде да создадеме два поддомени во Plesk во нашата претплата: docker.helloworld.ru и docker-ui.helloworld.ru и да ги конфигурираме Let's Encrypt сертификатите за нив.
  2. Додајте ја датотеката во папката на поддоменот docker.helloworld.ru docker-compose.yml со ваква содржина:
    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. Под SSH, ќе генерираме датотека .htpasswd за основна овластување во складиштето Docker:
    htpasswd -bBc .htpasswd hw_docker_admin hw_docker_password
  4. Соберете и подигнете контејнери:
    docker-compose up -d
  5. И ние треба да го пренасочиме Nginx кон нашите контејнери. Ова може да се направи преку Plesk.

Следниве чекори треба да се направат за поддомените docker.helloworld.ru и docker-ui.helloworld.ru:

Во делот Dev Алатки нашата страница одете на Правила за докер прокси:

CI/CD во Github Actions за проект Flask+Angular
И додадете правило за дојдовниот сообраќај на прокси во нашиот контејнер:

CI/CD во Github Actions за проект Flask+Angular

  1. Проверуваме дали можеме да се најавиме во нашиот контејнер од локалната машина:
    $ 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. Ајде да ја провериме и работата на поддоменот docker-ui.helloworld.ru:

    CI/CD во Github Actions за проект Flask+Angular
    Кога ќе кликнете на Browse repositories, прелистувачот ќе прикаже прозорец за авторизација каде што ќе треба да ги внесете корисничкото име и лозинката за складиштето. После тоа, ќе бидеме префрлени на страница со список на складишта (засега ќе биде празна за вас):

    CI/CD во Github Actions за проект Flask+Angular

Отворање порти во заштитниот ѕид на Plesk

Откако ќе ги инсталираме и конфигурираме компонентите, треба да ги отвориме портите така што компонентите се достапни од контејнерите на Docker и надворешната мрежа.

Ајде да видиме како да го направиме ова користејќи ја наставката за заштитен ѕид за Plesk што ја инсталиравме порано.

  1. Оди до Алатки и поставки > Поставки > Заштитен ѕид:
    CI/CD во Github Actions за проект Flask+Angular
  2. Оди до Изменете ги правилата за заштитниот ѕид на Plesk > Додајте приспособено правило и отворете ги следните TCP порти за подмрежата Docker (172.0.0.0 / 8):
    RabbitMQ: 1883, 4369, 5671-5672, 25672, 61613-61614
    Редис: 32785, 32786

    CI/CD во Github Actions за проект Flask+Angular

  3. Исто така, ќе додадеме правило кое ќе ги отвори портите PostgreSQL и панелите за управување со RabbitMQ кон надворешниот свет:

    CI/CD во Github Actions за проект Flask+Angular

  4. Применете ги правилата користејќи го копчето Примени промени:

    CI/CD во Github Actions за проект Flask+Angular

Поставување CI/CD во Github Actions

Ајде да се спуштиме на најинтересниот дел - поставување на цевковод за континуирана интеграција и доставување на нашиот проект до серверот.

Овој гасовод ќе се состои од два дела:

  • градење слика и извршување на тестови (за задниот дел) - на страната Github;
  • лансирање миграции (за задниот дел) и распоредување контејнери на серверот.

Распоредете во Плеск

Ајде прво да се справиме со втората точка (затоа што првата зависи од тоа).

Ќе го конфигурираме процесот на распоредување користејќи ја наставката Git за Plesk.

Размислете за пример со Prod околина за складиште за Backend.

  1. Одиме на претплатата на нашата веб-страница Helloworld и одиме во потсекцијата Git:

    CI/CD во Github Actions за проект Flask+Angular

  2. Вметнете врска до нашето складиште Github во полето „Remote Git repository“ и променете ја стандардната папка httpdocs на друг (на пр. /httpdocs/hw_back):

    CI/CD во Github Actions за проект Flask+Angular

  3. Копирајте го јавниот клуч SSH од претходниот чекор и додадете е во поставките за Github.
  4. Кликнете OK на екранот во чекор 2, по што ќе бидеме пренасочени на страницата за складиште во Plesk. Сега треба да го конфигурираме складиштето да се ажурира за обврзувања на главната гранка. За да го направите ова, одете на Поставки на складиштето и зачувајте ја вредноста Webhook URL (ова ќе ни треба подоцна при поставување на Github Actions):

    CI/CD во Github Actions за проект Flask+Angular

  5. Во полето Дејства на екранот од претходниот пасус, внесете ја скриптата за стартување на распоредувањето:
    cd {REPOSITORY_ABSOLUTE_PATH}
    .ci-cd/deploy.sh {ENV} {DOCKER_REGISTRY_HOST} {DOCKER_USER} {DOCKER_PASSWORD} {TG_BOT_TOKEN} {TG_CHAT_ID} 

    каде што:

    {REPOSITORY_ABSOLUTE_PATH} - патека до папката prod на складиштето на заднината на серверот;
    {ENV} - околина (dev / prod), во нашиот случај prod;
    {DOCKER_REGISTRY_HOST} - домаќин на нашето складиште за докер
    {TG_BOT_TOKEN} — Телеграмски бот токен;
    {TG_CHAT_ID} — ID на разговор/канал за испраќање известувања.

    Пример за скрипта:

    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. Додајте корисник од нашата претплата во групата Docker (за да може да управува со контејнерите):
    sudo usermod -aG docker helloworld_admin

Околината на dev за складиштето на заднината и предниот дел се поставени на ист начин.

Распоредување на гасоводот во Github Actions

Ајде да продолжиме со поставувањето на првиот дел од нашиот гасовод за CI/CD во Github Actions.

Заднинската

Гасоводот е опишан во deploy.yml датотека.

Но, пред да го анализираме, ајде да ги пополниме Тајните променливи што ни се потребни во Github. За да го направите ова, одете на Поставки -> Тајни:

  • DOCKER_REGISTRY - домаќин на нашето складиште Docker (docker.helloworld.ru);
  • DOCKER_LOGIN - најавете се во складиштето Docker;
  • DOCKER_PASSWORD - лозинка за неа;
  • DEPLOY_HOST — домаќин каде што е достапен административниот панел на Plesk (пример: helloworld.com: 8443 или 123.4.56.78:8443);
  • DEPLOY_BACK_PROD_TOKEN - токен за распоредување во складиштето за производство на серверот (го добивме во Deployment во Plesk стр. 4);
  • DEPLOY_BACK_DEV_TOKEN - токен за распоредување во складиштето на dev на серверот.

Процесот на распоредување е едноставен и се состои од три главни чекори:

  • градење и објавување на сликата во нашето складиште;
  • извршување на тестови во контејнер врз основа на свежо изградена слика;
  • распоредување во саканата средина во зависност од гранката (dev/master).

интерфејс

Датотеката deploy.yml за предното складиште не се разликува многу од онаа на Беков. Недостасува чекор со извршување на тестови и ги менува имињата на токените за распоредување. Тајните за предното складиште, патем, треба да се пополнат посебно.

Поставување на страницата

Прокси сообраќај преку Nginx

Па, дојдовме до крајот. Останува само да го конфигурираме проксирањето на дојдовниот и појдовниот сообраќај до нашиот контејнер преку Nginx. Веќе го опфативме овој процес во чекор 5 од поставувањето на Docker Registry. Истото треба да се повтори за задните и предните делови во средини за развој и прод.

Ќе дадам слики од екранот на поставките.

Заднинската

CI/CD во Github Actions за проект Flask+Angular

интерфејс

CI/CD во Github Actions за проект Flask+Angular
важно уточнување. Сите URL-адреси ќе бидат проксирани до контејнерот на предниот дел, освен оние што почнуваат со /api/ - тие ќе бидат поврзани со задниот контејнер (така во задниот контејнер, сите ракувачи мора да започнат со /api/).

Резултатите од

Сега нашата страница треба да биде достапна на helloworld.ru и dev.helloworld.ru (прод- и де-средини, соодветно).

Севкупно, научивме како да подготвиме едноставна апликација во Flask и Angular и да поставиме цевковод во Github Actions за да ја пренесеме на сервер кој работи на Plesk.

Ќе ги дуплицирам врските до складиштата со кодот: задниот дел, предниот крај.

Извор: www.habr.com

Додадете коментар