Sistemski pristup varijablama u Ansibleu

ansible devops codestyle

Hej! Moje ime je Denis Kalyuzhny Radim kao inženjer u odjelu za automatizaciju razvojnih procesa. Svaki dan, nove verzije aplikacija se uvode na stotine servera kampanje. I u ovom članku dijelim svoje iskustvo korištenja Ansiblea u ove svrhe.

Ovaj vodič nudi način organiziranja varijabli u implementaciji. Ovaj vodič je dizajniran za one koji već koriste uloge u svojim igrama i čitaju Najbolje prakseali nailazi na slične probleme:

  • Nakon što smo pronašli varijablu u kodu, nemoguće je odmah shvatiti za šta je odgovorna;
  • Postoji nekoliko uloga, a varijable moraju biti povezane s jednom vrijednošću, ali to ne funkcionira;
  • Imate poteškoća da objasnite drugima kako funkcioniše logika varijabli u vašim priručnicima

Sa ovim problemima smo se susreli na projektima u našoj kompaniji, usled čega smo došli do pravila za formatiranje varijabli u našim playbookovima, što je donekle i rešilo ove probleme.

Sistemski pristup varijablama u Ansibleu

Varijable u ulogama

Uloga je zaseban sistemski objekt implementacije. Kao i svaki objekat sistema, on mora imati interfejs za interakciju sa ostatkom sistema. Varijable uloga su takav interfejs.

Uzmimo, na primjer, ulogu api, koji instalira Java aplikaciju na server. Koje varijable ima?

Sistemski pristup varijablama u Ansibleu

Varijable uloga mogu se podijeliti u 2 tipa prema vrsti:

1. Свойства
    a) независимые от среды
    б) зависимые от среды
2. Связи
    a) слушатели 
    б) запросы внутри системы
    в) запросы в среду

Promjenjiva svojstva su varijable koje definiraju ponašanje uloge.

Query Variables su varijable čija se vrijednost koristi za označavanje resursa izvan uloge.

Varijabilni slušaoci su varijable čija se vrijednost koristi za formiranje varijabli upita.

S druge strane, 1a, 2a, 2b su varijable koje ne ovise o okruženju (gvožđe, eksterni resursi, itd.) i mogu se popuniti zadanim vrijednostima u zadanoj ulozi. Međutim, varijable poput 1.b i 2.c ne mogu se ispuniti drugim vrijednostima osim 'primjera', jer će se mijenjati od stajališta do stajališta ovisno o okruženju.

stil koda

  • Ime varijable mora početi s imenom uloge. Ovo će olakšati da se u budućnosti shvati iz koje je uloge varijabla i za šta je odgovorna.
  • Kada koristite varijable u ulogama, morate biti sigurni da slijedite princip enkapsulacije i koristite varijable definirane ili u samoj ulozi ili u ulogama od kojih trenutna ovisi.
  • Izbjegavajte korištenje rječnika za varijable. Ansible vam ne dozvoljava da jednostavno zaobiđete pojedinačne vrijednosti u rječniku.

    Primjer loše varijable:

    myrole_user:
        login: admin
        password: admin

    Ovdje je login srednja varijabla, a lozinka je zavisna varijabla. Ali
    pošto su kombinovani u rečnik, moraćete da ga u potpunosti navedete
    Uvijek. Što je veoma nezgodno. Bolje ovako:

    myrole_user_login: admin
    myrole_user_password: admin

Varijable u priručnicima za implementaciju

Prilikom sastavljanja priručnika za implementaciju (u daljem tekstu playbook), pridržavamo se pravila da ga treba staviti u posebno spremište. Baš kao i uloge: svaka u svom git repozitorijumu. Ovo vam omogućava da shvatite da su uloge i playbook različiti nezavisni objekti sistema za implementaciju, a promjene u jednom objektu ne bi trebale utjecati na rad drugog. To se postiže promjenom zadanih vrijednosti varijabli.

Prilikom sastavljanja playbook-a, da rezimiramo, moguće je zaobići zadane vrijednosti varijabli uloga na dva mjesta: u varijablama playbook-a i u varijablama inventara.

mydeploy                        # Каталог деплоя
├── deploy.yml                  # Плейбук деплоя
├── group_vars                  # Каталог переменных плейбука
│   ├── all.yml                 # Файл для переменных связи всей системы
│   └── myapi.yml               # Файл переменных свойств группы myapi
└── inventories                 #
    └── prod                    # Каталог окружения prod
        ├── prod.ini            # Инвентори файл
        └── group_vars          # Каталог для переменных инвентори
            └── myapi           #
                ├── vars.yml    # Средозависимые переменные группы myapi
                └── vault.yml   # Секреты (всегда средозависимы) *

* - Varijable i trezori

