Ansible. Role 13 установка и настройка NGINX

Thank you for reading this post, don't forget to subscribe!

Группы хостов

Созда­дим тесто­вую груп­пу хостов, на кото­рой будем тести­ро­вать уда­лен­ную уста­нов­ку приложения.

Откры­ва­ем файл хостов ansible:

vi /etc/ansible/hosts

Добав­ля­ем груп­пу хостов или редак­ти­ру­ем ее:

[redhat-servers]
192.168.0.11

[debian-servers]
192.168.0.12

* в дан­ном при­ме­ре мы созда­ем 2 груп­пы хостов — redhat-servers для сер­ве­ров семей­ства Red Hat и debian-servers — для deb-сер­ве­ров. В каж­дую груп­пу вхо­дят по одно­му сер­ве­ру — 192.168.0.11 и 192.168.0.12.

Про­ве­рить доступ­ность хостов для ansible мож­но командой:

ansible -m ping all -u ansible -k

* дан­ной коман­дой мы про­пин­гу­ем все хосты из инвен­та­ри­за­ци­он­но­го фай­ла hosts.

Создание плейбука

Созда­ем файл для playbook:

vi /etc/ansible/play.yml

 

 

* где:

  • --- — нача­ло фай­ла YAML. Дан­ный фор­мат име­ет стро­гую струк­ту­ру  — важен каж­дый пробел; 
  • hosts — груп­па хостов, к кото­рым будут при­ме­нять­ся пра­ви­ла плей­бу­ка (если мы хотим, что­бы пра­ви­ла при­ме­ня­лись ко всем хостам, ука­зы­ва­ем hosts: all); 
  • become — ука­зы­ва­ет на необ­хо­ди­мость эска­ла­ции привилегий; 
  • become_method — метод эска­ла­ции привилегий; 
  • become_user — поль­зо­ва­тель под кото­рым мы захо­дим с помо­щью become_method
  • remote_user — поль­зо­ва­тель, под кото­рым будем под­клю­чать­ся к уда­лен­ным серверам; 
  • roles — спи­сок ролей, кото­рые будут при­ме­нять­ся для плейбука.

* В дан­ном слу­чае мы задей­ству­ем нашу груп­пы хостов, кото­рые созда­ли в самом нача­ле; повы­ша­ем при­ви­ле­гии мето­дом su под поль­зо­ва­те­лем root (su - root) для груп­пы redhat-servers и мето­дом sudo для debian-servers; под­клю­че­ние к сер­ве­рам выпол­ня­ет­ся от поль­зо­ва­те­ля ansible; исполь­зу­ем создан­ную нами роль nginx (саму роль мы созда­дим поз­же). Для систем RPM сна­ча­ла выпол­ним роль epel — она будет отве­чать за уста­нов­ку репо­зи­то­рия EPEL, так как в стан­дарт­ном репо­зи­то­рии nginx нет.

Сто­ит отдель­но уде­лить вни­ма­ние вопро­су повы­ше­ния при­ви­ле­гий. IT-сре­ды могут при­ме­нять раз­ные поли­ти­ки отно­си­тель­но без­опас­но­сти. Напри­мер, на сер­ве­рах CentOS, по умол­ча­нию, нет sudo и повы­шать при­ви­ле­гии нуж­но с помо­щью su. В Ubuntu наобо­рот — по умол­ча­нию есть sudo, а su не рабо­та­ет, так как пароль на root не уста­нав­ли­ва­ет­ся. В дан­ном слу­чае есть несколь­ко путей при рабо­те с Ansible:

  1. Как в нашем при­ме­ре, раз­де­лить груп­пы хостов на раз­ные семей­ства опе­ра­ци­он­ных систем и при­ме­нять к ним раз­ные мето­ды повы­ше­ния при­ви­ле­гий. Что­бы дан­ный плей­бук кор­рект­но отра­бо­тал, учет­ная запись, под кото­рой идет уда­лен­ное под­клю­че­ние к сер­ве­ру (в нашем при­ме­ре ansible) долж­на иметь такой же пароль, как у поль­зо­ва­те­лей root на сер­ве­рах семей­ства Red Hat. Дан­ный метод удо­бен с точ­ки зре­ния отсут­ствия необ­хо­ди­мо­сти при­во­дить к еди­но­му виду без­опас­ность сер­ве­ров раз­но­го семей­ства. Одна­ко, с точ­ки зре­ния без­опас­но­сти луч­ше, что­бы паро­ли у root и ansible были разные.
  2. Исполь­зо­вать метод для созда­ния плей­бу­ка, как опи­сан выше, но запус­кать его с клю­чом --limit, напри­мер, ansible-playbook --limit=debian-servers … — таким обра­зом, мы запу­стим отдель­ные зада­ния для каж­до­го семей­ства опе­ра­ци­он­ных систем и смо­жем вве­сти инди­ви­ду­аль­ные паро­ли для каж­до­го случая.
  3. Мы можем на всех сер­ве­рах deb уста­но­вить пароль для поль­зо­ва­те­ля root, таким обра­зом, полу­чив воз­мож­ность для become_method: su.
  4. И нако­нец, мож­но для сер­ве­ров Red Hat уста­но­вить sudo и про­хо­дить become с помо­щью мето­да sudo.

