Pull to refresh

[SOA] Service Oriented Ansible

Reading time 6 min
Views 4.6K

Доброго дня. Сегодня мы будем говорить об Ansible и сервисах, можно конечно использовать и другие запчасти для SOA типа Docker, Jenkins и Puppet, но сегодня у нас Ansible, сервисы и пару строчек PHP. Многие из вас видели такие картинки (картинки и символы изменены).


SOA

и читали такие статьи c картинками (первая, вторая), где упоминается SOA.


Так и ближе к делу! Cегодня мы будем


Деплоить SOA


2 nginx, 2 фронта и сервис и деплой. Всего 7 ВМ понадобиться для разворачивания SOA песочницы.


В качестве деплой сервера будем использовать локальную машину и в том же сегменте сети у нас развернуты виртуалки с пользователем ansible#ansible. Так же нашим ВМ требуется доступ в интернет для установки софта. Самый просто способ это сделать 2 сетевых интерфейса с NAT и внутренней сетью 192.168.0.0\32. Если пере использовать ВМ то можно сократить это число до 4, в качестве песочницы, но не более.


Главный репозиторий, который нам все это намажет на наш бутерброд из ВМ и чтобы работало.


Также будем использовать ещё 2 репозитория. Они содержат в себе пару строчек PHP кода без привязки к какому либо фреймворку или проекту. Раз и два.


Задача фронта сделать запрос к сервису и отобразить его результат.


Задача сервиса ответить 3 большие буквы. Ваш Капитан очевидность. (Можно попробовать подсунуть свой репозиторий — п.с. Ваш Капитан очевидность снова).


Инвенторий


Так назвается файл в котором храниться описание структуры ВМ и их особенности hosts/prod.ini


Обзовём наши ВМ и дадим им имена. Фронт к которому у нас обращаться пользвоатель это


nginx-front-00 ansible_host=192.168.56.102

Осноной аппликейшен который принимает запросы


php-front-00 ansible_host=192.168.56.103
php-front-01 ansible_host=192.168.56.101

Один маленький балансер который обслуживает наши сервисы


nginx-balance-00 ansible_host=192.168.56.104

Один маленький сервис который горовит слово из 3х букв


service-sign-00 ansible_host=192.168.56.101
service-sign-01 ansible_host=192.168.56.103

Как видете я переиспользую ВМы для сервиса и для форонта, но давйте будем думать что это разные ВМ который находяться на разных железных серверах для отказоустойчивости.


Структура инвентория


Мы обозвали наши хосты, теперь софрмируем из них группы, а сами группы разделим на несколько частей. Первая группа груп это группы сервисов.


Группа сервисы


[nginx-front]
nginx-front-00

[front_app]
php-front-00
php-front-01

[nginx-balancer]
nginx-balance-00

[sign]
service-sign-00
service-sign-01

[deploy]
deploy

Группы Софт


Мы сгруппировали наши хосты в группы и теперь надо указать какой софт необходим каждоый группе для этого необходима ещё одна группа груп.


[php-cli:children]
front_app

[php-fpm:children]
front_app
sign

[git:children]
front_app

[hg:children]

[nginx:children]
nginx-front
nginx-balancer

Добавление группы в группу подскажет нашему деплою что на данную группу необходимо установить соответвуютщее програмное обеспечение. Для хостов входящих в группу php-cli установить консольный вариант PHP для крон заданий например.
П.с. Ваш Капитан очевидность


Группа Сервисы


Следующая группа групп =)


[services:children]
sign

Группирует наши сервисы как сервисы.


Особенность Сервисов


Особенность сервисов состоит в том что сушествуют 2 точки входа


// server_name {{ service_name }}
api/index.php

// server_name {{ service_name }}_web
web/index.php

Зачем эту необходимо? Если вы хотите сделать административную панель сервиса то ненадо делать для неё дополнительный сервис можно использовать эти же ВМ и обраoаться к ним как {{service_name}}_web через ифрайм или курл запросом. Сервисы могут меняться таким образом код администрирования сервисов будет обновляться вместе с сервисом.


Ключи


Каждый раз иcпользовать пароли не очень удобно, поэтому давайте разбросаем ключи на наши ВМ


ansible-playbook -i hosts/prod.ini task/system/authorized_key.yml  -k --ask-sudo-pass

специально для вас я уже сгенерировал ключи в папке roles/authorized_key/keys, но вы обязаныможете сделать свои.


Добавим приватный ключ в ключе хранилище


cp roles/authorized_key/keys/id_rsa ~/.ssh/id_rsa_deploy && chmod 700 ~/.ssh/id_rsa_deploy && ssh-add ~/.ssh/id_rsa_deploy

ВАЖНО: после перезагрузки машины ключ надо добавить заново


Или прописать его в конфигурациях например в файл /etc/ssh/ssh_config добавить строчку


IdentityFile /etc/ssh/ssh_hg_deploy_key

Софт


Установим необходимый софт на ВМ


ansible-playbook -i hosts/prod.ini task/system/soft-install.yml

Это поставит нам необходимый софт на наши Группы Софт. Мы можем добавлять или удалять группы из групп чтобы на каждой ВМ стоял только необходимый набор программного обеспечения. В случае если ВМ пере используется в другом сервисе или происходят большие изменения сервиса то проще ВМ уничтожить и развернуть заново.


Мы установили php-cli, php-fpm, git, nginx на ниши машинки что же дальше…