Razlika je u tome što se varijable playbook-a uvijek koriste kada se pozivaju playbook-ovi koji se nalaze na istom nivou s njima. To znači da su ove varijable odlične za promjenu zadanih vrijednosti varijabli koje ne ovise o okruženju. Suprotno tome, varijable inventara će se koristiti samo za određeno okruženje, što je idealno za varijable specifične za okruženje.

Važno je napomenuti da vam prioritet varijabli neće dozvoliti da redefinirate varijable prvo u varijablama priručnika, a zatim zasebno u istom inventaru.

To znači da već u ovoj fazi morate odlučiti da li varijabla ovisi o okruženju ili ne i postaviti je na pravo mjesto.

Na primjer, u jednom projektu, varijabla odgovorna za omogućavanje SSL-a je dugo vremena ovisila o okruženju, jer na jednom od štandova nismo mogli omogućiti SSL iz razloga van naše kontrole. Nakon što smo popravili ovaj problem, postao je srednje nezavisan i prešao na varijable playbook-a.

Varijable svojstava za grupe

Proširimo naš model na slici 1 dodavanjem 2 grupe servera sa različitom Java aplikacijom, ali sa različitim postavkama.

Sistemski pristup varijablama u Ansibleu

Zamislite kako će playbook izgledati u ovom slučaju:

- hosts: myapi
  roles:
    - api

- hosts: bbauth
  roles:
    - auth

- hosts: ghauth
  roles:
    - auth

Imamo tri grupe u playbook-u, pa je preporučljivo kreirati što više grupnih datoteka u group_vars inventaru varijabli i playbook varijabli odjednom. Jedna grupna datoteka u ovom slučaju je opis jedne komponente vaše aplikacije u playbook-u. Kada otvorite datoteku grupe u varijablama playbook-a, odmah vidite sve razlike u odnosu na zadano ponašanje uloga koje su dodijeljene grupi. U varijablama inventara: razlike u ponašanju grupe od štanda do štanda.

stil koda

  • Pokušajte da uopšte ne koristite host_vars varijable, jer one ne opisuju sistem, već samo poseban slučaj, što će dugoročno dovesti do pitanja: "Zašto se ovaj host razlikuje od ostalih?", na koji je odgovor nije uvek lako pronaći.

Link varijable

Međutim, radi se o varijablama svojstava, ali šta je sa varijablama veze?
Njihova razlika je u tome što moraju imati istu vrijednost u različitim grupama.

Na početku je bilo ideja koristite monstruoznu konstrukciju oblika:
hostvars[groups['bbauth'][0]]['auth_bind_port'], ali je odmah napušteno
jer ima nedostataka. Prvo, glomaznost. Drugo, ovisnost o određenom domaćinu u grupi. Treće, potrebno je prikupiti činjenice sa svih hostova prije početka implementacije, ako ne želimo da dobijemo grešku nedefinirane varijable.

Kao rezultat toga, odlučeno je da se koriste varijable veze.

Link varijable su varijable koje pripadaju playbook-u i potrebne su za povezivanje sistemskih objekata.

Varijable veze se popunjavaju u općim sistemskim varijablama group_vars/all/vars i formiraju se uklanjanjem svih varijabli slušatelja iz svake grupe i dodavanjem imena grupe iz koje je slušatelj uklonjen na početak varijable.

Time je osigurana uniformnost i neukrštanje naziva.

Pokušajmo povezati varijable iz gornjeg primjera:

Sistemski pristup varijablama u Ansibleu

Zamislite da imamo varijable koje zavise jedna od druge:

# roles/api/defaults:
# Переменная запроса
api_auth1_address: "http://example.com:80"
api_auth2_address: "http://example2.com:80"

# roles/auth/defaults:
# Переменная слушатель
auth_bind_port: "20000"

Stavimo to u zajedničke varijable group_vars/all/vars svim slušaocima i imenu dodajte ime grupe:

# group_vars/all/vars
bbauth_auth_bind_port: "20000"
ghauth_auth_bind_port: "30000"

# group_vars/bbauth/vars
auth_bind_port: "{{ bbauth_auth_bind_port }}"

# group_vars/ghauth/vars
auth_bind_port: "{{ ghauth_auth_bind_port }}"

# group_vars/myapi/vars
api_auth1_address: "http://{{ bbauth_auth_service_name }}:{{ bbauth_auth_bind_port }}"
api_auth2_address: "http://{{ ghauth_auth_service_name }}:{{ ghauth_auth_bind_port }}"

Sada, promjenom vrijednosti konektora, bit ćemo sigurni da će zahtjev ići na isti port.

stil koda

  • Pošto su uloge i grupe različiti sistemski objekti, moraju imati različita imena kako bi varijable veze tačno pokazale da pripadaju određenoj grupi servera, a ne ulozi u sistemu.