Создание роли

Роли в Ansible исполь­зу­ют­ся для логи­че­ско­го раз­де­ле­ния плей­бу­ка. Они име­ют стро­гий син­так­сис и фай­ло­вую струк­ту­ру. Таким обра­зом, кон­фи­гу­ра­ция ста­но­вит­ся более упо­ря­до­чен­ной и понят­ной для даль­ней­шей поддержки.

И так, для ролей долж­на быть чет­кая фай­ло­вая струк­ту­ра — созда­ем каталоги:

mkdir -p /etc/ansible/roles/nginx/tasks

mkdir -p /etc/ansible/roles/epel/tasks

* в дан­ном слу­чае мы созда­ли ката­ло­ги nginxepel и tasks внут­ри ката­ло­га roles. В ansible это озна­ча­ет, что мы созда­ли роли с назва­ни­ем nginx и epel, а файл main.yml, кото­рый мы поме­стим в ката­ло­ги tasks будет опи­сы­вать зада­чи дан­ных ролей.

Созда­ем файл с опи­са­ни­ем задач для роли nginx:

vi /etc/ansible/roles/nginx/tasks/main.yml

 

 

* где 

  • --- — нача­ло фай­ла YAML
  • name — назва­ние для роли (может быть любым);
  • yum/apt — исполь­зу­е­мый модуль для уста­нов­ки приложения; 
  • yum/apt name — назва­ние паке­та, кото­рое мы устанавливаем; 
  • yum/apt state — состо­я­ние паке­та, кото­рое долж­но кон­тро­ли­ро­вать­ся ролью;
  • when — усло­вие, при кото­ром дан­ная роль будет выполняться;
  • notify — обра­бот­чик, кото­рый будет вызван в слу­чае успеш­но­го выпол­не­ния зада­чи. При необ­хо­ди­мо­сти, мож­но задать несколь­ко обработчиков;

* В дан­ном при­ме­ре мы созда­ли про­стую зада­чу для роли по раз­вер­ты­ва­нию nginx. На систе­мы RPM уста­нов­ка выпол­ня­ет­ся с помо­щью моду­ля yum, на deb — apt. Вер­сия долж­на быть послед­ней (latest); после уста­нов­ки паке­та, необ­хо­ди­мо раз­ре­шить авто­за­пуск сер­ви­са и запу­стить его.
* при уста­нов­ке паке­тов так­же сле­ду­ет учи­ты­вать, что неко­то­рые могут иметь раз­ные назва­ния в раз­ных систе­мах. Напри­мер, Apache в RMP-систе­мах назы­ва­ет­ся httpd, в deb — apache2.

Созда­ем файл с опи­са­ни­ем задач для роли epel:

vi /etc/ansible/roles/epel/tasks/main.yml

 

 

Обра­ти­те вни­ма­ние, что в плей­бу­ке выше мы задей­ство­ва­ли notify, но не зада­ли handlers — в каче­стве при­ме­ра, мы выне­сем его в отдель­ный файл:

mkdir /etc/ansible/roles/nginx/handlers

vi /etc/ansible/roles/nginx/handlers/main.yml

 

 

handlers — опи­са­ние обра­бот­чи­ка, кото­рый может быть вызван с помо­щью notify; systemd — модуль для управ­ле­ния юни­та­ми systemd; systemd enabled — раз­ре­ша­ет или запре­ща­ет сер­вис; systemd state — состо­я­ние, кото­рое долж­но быть у сер­ви­са. В дан­ном при­ме­ре мы ука­зы­ва­ем, что у демо­на nginx долж­но быть состо­я­ние started и раз­ре­шен авто­за­пуск (enabled).

Запуск плейбука

Запус­ка­ем наш плейбук:

ansible-playbook /etc/ansible/play.yml -kK

После вво­да дан­ной коман­ды систе­ма запро­сит пер­вый пароль для учет­ной запи­си, от кото­рой мы под­клю­ча­ем­ся к уда­лен­ным сер­ве­рам (в нашем при­ме­ре мы зада­ли ее в самом плей­бу­ке, опции remote_user):

SSH password:

После вво­да паро­ля, будет запро­шен вто­рой пароль — для повы­ше­ния при­ви­ле­гий на самой уда­лен­ной системе:

BECOME password[defaults to SSH password]:

