Configurarea unui cluster Nomad folosind Consul și integrarea cu Gitlab

Introducere

Recent, popularitatea Kubernetes a crescut rapid - tot mai multe proiecte îl implementează. Am vrut să ating un orchestrator precum Nomad: este perfect pentru proiecte care folosesc deja alte soluții de la HashiCorp, de exemplu, Vault și Consul, iar proiectele în sine nu sunt complexe din punct de vedere al infrastructurii. Acest material va conține instrucțiuni pentru instalarea Nomad, combinând două noduri într-un cluster, precum și integrarea Nomad cu Gitlab.

Configurarea unui cluster Nomad folosind Consul și integrarea cu Gitlab

stand de testare

Câteva despre bancul de testare: sunt folosite trei servere virtuale cu caracteristicile a 2 CPU, 4 RAM, SSD de 50 Gb, unite într-o rețea locală comună. Numele și adresele IP ale acestora:

  1. nomad-livelinux-01: 172.30.0.5
  2. nomad-livelinux-02: 172.30.0.10
  3. consul-livelinux-01: 172.30.0.15

Instalarea Nomad, Consul. Crearea unui cluster Nomad

Să începem cu instalarea de bază. Deși configurarea a fost simplă, o voi descrie de dragul integrității articolului: a fost creat în esență din schițe și note pentru acces rapid atunci când este necesar.

Înainte de a începe practica, vom discuta partea teoretică, deoarece în această etapă este important să înțelegem structura viitoare.

Avem două noduri nomade și vrem să le combinăm într-un cluster, iar pe viitor vom avea nevoie și de scalarea automată a clusterului - pentru asta vom avea nevoie de Consul. Cu acest instrument, gruparea și adăugarea de noi noduri devine o sarcină foarte simplă: nodul Nomad creat se conectează la agentul Consul și apoi se conectează la clusterul Nomad existent. Prin urmare, la început vom instala serverul Consul, vom configura autorizarea http de bază pentru panoul web (este fără autorizație implicit și poate fi accesat la o adresă externă), precum și agenții Consul înșiși pe serverele Nomad, după care vom merge doar la Nomad.

Instalarea instrumentelor HashiCorp este foarte simplă: în esență, mutăm fișierul binar în directorul bin, setăm fișierul de configurare al instrumentului și creăm fișierul de serviciu al acestuia.

Descărcați fișierul binar Consul și despachetați-l în directorul principal al utilizatorului:

root@consul-livelinux-01:~# wget https://releases.hashicorp.com/consul/1.5.0/consul_1.5.0_linux_amd64.zip
root@consul-livelinux-01:~# unzip consul_1.5.0_linux_amd64.zip
root@consul-livelinux-01:~# mv consul /usr/local/bin/

Acum avem un binar consul gata făcut pentru configurare ulterioară.

Pentru a lucra cu Consul, trebuie să creăm o cheie unică folosind comanda keygen:

root@consul-livelinux-01:~# consul keygen

Să trecem la setarea configurației Consul, creând un director /etc/consul.d/ cu următoarea structură:

/etc/consul.d/
├── bootstrap
│   └── config.json

Directorul bootstrap va conține un fișier de configurare config.json - în el vom seta setările Consul. Conținutul său:

{
"bootstrap": true,
"server": true,
"datacenter": "dc1",
"data_dir": "/var/consul",
"encrypt": "your-key",
"log_level": "INFO",
"enable_syslog": true,
"start_join": ["172.30.0.15"]
}

Să ne uităm separat la principalele directive și la semnificațiile lor:

  • bootstrap: Adevărat. Permitem adăugarea automată de noi noduri dacă acestea sunt conectate. Observ că nu indicăm aici numărul exact de noduri așteptate.
  • serverul: Adevărat. Activați modul server. Consul pe această mașină virtuală va acționa ca singurul server și master în acest moment, VM-ul lui Nomad va fi clienții.
  • centru de date: dc1. Specificați numele centrului de date pentru a crea clusterul. Trebuie să fie identic atât pe clienți, cât și pe servere.
  • criptați: cheia ta. Cheia, care trebuie să fie, de asemenea, unică și să se potrivească pe toți clienții și serverele. Generat folosind comanda consul keygen.
  • start_join. În această listă indicăm o listă de adrese IP la care se va face conexiunea. Momentan lasam doar adresa noastra.