Fajlovi okruženja

Uloge mogu koristiti datoteke koje se razlikuju od okruženja do okruženja.

SSL certifikati su primjer takvih datoteka. Sačuvajte ih kao tekst
u varijabli nije baš zgodno. Ali zgodno je pohraniti putanju do njih unutar varijable.

Na primjer, koristimo varijablu api_ssl_key_file: "/path/to/file".

Budući da je očigledno da će se certifikat ključa mijenjati iz okruženja u okruženje, ovo je varijabla zavisna od okruženja, što znači da bi se trebala nalaziti u datoteci
group_vars/myapi/vars inventar varijabli, i sadrže vrijednost 'na primjer'.

Najprikladniji način u ovom slučaju je da stavite ključnu datoteku u playbook spremište duž putanje
files/prod/certs/myapi.key, tada će vrijednost varijable biti:
api_ssl_key_file: "prod/certs/myapi.key". Pogodnost leži u činjenici da ljudi odgovorni za postavljanje sistema na određenom štandu takođe imaju svoje namensko mesto u spremištu za skladištenje svojih fajlova. Istovremeno, ostaje moguće odrediti apsolutnu putanju do certifikata na serveru, u slučaju da se certifikati isporučuju od drugog sistema.

Više štandova u jednom okruženju

Često postoji potreba za postavljanjem nekoliko gotovo identičnih štandova u istom okruženju sa minimalnim razlikama. U ovom slučaju dijelimo varijable zavisne od okoline na one koje se ne mijenjaju unutar ovog okruženja i one koje se mijenjaju. A potonje vadimo direktno u same dosijee inventara. Nakon ove manipulacije, postaje moguće kreirati još jedan inventar direktno u direktoriju okruženja.

Ponovo će koristiti inventar group_vars i također će moći redefinirati neke varijable direktno za sebe.

Konačna struktura direktorija za projekat implementacije:

mydeploy                        # Каталог деплоя
├── deploy.yml                  # Плейбук деплоя
├── files                       # Каталог для файлов деплоя
│   ├── prod                    # Католог для средозависимых файлов стенда prod
│   │   └── certs               # 
│   │       └── myapi.key       #
│   └── test1                   # Каталог для средозависимых файлов стенда test1
├── group_vars                  # Каталог переменных плейбука
│   ├── all.yml                 # Файл для переменных связи всей системы
│   ├── myapi.yml               # Файл переменных свойств группы myapi
│   ├── bbauth.yml              # 
│   └── ghauth.yml              #
└── inventories                 #
    ├── prod                    # Каталог окружения prod
    │   ├── group_vars          # Каталог для переменных инвентори
    │   │   ├── myapi           #
    │   │   │   ├── vars.yml    # Средозависимые переменные группы myapi
    │   │   │   └── vault.yml   # Секреты (всегда средозависимы)
    │   │   ├── bbauth          # 
    │   │   │   ├── vars.yml    #
    │   │   │   └── vault.yml   #
    │   │   └── ghauth          #
    │   │       ├── vars.yml    #
    │   │       └── vault.yml   #
    │   └── prod.ini            # Инвентори стенда prod
    └── test                    # Каталог окружения test
        ├── group_vars          #
        │   ├── myapi           #
        │   │   ├── vars.yml    #
        │   │   └── vault.yml   #
        │   ├── bbauth          #
        │   │   ├── vars.yml    #
        │   │   └── vault.yml   #
        │   └── ghauth          #
        │       ├── vars.yml    #
        │       └── vault.yml   #
        ├── test1.ini           # Инвентори стенда test1 в среде test
        └── test2.ini           # Инвентори стенда test2 в среде test

Sažimanje

Nakon organizovanja varijabli u skladu sa člankom: svaki fajl sa varijablama je odgovoran za određeni zadatak. A pošto datoteka ima određene zadatke, postalo je moguće dodijeliti osobu odgovornu za ispravnost svakog fajla. Na primjer, programer implementacije sistema postaje odgovoran za ispravno popunjavanje varijabli playbook-a, dok je administrator, čiji je stav opisan u inventaru, direktno odgovoran za popunjavanje inventara varijabli.

Uloge su postale samostalna razvojna jedinica sa sopstvenim interfejsom, omogućavajući programeru uloge da razvije karakteristike, a ne da prilagođava ulogu da odgovara sistemu. Ovo pitanje je posebno važilo za zajedničke uloge za sve sisteme u kampanji.

Sistemski administratori više ne moraju razumjeti kod za implementaciju. Sve što se od njih traži za uspješnu implementaciju je da popune datoteke varijabli okruženja.

Literatura

  1. Dokumentacija

autor

Kaljužni Denis Aleksandrovič

izvor: www.habr.com

Dodajte komentar