… в ито­ге мы долж­ны уви­деть сле­ду­ю­щую картину:

192.168.0.11    : ok=2    changed=1    unreachable=0    failed=0    skipped=1    rescued=0    ignored=0
192.168.0.12    : ok=2    changed=1    unreachable=0    failed=0    skipped=1    rescued=0    ignored=0

Настройка NGINX с помощью шаблона ansible

После уста­нов­ки веб-сер­ве­ра nginx необ­хо­ди­мо его настро­ить. Про­цесс настрой­ки мы раз­де­лим на созда­ние пере­мен­ных и шаб­ло­нов кон­фи­гу­ра­ци­он­ных фай­лов, а так­же настрой­ки роли для фор­ми­ро­ва­ния кон­фи­гу­ра­ци­он­ных фай­лов на осно­ве шаблона.

Создаем общие переменные

Пере­мен­ные зада­ют­ся в фай­ле main.yml, кото­рый нахо­дит­ся в ката­ло­ге vars, кото­рый, в свою оче­редь, нахо­дит­ся в ката­ло­ге роли. И так, созда­ем ката­лог для переменных:

mkdir /etc/ansible/roles/nginx/vars

… и сам файл main.yml:

vi /etc/ansible/roles/nginx/vars/main.yml

 

 

* где пред­став­ле­ны неко­то­рые опции настрой­ки NGINX:

  • worker_processes — опре­де­ля­ет коли­че­ство рабо­чих про­цес­сов. Чаще все­го, опти­маль­нее выстав­лять авто­ма­ти­че­ское конфигурирование.
  • worker_connections — мак­си­маль­ное коли­че­ство соеди­не­ний одно­го рабо­че­го процесса.
  • client_max_body_size — мак­си­маль­ный раз­мер загру­жа­е­мых данных.

Шаблон для nginx.conf

Созда­ем ката­лог для хра­не­ния шаблонов:

mkdir /etc/ansible/roles/nginx/templates

… и созда­ем пер­вый шаб­лон для кон­фи­гу­ра­ци­он­но­го фай­ла nginx.conf:

vi /etc/ansible/roles/nginx/templates/nginx.conf

 

 

* это при­мер рабо­че­го кон­фи­гу­ра­ци­он­но­го фай­ла. Пере­мен­ных мог­ло быть и боль­ше, но для демон­стра­ции их исполь­зо­ва­ния, вполне, доста­точ­но. Сами пере­мен­ные заклю­че­ны в двой­ные фигур­ные скоб­ки и были нами опре­де­ле­ны в фай­ле выше (кро­ме пере­мен­ной nginx_user, кото­рая будет опре­де­ле­на в настрой­ках плей­бу­ка, так как для каж­до­го типа опе­ра­ци­он­ной систе­мы она долж­на быть своя).

Теперь настра­и­ва­ем нашу роль для исполь­зо­ва­ния шаблона:

vi /etc/ansible/roles/nginx/tasks/main.yml

 

 

* дан­ная роль опре­де­ля­ет, каким фай­лом на сер­ве­ре ansible (src) необ­хо­ди­мо заме­нить файл на уда­лен­ной систе­ме (dest).

И послед­нее, откры­ва­ем файл плейбука:

vi /etc/ansible/play.yml

 

 

* в дан­ном при­ме­ре мы созда­ем пере­мен­ную nginx_user. Так как для раз­ных семейств опе­ра­ци­он­ных систем исполь­зу­ют­ся раз­ные поль­зо­ва­те­ля для nginx по умол­ча­нию, мы так­же сде­ла­ли пере­мен­ную с раз­ны­ми зна­че­ни­я­ми для RPM и deb.

Гото­во — запус­ка­ем плейбук:

ansible-playbook /etc/ansible/play.yml -kK

… и вво­дим два­жды паро­ли. На наших сер­ве­рах дол­жен появить­ся кон­фи­гу­ра­ци­он­ной файл nginx.conf в соот­вет­ствии с нашим шаблоном.

Шаблон для создания виртуальных доменов в NGINX

Созда­дим вир­ту­аль­ные доме­ны при помо­щи ansible. Сна­ча­ла созда­дим пере­мен­ные — для каж­до­го сер­ве­ра долж­ны быть свои доме­ны — такие пере­мен­ные мож­но задать в фай­ле hosts, кото­ром мы созда­ва­ли хосты для ansible:

vi /etc/ansible/hosts

 

 

* мы созда­ли пере­мен­ную virtual_domain, у кото­рой будут свои зна­че­ния для каж­до­го хоста.

Созда­ем шаблон:

vi /etc/ansible/roles/nginx/templates/nginx_vhosts.conf

 

 