În acest moment, putem rula consul folosind linia de comandă:

root@consul-livelinux-01:~# /usr/local/bin/consul agent -config-dir /etc/consul.d/bootstrap -ui

Aceasta este o modalitate bună de a depana acum, cu toate acestea, nu veți putea folosi această metodă în mod continuu din motive evidente. Să creăm un fișier de serviciu pentru a gestiona Consul prin systemd:

root@consul-livelinux-01:~# nano /etc/systemd/system/consul.service

Conținutul dosarului consul.service:

[Unit]
Description=Consul Startup process
After=network.target
 
[Service]
Type=simple
ExecStart=/bin/bash -c '/usr/local/bin/consul agent -config-dir /etc/consul.d/bootstrap -ui' 
TimeoutStartSec=0
 
[Install]
WantedBy=default.target

Lansați Consul prin systemctl:

root@consul-livelinux-01:~# systemctl start consul

Să verificăm: serviciul nostru trebuie să ruleze, iar executând comanda membrilor consul ar trebui să vedem serverul nostru:

root@consul-livelinux:/etc/consul.d# consul members
consul-livelinux    172.30.0.15:8301  alive   server  1.5.0  2         dc1  <all>

Etapa următoare: instalarea Nginx și configurarea proxy și autorizarea http. Instalăm nginx prin managerul de pachete și în directorul /etc/nginx/sites-enabled creăm un fișier de configurare consul.conf cu următorul conținut:

upstream consul-auth {
    server localhost:8500;
}

server {

    server_name consul.doman.name;
    
    location / {
      proxy_pass http://consul-auth;
      proxy_set_header Host $host;
      auth_basic_user_file /etc/nginx/.htpasswd;
      auth_basic "Password-protected Area";
    }
}

Nu uitați să creați un fișier .htpasswd și să generați un nume de utilizator și o parolă pentru acesta. Acest articol este necesar pentru ca panoul web să nu fie disponibil tuturor celor care cunosc domeniul nostru. Cu toate acestea, la configurarea Gitlab, va trebui să renunțăm la aceasta - altfel nu vom putea implementa aplicația noastră în Nomad. În proiectul meu, atât Gitlab, cât și Nomad sunt doar pe web gri, așa că nu există o astfel de problemă aici.

Pe celelalte două servere instalăm agenți Consul conform următoarelor instrucțiuni. Repetăm ​​pașii cu fișierul binar:

root@nomad-livelinux-01:~# wget https://releases.hashicorp.com/consul/1.5.0/consul_1.5.0_linux_amd64.zip
root@nomad-livelinux-01:~# unzip consul_1.5.0_linux_amd64.zip
root@nomad-livelinux-01:~# mv consul /usr/local/bin/

Prin analogie cu serverul anterior, creăm un director pentru fișierele de configurare /etc/consul.d cu următoarea structură:

/etc/consul.d/
├── client
│   └── config.json

Conținutul fișierului config.json:

{
    "datacenter": "dc1",
    "data_dir": "/opt/consul",
    "log_level": "DEBUG",
    "node_name": "nomad-livelinux-01",
    "server": false,
    "encrypt": "your-private-key",
    "domain": "livelinux",
    "addresses": {
      "dns": "127.0.0.1",
      "https": "0.0.0.0",
      "grpc": "127.0.0.1",
      "http": "127.0.0.1"
    },
    "bind_addr": "172.30.0.5", # локальный адрес вм
    "start_join": ["172.30.0.15"], # удаленный адрес консул сервера
    "ports": {
      "dns": 53
     }

Salvați modificările și treceți la configurarea fișierului de serviciu, conținutul acestuia:

/etc/systemd/system/consul.service:

[Unit]
Description="HashiCorp Consul - A service mesh solution"
Documentation=https://www.consul.io/
Requires=network-online.target
After=network-online.target

[Service]
User=root
Group=root
ExecStart=/usr/local/bin/consul agent -config-dir=/etc/consul.d/client
ExecReload=/usr/local/bin/consul reload
KillMode=process
Restart=on-failure

[Install]
WantedBy=multi-user.target

Lansăm consul pe server. Acum, după lansare, ar trebui să vedem serviciul configurat în membrii nsul. Aceasta va însemna că sa conectat cu succes la cluster ca client. Repetați același lucru pe al doilea server și după aceea putem începe instalarea și configurarea Nomad.

Instalarea mai detaliată a Nomad este descrisă în documentația sa oficială. Există două metode tradiționale de instalare: descărcarea unui fișier binar și compilarea din sursă. Voi alege prima metodă.

Nota: Proiectul se dezvoltă foarte repede, noi actualizări sunt adesea lansate. Poate că o nouă versiune va fi lansată până la finalizarea acestui articol. Prin urmare, înainte de a citi, vă recomand să verificați versiunea curentă a Nomad în acest moment și să o descărcați.

root@nomad-livelinux-01:~# wget https://releases.hashicorp.com/nomad/0.9.1/nomad_0.9.1_linux_amd64.zip
root@nomad-livelinux-01:~# unzip nomad_0.9.1_linux_amd64.zip
root@nomad-livelinux-01:~# mv nomad /usr/local/bin/
root@nomad-livelinux-01:~# nomad -autocomplete-install
root@nomad-livelinux-01:~# complete -C /usr/local/bin/nomad nomad
root@nomad-livelinux-01:~# mkdir /etc/nomad.d

După despachetare, vom primi un fișier binar Nomad cu o greutate de 65 MB - acesta trebuie mutat în /usr/local/bin.

Să creăm un director de date pentru Nomad și să îi edităm fișierul de serviciu (cel mai probabil nu va exista la început):

root@nomad-livelinux-01:~# mkdir --parents /opt/nomad
root@nomad-livelinux-01:~# nano /etc/systemd/system/nomad.service

Lipiți acolo următoarele rânduri:

[Unit]
Description=Nomad
Documentation=https://nomadproject.io/docs/
Wants=network-online.target
After=network-online.target

[Service]
ExecReload=/bin/kill -HUP $MAINPID
ExecStart=/usr/local/bin/nomad agent -config /etc/nomad.d
KillMode=process
KillSignal=SIGINT
LimitNOFILE=infinity
LimitNPROC=infinity
Restart=on-failure
RestartSec=2
StartLimitBurst=3
StartLimitIntervalSec=10
TasksMax=infinity

[Install]
WantedBy=multi-user.target

Cu toate acestea, nu ne grăbim să lansăm nomad - încă nu am creat fișierul său de configurare:

root@nomad-livelinux-01:~# mkdir --parents /etc/nomad.d
root@nomad-livelinux-01:~# chmod 700 /etc/nomad.d
root@nomad-livelinux-01:~# nano /etc/nomad.d/nomad.hcl
root@nomad-livelinux-01:~# nano /etc/nomad.d/server.hcl

Structura finală a directorului va fi următoarea:

/etc/nomad.d/
├── nomad.hcl
└── server.hcl

Fișierul nomad.hcl ar trebui să conțină următoarea configurație:

datacenter = "dc1"
data_dir = "/opt/nomad"

Conținutul fișierului server.hcl:

server {
  enabled = true
  bootstrap_expect = 1
}

consul {
  address             = "127.0.0.1:8500"
  server_service_name = "nomad"
  client_service_name = "nomad-client"
  auto_advertise      = true
  server_auto_join    = true
  client_auto_join    = true
}

bind_addr = "127.0.0.1" 

advertise {
  http = "172.30.0.5"
}

client {
  enabled = true
}

Nu uitați să schimbați fișierul de configurare pe al doilea server - acolo va trebui să schimbați valoarea directivei http.

Ultimul lucru în această etapă este să configurați Nginx pentru proxy și configurarea autorizației http. Conținutul fișierului nomad.conf:

upstream nomad-auth {
        server 172.30.0.5:4646;
}

server {

        server_name nomad.domain.name;
        
        location / {
	        proxy_pass http://nomad-auth;
	        proxy_set_header Host $host;
	        auth_basic_user_file /etc/nginx/.htpasswd;
		   auth_basic "Password-protected Area";
        }
        
}

Acum putem accesa panoul web printr-o rețea externă. Conectați-vă și accesați pagina de servere:

Configurarea unui cluster Nomad folosind Consul și integrarea cu Gitlab
Imaginea 1. Lista serverelor din clusterul Nomad

Ambele servere sunt afișate cu succes în panou, vom vedea același lucru în rezultatul comenzii nomad node status:

Configurarea unui cluster Nomad folosind Consul și integrarea cu Gitlab
Imaginea 2. Ieșirea comenzii de stare a nodului nomad

Dar consul? Să aruncăm o privire. Accesați panoul de control Consul, pagina de noduri:
Configurarea unui cluster Nomad folosind Consul și integrarea cu Gitlab
Imaginea 3. Lista nodurilor din clusterul Consul

Acum avem un Nomad pregătit care lucrează împreună cu Consul. În etapa finală, vom ajunge la partea distractivă: configurarea livrării containerelor Docker de la Gitlab către Nomad și, de asemenea, vorbim despre unele dintre celelalte caracteristici distinctive ale acestuia.

Se creează Gitlab Runner

Pentru a implementa imagini docker la Nomad, vom folosi un ruler separat cu fișierul binar Nomad înăuntru (aici, apropo, putem observa o altă caracteristică a aplicațiilor Hashicorp - individual, acestea sunt un singur fișier binar). Încărcați-l în directorul runner. Să creăm un Dockerfile simplu pentru acesta, cu următorul conținut:


FROM alpine:3.9
RUN apk add --update --no-cache libc6-compat gettext
COPY nomad /usr/local/bin/nomad

În același proiect creăm .gitlab-ci.yml:

variables:
  DOCKER_IMAGE: nomad/nomad-deploy
  DOCKER_REGISTRY: registry.domain.name
 

stages:
  - build

build:
  stage: build
  image: ${DOCKER_REGISTRY}/nomad/alpine:3
  script:
    - tag=${DOCKER_REGISTRY}/${DOCKER_IMAGE}:latest
    - docker build --pull -t ${tag} -f Dockerfile .
    - docker push ${tag}

Ca urmare, vom avea o imagine disponibilă a alergătorului Nomad în Registrul Gitlab, acum putem merge direct la depozitul de proiect, putem crea o conductă și configura jobul nomad al lui Nomad.

Configurarea proiectului

Să începem cu dosarul jobului pentru Nomad. Proiectul meu din acest articol va fi destul de primitiv: va consta dintr-o singură sarcină. Conținutul .gitlab-ci va fi după cum urmează:

variables:
  NOMAD_ADDR: http://nomad.address.service:4646
  DOCKER_REGISTRY: registry.domain.name
  DOCKER_IMAGE: example/project

stages:
  - build
  - deploy

build:
  stage: build
  image: ${DOCKER_REGISTRY}/nomad-runner/alpine:3
  script:
    - tag=${DOCKER_REGISTRY}/${DOCKER_IMAGE}:${CI_COMMIT_SHORT_SHA}
    - docker build --pull -t ${tag} -f Dockerfile .
    - docker push ${tag}


deploy:
  stage: deploy
  image: registry.example.com/nomad/nomad-runner:latest
  script:
    - envsubst '${CI_COMMIT_SHORT_SHA}' < project.nomad > job.nomad
    - cat job.nomad
    - nomad validate job.nomad
    - nomad plan job.nomad || if [ $? -eq 255 ]; then exit 255; else echo "success"; fi
    - nomad run job.nomad
  environment:
    name: production
  allow_failure: false
  when: manual

Aici implementarea are loc manual, dar o puteți configura pentru a modifica conținutul directorului de proiect. Conducta constă din două etape: asamblarea imaginii și implementarea acesteia către nomazi. În prima etapă, asamblam o imagine docker și o introducem în Registrul nostru, iar în a doua ne lansăm jobul în Nomad.

job "monitoring-status" {
    datacenters = ["dc1"]
    migrate {
        max_parallel = 3
        health_check = "checks"
        min_healthy_time = "15s"
        healthy_deadline = "5m"
    }

    group "zhadan.ltd" {
        count = 1
        update {
            max_parallel      = 1
            min_healthy_time  = "30s"
            healthy_deadline  = "5m"
            progress_deadline = "10m"
            auto_revert       = true
        }
        task "service-monitoring" {
            driver = "docker"

            config {
                image = "registry.domain.name/example/project:${CI_COMMIT_SHORT_SHA}"
                force_pull = true
                auth {
                    username = "gitlab_user"
                    password = "gitlab_password"
                }
                port_map {
                    http = 8000
                }
            }
            resources {
                network {
                    port "http" {}
                }
            }
        }
    }
}

Vă rugăm să rețineți că am un registru privat și pentru a extrage cu succes o imagine docker trebuie să mă conectez la el. Cea mai bună soluție în acest caz este să introduceți un login și o parolă în Vault și apoi să le integrați cu Nomad. Nomad acceptă în mod nativ Vault. Dar mai întâi, în Vault în sine, vom instala politicile necesare pentru Nomad, le puteți descărca:

# Download the policy and token role
$ curl https://nomadproject.io/data/vault/nomad-server-policy.hcl -O -s -L
$ curl https://nomadproject.io/data/vault/nomad-cluster-role.json -O -s -L

# Write the policy to Vault
$ vault policy write nomad-server nomad-server-policy.hcl

# Create the token role with Vault
$ vault write /auth/token/roles/nomad-cluster @nomad-cluster-role.json

Acum, după ce am creat politicile necesare, vom adăuga integrarea cu Vault în blocul de activități din fișierul job.nomad:

vault {
  enabled = true
  address = "https://vault.domain.name:8200"
  token = "token"
}

Folosesc autorizarea prin token și o înregistrez direct aici, există și opțiunea de a specifica jetonul ca variabilă la pornirea agentului nomad:

$ VAULT_TOKEN=<token> nomad agent -config /path/to/config

Acum putem folosi cheile cu Vault. Principiul de funcționare este simplu: creăm un fișier în jobul Nomad care va stoca valorile variabilelor, de exemplu:

template {
                data = <<EOH
{{with secret "secrets/pipeline-keys"}}
REGISTRY_LOGIN="{{ .Data.REGISTRY_LOGIN }}"
REGISTRY_PASSWORD="{{ .Data.REGISTRY_LOGIN }}{{ end }}"

EOH
    destination = "secrets/service-name.env"
    env = true
}

Cu această abordare simplă, puteți configura livrarea containerelor către clusterul Nomad și puteți lucra cu acesta în viitor. Voi spune că într-o oarecare măsură simpatizez cu Nomad - este mai potrivit pentru proiecte mici în care Kubernetes poate provoca o complexitate suplimentară și nu își va realiza întregul potențial. În plus, Nomad este perfect pentru începători — este ușor de instalat și configurat. Cu toate acestea, atunci când testez unele proiecte, întâmpin o problemă cu versiunile sale timpurii - multe funcții de bază pur și simplu nu sunt acolo sau nu funcționează corect. Totuși, cred că Nomad va continua să se dezvolte și în viitor va dobândi funcțiile de care toată lumea are nevoie.

Autor: Ilya Andreev, editat de Alexey Zhadan și echipa Live Linux


Sursa: www.habr.com

Adauga un comentariu