FRONT


Нам необходимо сконфигурировать наш фронтовой НГИНКС который находиться тут


 roles/nginx-front/templates/nginx.conf.j2

Как видимо это шаблон с минимально сконфигурированным набором параметров, даже особо не конфигурированный. Также очень необходимый файл:


 roles/nginx-front/templates/vhosts.conf.j2 

Рассмотрим его более детально


upstream php-front
{
    {% for upstream in groups["front_app"] %}
        server {{ hostvars[upstream]["ansible_host"] }}:9000;
    {% endfor %}
}

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


Виртуальный хост использует upstream php-front.


  fastcgi_pass php-front;

Применим эти настройки на наш фронт


ansible-playbook -i hosts/prod.ini task/nginx/front.yml 

Теперь наш фронт начал посылать запросы на наш фронт апп!
Но там ещё ничего нет ....


Сервисы


Наш фронт апп также является сервисом как и остальные сервисы, просто он принимает запрос из сети интернет, поэтому он конфигурируеться как и все остальный сервисы.


в папке hosts/group_vars/ в соответвии названием группы находяться файлы конфигурации группы


#hosts/group_vars/front_app.yml
service_name: front_app
deploy_via: git
repo: 'https://github.com/dangerousvasil/simpleFront'
branch: 'master'
keep_releases: 10

также общие конфигурации hosts/group_vars/all.yml


 releases_path: '/var/www'
 current_release_dir: 'www'
 application_configuration_path: '/etc/application/config.ini'
 keep_releases: 0
 apt_cache_valid_time: 86400
 www_user: 'www-data'

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


Запустим задачу на обновления кода приложения


 ansible-playbook -i hosts/prod.ini task/app/code-update.yml 

Теперь наше приложение уже готово принимать первые запросы на фронт! Также мы можем зайти на нашу ВМ и посмотреть где же лежит наш код по умолчанию это


{{ releases_path }}/{{ service_name }}/{{ current_release_dir }}
/var/www/front_app/www

Зайдя на машинку мы увидим что эта папка у нас являеться ссылкой которая ведёт на другую папку releases/20171024121418Z, это сделаного для того чтобы мы всегда могли откатить изменения на прошлый успешный релиз


lrwxrwxrwx /var/www/front_app/www -> /var/www/front_app/releases/20171024121418Z

releases:
total 40
drwxr-xr-x 2  20171024121418Z
drwxr-xr-x 2  20171024120329Z
drwxr-xr-x 2  20171024112918Z
drwxr-xr-x 2  20171024104100Z
drwxr-xr-x 2  20171024102800Z
drwxr-xr-x 2  20171024102702Z
drwxr-xr-x 2  20171024102548Z
drwxr-xr-x 2  20171024102458Z
drwxr-xr-x 2  20171024095629Z
drwxr-xr-x 2  20171024094949Z

Для этого есть задача


ansible-playbook -i hosts/prod.ini task/app/code-rollback.yml 

Это передвинет нашу ссылку на прошлый релиз, если он был, или выдаст исключение. Если запустить задачу ещё раз то передвинет ссылку дальше пока релизы не закончатся.


Балансер


Код выложен, фронт настроен, осталось дело за малым — балансировщик сервисов.
Пока используем 1 можно добавить ещё несколько и банасировать между ними с помощью разных инструментов ddns или HAProxy или просто рандомно выбирать сервер на стороне приложения — решать вам.


Запускаем задачу


ansible-playbook -i hosts/prod.ini task/nginx/balancer.yml 

С помошью файла hosts/group_vars/nginx-balancer.yml


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


with_services:
  - sign

Окружение


Для того чтобы наше приложение знало что её окружает (балансеры, сервисы) мы сгенерируем небольшой ini файл и разложим его на каждую машинку


ansible-playbook -i hosts/prod.ini task/app/app_config.yml 

$ cat /etc/application.ini 
[application]
service.host[]=192.168.56.102

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


Тестирование


Открыв в браузере наш фронт http://192.168.56.102 мы увидим неприглядную картинку


string(14) "192.168.56.104"
string(191) "HTTP/1.1 200 OK
Server: nginx/1.10.3 (Ubuntu)
Date: Wed, 25 Oct 2017 09:51:43 GMT
Content-Type: text/html; charset=UTF-8
Transfer-Encoding: chunked
Connection: keep-alive

<h1>API</h1>"

Для кого-то это кажеться полной ерундой, а кто-то увидит что наш сервис написал нам свои 3 большие буквы "API" и обрадуется.


Заключение


Если вы добавили свой проект в качестве фронта и написали там пару строчек или подключили пару бибилиотек для работы с сервисами по json-rpc( наверно вы разбираетесь в PHP и вам это сильно поможет)


$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://' . $serviceHost); // balancer
$header[] = "Host: service";       // необходимый сервис
@curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
$output = curl_exec($ch);
var_dump($output);

Вариант с бибилиотекой fguillot/json-rpc


$client = new Client('http://' . $serviceHost); // balancer
$http = $client->getHttpClient()
        ->withHeaders(['Host: service']);  // service

То поздравляю вы окунули свой проект в самый модный и молодежный тренд сезона SOA.


Пост скриптум


Код проекта ещё требует множества доработок и конфигураций, поэтому сделаны только основные конфигурации чтобы работало.

Tags:
Hubs:
+7
Comments 3
Comments Comments 3

Articles