* в дан­ном при­ме­ре мы созда­ем про­стой кон­фи­гу­ра­ци­он­ный файл для созда­ния вир­ту­аль­но­го доме­на. В каче­стве само­го доме­на берет­ся зна­че­ние пере­мен­ной virtual_domain, кото­рую мы зада­ли через файл hosts. Пере­мен­ная fastcgi_pass_path будет созда­на для каж­дой груп­пы систем своя и опре­де­ля­ем путь до сокет­но­го фай­ла для вза­и­мо­дей­ствия nginx с fastcgi.

Настра­и­ва­ем нашу роль — созда­ем 3 задачи:

vi /etc/ansible/roles/nginx/tasks/main.yml

 

 

* пер­вая зада­ча нуж­на для созда­ния ката­ло­га, в кото­ром будут нахо­дить­ся фай­лы сай­та (без дан­но­го ката­ло­га наш кон­фи­гу­ра­ци­он­ный сайт выдаст ошиб­ку при попыт­ке пере­за­пу­стить сер­вис nginx). Вто­рая зада­ча созда­ем кон­фи­гу­ра­ци­он­ный файл для вир­ту­аль­но­го доме­на, кото­рый нахо­дит­ся в ката­ло­ге /etc/nginx/conf.d; источ­ни­ком дан­ных слу­жит создан­ный нами шаб­лон nginx_vhosts.conf; так­же мы зада­ем пере­мен­ную fastcgi_pass_path, кото­рая будет ука­зы­вать путь до сокет­но­го фай­ла. Тре­тья зада­ча так­же созда­ет кон­фи­гу­ра­цию для вир­ту­аль­но­го доме­на на базе создан­но­го шаб­ло­на; в отли­чие от вто­рой зада­чи, тре­тья созда­ет кон­фи­гу­ра­ци­он­ный файл в ката­ло­ге /etc/nginx/sites-enabled, а так­же име­ет дру­гое зна­че­ние пере­мен­ной fastcgi_pass_path. После успеш­но­го выпол­не­ния зада­чи, будет отправ­лен сиг­нал на пере­за­пуск служ­бы nginx для при­ме­не­ния настро­ек (неко­то­рые сер­ви­сы при­ни­ма­ют более пред­по­чти­тель­ный вари­ант — reloaded).Так­же мы доба­ви­ли усло­вие — вто­рая зада­ча будет при­ме­нять­ся к систе­ма на базе Red Hat, тре­тья — Debian.
* на самом деле, мы мог­ли две послед­ние зада­чи объ­еди­нить в одну, а пере­мен­ную fastcgi_pass_path задать в фай­ле плей­бу­ка. Но мы так посту­пи­ли наме­рен­но, что­бы про­де­мон­стри­ро­вать воз­мож­ность исполь­зо­ва­ния пере­мен­ных при опи­са­нии роли.

Откры­ва­ем обработчик:

vi /etc/ansible/roles/nginx/handlers/main.yml

Допи­сы­ва­ем:

 

 

Запус­ка­ем плейбук:

ansible-playbook /etc/ansible/play.yml -kK

Теги

В нашем при­ме­ре нам не дове­лось исполь­зо­вать теги — еще одну удоб­ную воз­мож­ность управ­ле­ния запус­ком плейбука.

Теги поз­во­ля­ют отме­тить роль и при запус­ке плей­бу­ка запу­стить имен­но ее, про­игно­ри­ро­вав дру­гие роли. Напри­мер, есть такой плейбук:

 

 

* в дан­ном плей­бу­ке есть две роли — одна назы­ва­ет­ся nginx, вто­рая — apache; для каж­дой роли мы зада­ли свой тег.

Теперь, что­бы запу­стить плей­бук, но выпол­нить в нем опре­де­лен­ную роль, нам доста­точ­но ука­зать тег:

ansible-playbook --tags web2 /etc/ansible/play.yml -kK

* дан­ная коман­да запу­стит плей­бук с выпол­не­ни­ем толь­ко роли с тегом web2 (в нашем при­ме­ре, apache).

Ansible Galaxy

пара слов о Ansible Galaxy. Гру­бо гово­ря, это репо­зи­то­рий гото­вых плей­бу­ков и ролей. Най­ти фай­лы, соот­вет­ству­ю­щую зада­че, а так­же доку­мен­та­цию мож­но на пор­та­ле galaxy.ansible.com. Уста­нов­ка выпол­ня­ет­ся коман­дой ansible-galaxy, например:

ansible-galaxy install geerlingguy.apache

* дан­ная коман­да создаст в ката­ло­ге поль­зо­ва­те­ля пап­ку .ansible/roles/geerlingguy.apache — в нее поме­стит фай­лы с опи­са­ни­ем роли.

Гото­вые биб­лио­те­ки мож­но исполь­зо­вать для выпол­не­ния задач или про­сто как шпаргалки.