17 February 2015

Управление неуправляемым и мониторинг критичного

Abnormal programmingOpen sourceSystem Analysis and DesignPuppet
В чужой монастырь со своим уставом не ходят. На очередном месте работы в мои задачи входит создание и последующая поддержка документооборота на платформе Alfresco, попутно ведение других систем. Заведение с предписанными правилам, устоявшимися обычаями и порядками. Многих привычных IT вещей в инфраструктуре нет, но всё работает надежно и всех устраивает. Как человек обладающий интеллектом и зачатками воспитания не буду пытаться нарушить чужие традиции и глобально что-либо менять. Учитывая over 500 рабочих мест, некоторые замечу не всегда рядом и критичность создаваемого сервиса для организации, некоторые вещи сделаю на свой лад. К ним относятся мониторинг и оркестрация.

Большинство рабочих мест располагается в здании на 6-и этажах. Имеются удалённые рабочие места. Парк администрируется разными сотрудниками, некоторые места относятся к другим организациям и могут вообще не иметь ответственного за IT сотрудника. Глобальная сеть и безопасность в зоне ответственности специально обученных людей. DHCP, DNS, AD если и есть то не везде. ITIL/ITSM просто импортные буквы. Операционные системы WindowsXP, WindowsVista, Windows7. Рабочие места могут мигрировать в разные части здания или за его пределы с обязательной сменой IP адреса. Пользователи работают на компьютерах обычно с правами администратора следовательно, могут менять все, включая %COMPUTERNAME%. Смену последнего желательно недопускать т.к. используется для общих принтеров.

Исходные данные и цели


Цели проекта в мониторинге – это проверка на доступность web приложений, снятие параметров с построением графиков java & postgresql & OS, оповещение посредством rss, sms и голосового звонка в критичных случаях.

Основная цель оркестрации – это исключить общение с over 500 пользователями. Иметь возможность оперативного массового изменения параметров, установки пакетов ПО, сертификатов и “мягкие политики — like GPO”.

С учётом стратегических приоритетов государства, ориентированности на полное импортозамещение, завтра на рабочих местах у пользователей документооборота могут оказаться МСВСфера или ROSA, соответственно инструменты управления конфигурацией и мониторинга лучше иметь кроссплатформенные с открытым исходным кодом, веб-интерфейсом управления и нулевой стоимостью внедрения&владения.

Динамический DNS


IP адреса ведутся по правилу: 10.здание.кабин.етрозетка. При смене дислокации рабочего места, меняется и IP адрес. Меняется вручную т.к. DHCP нет, следовательно option 82 не применим. В инвентарных номерах системных блоков могут встречаться дубликаты. Единственное, что относительно неизменно это MAC адрес. К нему и сделаем привязку. Определим шаблон имени рабочего места как РС-{макбезразделителей}. Если на компьютере несколько сетевых подключений будем считать, что Ethernet будет первым, сразу после инсталляции операционной системы. Его адрес будем использовать как константу для %COMPUTERNAME%.

Для работы с сертификатами необходимо иметь имя FQDN (Fully Qualified Domain Name), а из условий следует, что DNS отсутствует. Удобное решение в данной ситуации динамический DNS, он удобен для сопоставления %COMPUTERNAME% с IP адресом и соответственно определением текущего местонахождения рабочего места, если возникнет необходимость личного общения с пользователем.

Первое из решений, для динамического обновления DNS зон клиентом, виделась утилита Nsupdate из пакета Bind для Windows, но в этом случае клиенты имели общий ключ и следовательно могли изменять не только свои записи в зоне. Более безопасным виделось решение, когда клиент отправляет HTTP запрос, а сервер согласно своим правилам вносит изменения. Способ хранения зон в этом варианте очевиден – это SQL база. По умолчанию настроен на обслуживание запросов из БД сервер PowerDNS. Он используется во многих крупных проектах и представляется весьма стабильным. Его и будем использовать.

Как установить на Ubuntu
Устанавливаем PowerDNS:
$ sudo apt-get install -y pdns-server pdns-backend-mysql

Тестируем PowerDNS:
Проверим, что PowerDNS запущен:
$ sudo netstat -tap | grep pdns
Должно выдать:
roto@salt:~# netstat -tap | grep pdns

tcp        0      0 *:domain                *:*                     LISTEN      891/pdns_server-ins

Проверим, что PowerDNS отвечает:
$ sudo dig 127.0.0.1
Должно выдать:
roto@salt:~# dig 127.0.0.1

; <<>> DiG 9.9.5-3ubuntu0.1-Ubuntu <<>> @127.0.0.1
; (1 server found)
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 21529

;; flags: qr rd; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 2800
;; QUESTION SECTION:
;.              IN  NS

;; Query time: 1 msec
;; SERVER: 127.0.0.1#53(127.0.0.1)
;; WHEN: Fri Feb 13 11:29:05 KRAT 2015
;; MSG SIZE  rcvd: 239



Для комфортного управления зонами написано много разных интерфейсов к PowerDNS. Мы утвердили в работу powerdns-webinterface
Как это выглядит


Как установить на Ubuntu
Устанавливаем LAMP и необходимый модуль:
$ sudo apt-get install gettext

Скачиваем скрипты панели:
$ cd /tmp
$ wget powerdns-webinterface.googlecode.com/files/powerdns-webinterface-1.5.3.tar.gz
$ tar xvfz webinterface-1.5.3.tar.gz
$ sudo mv webinterface-1.5.3 /var/www/powerdns


Разрешаем запись в рабочую папку:
$ sudo chown -R www-data:www-data /var/www/powerdns/ tmp/templates_c

Выполняем импорт базы:
$ sudo mysql -u user-name -p pdns db < /path-to/ install.sql

Правим configs/db.php на правильные реквизиты подключения к базе pdns db

Заходим браузером по ссылке http://<IP_или_имя.нашего.сервера>/powerdns с именем/паролем admin: admin и меняем пароль.


Инструменты управления конфигурацией для автоматизации Windows ПК



Первоначально для централизованного распространения программного обеспечения рассматривались системы инвентаризации. Существующие проверенные решения ocsinventory-ng и Mandriva Pulse имеют в своем функционале возможность установки пакетов. Оба включают возможность интеграции с таким элемент ом ITIL/ITSM как Service Desk (в частности GLPI) удобно, но невнедримо в текущей ситуации. Изменение параметров реестра Windows и деплой сертификатов представляется не иначе как изготовлением инсталляционных пакетов. А эти пакеты пользователь с правами администратора может удалить с машины. Исходя из этого стал рассматривать системы управления конфигурацией.

Puppet считается наиболее распространённым. Он имеет множество модулей и пользовательских интерфейсов. Изменения в конфигурационных файлах(манифестах) для клиентов, последние получают их при очередном обращении к головному серверу, или через запрос от сервера для немедленного исполнения по средствам функции push.
Имеются модули для работы с Windows системами. Поддержка систем WindowsXP прекращена после версии puppet-3.1.1.msi, а текущую puppet-3.7.3.msi запустить не удалось т.к. завязана на вызове системных функций. В старших версиях отсутствуют `факты` как то `system32` и в манифестах необходимо описывать разные сценарии в зависимости от операционной системы. Это всё усложняет использование системы и решено было отказаться в пользу других инструментов.
SaltStack схож с Puppet в том, что использует метод push для связи с клиентами(minion). Мinion не открывает каких-либо портов, а сам подключается к серверу и ждет от него команд, таким образом повышается безопасность сервиса. Если у Puppet есть манифесты для описания конфигураций, то в SaltStack введено понятие `состояние`(state). Изменения произведенные на мастере будут выполнены на всех minion`ах. Стоит обратить внимание, что выполнение state`ов инициируется с мастера, а не самими клиентами как это реализовано в Puppet. Для поддержания актуального состояния в случае длительного отключения minion`а в его файле конфигурации добавлен параметр:
startup_states: 'highstate' (C:\salt\conf\minion)
Состояния — это конфигурационные файлы в формате YAML с расширением sls.
Как это выглядит
sls tree

Считывание state`ов начинается с файла top.sls, если не определено другое. Он содержит список файлов .sls для определенных групп.
roto@salt:/etc/salt/files# cat top.sls
base:
# '*':
# Для всех ПК с Windows
 'all_pc':
  - match: nodegroup
  - gr_inventory
  - gr_7z
  - gr_chrome
  - gr_libreoffice
  - gr_klitecodec
  - gr_essentials
# Гарант
 'gr_garant':
  - match: nodegroup
  - gr_garant
  # Консультант+
 'gr_consultant':
  - match: nodegroup
  - gr_consultant


Группы определяются в конфигурационном файле master’а (/etc/salt/master)и позволяют задавать их довольно гибко. Подробнее читайте в документации
В примерах из документации группы определены переменными. Для динамических типа паролей к базам, токенов, хэшей это `подпорки` (pillar) и статических `зерна` (grain). Кроме того переменные можно использовать в описании state`ов и командной строке salt.
roto@salt:/etc/salt/files# salt –G ‘cpuarch:AMD64’ test.ping

В качестве примера листинг `состояния ` антивируса от Microsoft:
roto@salt:/etc/salt/files# cat gr_essentials.sls
{% if grains['cpuarch'] == 'AMD64' %}
   w64_essentials:
    pkg:
     - installed
     {% elif grains['osrelease'] == '7' %}
        w32_essentials:
         pkg:
          - installed
       {% elif grains['osrelease'] == 'XP' %}
         w32xp_essentials:
          pkg:
           - installed
{% endif %}


* в парке нет других х64 систем, кроме Windows7

Установка пакетов ПО производится из репозитария заданного в конфигурационном файле master’а (/etc/salt/master). Описание пакета в файле init.sls, его листинг:
roto@salt:/etc/salt/files/win/repo/w32xp_essentials# cat init.sls
w32xp_essentials:
  4.4.304.0:
    installer: 'salt://win/repo/w32xp_essentials/mseinstall.exe'
    full_name: Microsoft Security Essentials
    locale: ru_RU
    reboot: False
    install_flags: '/q /s /runwgacheck '
    uninstaller: '%ProgramFiles(x86)%\Microsoft Security Client\Setup.exe'
    uninstall_flags: ' /U /S'


Salt master имеет встроенный файловый сервер и может отдавать любые файлы minion`ам. Порты ТСР:
  • 4505 #для управления
  • 4506 #для передачи файлов


Для SaltStack существует веб-интерфейсы SaltPad и Halite. Первый завести не удалось, а с помощью второго можно просматривать системные журнал сообщений, статус minion`ов, а также посылать им команды.
Как это выглядит



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



Во избежания проблем установил SHELLINABOX.
Как это выглядит
SHELLINABOX

Как установить на Ubuntu
Инсталируем Shell In A Box для доступа по ssh через любой html5 браузер:
$ sudo apt-get install openssl shellinabox
Правим дефолтные конфиги:
$ sudo vi /etc/default/shellinabox
# TCP порт shellinboxd'а на котором отвечать
SHELLINABOX_PORT=443 
# IP адрес или имя SSH сервера
SHELLINABOX_ARGS="--o-beep -s /:SSH:localhost --localhost-only" 

Перезапускаем сервис:
$ sudo service shellinabox restart
Проверяем порт:
$ sudo netstat -nap | grep shellinabox
Открываем в html 5 совместимом браузере https://<IP_или_имя.нашего.сервера>. Пользуемся.


Итоговый скрипт для установки получился следующим:
install.cmd
@Echo Off

rem /*************************************
rem  *      Install for SaltStack        *
rem  *-----------------------------------*
rem  * (c) 2015 by Aleksey Ovchinnikov   *
rem  * License: GPL                      *
rem  * Feel free to customize on your    *
rem  * needs as long this copyright      *
rem  * remains intact                    *
rem  *************************************/

SetLocal EnableExtensions

rem /// Проверяем, что скрипт запущен от Администратора

AT > NUL
If %ERRORLEVEL% EQU 1 (
	echo Please use "Run as Administrator"!
	pause
	exit /b 
)

rem /// Получаем mac первого адаптера

%SYSTEMROOT%\System32\getmac.exe /NH /FO csv > %TEMP%\all_mac.tmp
type %TEMP%\all_mac.tmp | findstr /r /c:"-" > %TEMP%\all_mac.txt
del %TEMP%\all_mac.tmp

	for /f "usebackq  delims=" %%i in (`find /n /v "" %TEMP%\all_mac.txt ^| find "[1]"`) do (
	  set mac=%%i

)

	For /f "delims=, tokens=1" %%i in ("%mac%") do ( set mac=%%i  )

set mac=%mac:~4,17%

	For /f "delims=^- tokens=*" %%i in ("%mac%") do ( set mac=%%i  )

set mac=%mac:-=%
set mac=%mac:~0,12%


rem /// Меняем имя компьютера

If not "%ComputerName%"=="PC-%mac%" (
rem	wmic.exe /interactive:off ComputerSystem Where "name = '%computername%'" call rename Name='PC-%mac%'
rem	wmic os where Primary='TRUE' reboot

	REG ADD HKLM\SYSTEM\ControlSet001\Control\ComputerName\ComputerName /v ComputerName /t REG_SZ /d "PC-%mac%" /f
	REG ADD HKLM\SYSTEM\CurrentControlSet\Control\ComputerName\ComputerName /v ComputerName /t REG_SZ /d "PC-%mac%" /f
	REG ADD HKLM\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters /v "NV Hostname" /t REG_SZ /d "PC-%mac%" /f
	REG ADD HKLM\SYSTEM\ControlSet001\Services\Tcpip\Parameters /v "NV Hostname" /t REG_SZ /d "PC-%mac%" /f
	shutdown -t 0 -r -f	
exit /b

)
echo ...get NAME  ^> %ComputerName%



rem /// Получаем IP компьютера

	FOR /F "usebackq tokens=2 delims=[]" %%i IN (`ping %Computername% -n 1 -4`) DO if not "%%i"=="" Set ip=%%i

echo ...get IP    ^> %ip%




rem /// Получаем версию системы

set key=HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion

	For /F "delims=" %%a in ('reg query "%key%" /v "ProductName" ^| find /i "ProductName"') do ( set OSName=%%a )

set OSName=%OSName:ProductName=%
set OSName=%OSName:REG_SZ=%

	For /F "tokens=* delims= "  %%a in ("%OSName%")  do ( set OSName=%%a )

echo ...get OS    ^> %OSName%




rem /// Получаем разрядность системы

Set xOS=x64

If "%PROCESSOR_ARCHITECTURE%"=="x86" If Not Defined PROCESSOR_ARCHITEW6432 Set xOS=x86

echo ...get TYPE  ^> %xOS%




rem /// Передаем для записи в DNS

set data=%ip%:%COMPUTERNAME%:%COMPUTERNAME%_%OSName%_%xOS%
set data=%data: =_%

echo ...add DNS   ^> 

	c:\saltstack\curl.exe -s http://salt.домен.ру/dns/update.php?data=%data%"




rem /// Устанавливаем SaltStack учитывая разрядность Windows

 If %xOS%==x86 (c:\saltstack\Salt-Minion-3.1.5-win32-Setup.exe /S /master=salt.домен.ру /minion-name=%COMPUTERNAME%) Else (c:\saltstack\Salt-Minion-3.1.5-AMD64-Setup.exe /S /master=salt.домен.ру /minion-name=%COMPUTERNAME%)




rem /// Добавляем записи для автообновления стэйтов призапуске системы

echo.startup_states:  'highstate' >>"C:\salt\conf\minion"
echo ...auto state    ^> Done!
attrib +H +S c:\salt
echo ...hide folder    ^> Done!
cd c:\
rmdir /s /q c:\saltstack



Система мониторинга Zabbix


Существует множество систем мониторинга. С Zabbix знаком давно, его и выбрал.

Как это выглядит



Как установить на Ubuntu
Устанавливаем необходимые пакеты:
$ sudo apt-get install zabbix-server-mysql zabbix-frontend-php ca-certificates-java libslf4j-java jarwrapper libandroid-json-org-java liblogback-java

В файле конфигурации сервера /etc/zabbix/zabbix_server.conf настраиваем соединение с базой данных:
$ sudo mcedit /etc/zabbix/zabbix_server.conf
### Option: DBHost
#       Database host name.
#       If set to localhost, socket is used for MySQL.
#       If set to empty string, socket is used for PostgreSQL.
#
# Mandatory: no
# Default:
# DBHost=localhost

### Option: DBName
#       Database name.
#       For SQLite3 path to database file must be provided. DBUser and DBPassword are ignored.
#       Sample SQLite3 DBName:
#                               DBName=/var/lib/zabbix/zabbix.sqlite3
#
# Mandatory: yes
# Default:
# DBName=
DBName=zabbix

### Option: DBUser
#       Database user. Ignored for SQLite.
#
# Mandatory: no
# Default:
# DBUser=

DBUser=zabbix

### Option: DBPassword
#       Database password. Ignored for SQLite.
#       Comment this line if no password is used.
#
# Mandatory: no
# Default:
# DBPassword=
DBPassword=zabbix

Готовим базу данных:
mysql –uuser-name –p
mysql> create database zabbix character set utf8 collate utf8_unicode_ci;
mysql> grant all privileges on zabbix.* to zabbix@localhost identified by 'zabbix';
mysql> exit;


Загружаем структуру и значения в базу данных:
$ sudo cd /usr/share/zabbix-server-mysql
$ sudo gunzip *.gz
$ sudo mysql -uuser-name zabbix -p < schema.sql
$ sudo mysql -uuser-name zabbix -p < images.sql
$ sudo mysql -uuser-name zabbix -p < data.sql


Перезапускаем zabbix:
$ sudo service zabbix-server start

И проверяем, что все без ошибок:
$ tail -n 100 /var/log/zabbix-server/zabbix_server.log

Скопируем необходимый файл:
$ sudo cp /usr/share/doc/zabbix-frontend-php/examples/apache.conf /etc/apache2/conf-available/zabbix.conf

Настроим параметры php для web интерфейса:
$ sudo mcedit /etc/apache2/conf-available/zabbix.conf
php_value max_execution_time 300
php_value memory_limit 128M
php_value post_max_size 16M
php_value upload_max_filesize 2M
php_value max_input_time 300
php_value date.timezone Asia/Krasnoyarsk


Добавим файл конфигурации web интерфейса zabbix к apache:
$ sudo a2enconf zabbix.conf

И перезапустим web сервер:
$ sudo service apache2 reload

Откройте URL вашwebсервер/zabbix и выполните все шаги:




На последнем шаге будет предложено войти:


Логин/пароль по умолчанию: Admin/zabbix. Измените пароль после входа.


Мониторинг JMX


Начиная с версии 2.0 в zabbix добавлена нативная поддержка для мониторинга JMX. Взаимодействие происходит через API управления JMX приложений через демона, называемого Zabbix Java gateway. Он написан на языке Java.
Как установить на Ubuntu
Устанавливаем необходимые пакеты:
$ sudo apt-get install --no-install-recommends zabbix-java-gateway

В файле конфигурации сервера /etc/zabbix/zabbix_java_gateway.conf настраиваем соединения и опции запуска Java-gateway:
$ sudo mcedit /etc/zabbix/zabbix_java_gateway.conf

# адрес нашего Java-gateway
JavaGateway=127.0.0.1
# порт для Java Gateway
JavaGatewayPort=10052
# количество Java Gateway процессов, которые будут обрабатывать информацию StartJavaPollers=5


В файле конфигурации сервера /etc/zabbix/zabbix_server.conf настраиваем соединение с Java-gateway:
$ sudo mcedit /etc/zabbix/zabbix_server.conf
### Option: JavaGateway
#<----->IP address (or hostname) of Zabbix Java gateway.
#<----->Only required if Java pollers are started.
#
# Mandatory: no
# Default:
# JavaGateway=
JavaGateway=127.0.0.1

### Option: JavaGatewayPort
#<----->Port that Zabbix Java gateway listens on.
#
# Mandatory: no
# Range: 1024-32767
# Default:
# JavaGatewayPort=10052
JavaGatewayPort=10052

### Option: StartJavaPollers
#<----->Number of pre-forked instances of Java pollers.
#
# Mandatory: no
# Range: 0-1000
# Default:
# StartJavaPollers=0
StartJavaPollers=5


Разрешаем запуск:
$ sudo mcedit /etc/default/zabbix-server
START=yes


Запускаем сервис:
$ sudo service zabbix-java-gateway restart

Следующая настройка производится на машине где будет производится мониторинг. Добавьте в скрипт запуска сервера приложений или контейнер сервелетов:
-Djava.rmi.server.hostname=192.168.3.14 \
-Dcom.sun.management.jmxremote \
-Dcom.sun.management.jmxremote.port=12345 \
-Dcom.sun.management.jmxremote.authenticate=false \
-Dcom.sun.management.jmxremote.ssl=false \

Закройте доступ к этому порту всем, кроме IP адресов сервера zabbix и машины администратора с помощью firewall.

С машины администратора запустите JConsole из jdk и подключитесь к машине где будет производится мониторинг.
Как это выглядит



При успешном соединении нужно зайти в web интерфейс zabbix и настроить параметры для мониторинга. Переходим в Настройка > Узлы сети, кликаем Создать узел сети и вводим необходимые значения.
Как это выглядит



Через некоторое время появятся данные и можно строить график.
Как это выглядит




Мониторинг PostgreSQL


Согластно wiki PostgreSQL, решений для мониторинга написано не мало. Я остановился на libzbxpgsql (Lib-Zabbix-PostgreSQL). Это изначально скомпилированный модуль написанный на C для zabbix агента и xml шаблон для сервера. Преимущество перед скриптами очевидно, это один процесс и отсутствие внешних зависимостей.
Как установить на Ubuntu
Предлагается компилировать модуль самостоятельно, бинарный пакет есть только в rpm. Его и возьмем.

Устанавливаем необходимые пакеты на машину с базой данных которую будем мониторить:
$ sudo apt-get install alien zabbix-agent

Скачиваем модуль:
$ sudo wget downloads.sourceforge.net/project/libzbxpgsl/rpms/libzbxpgsql-0.1.1-1.el7.centos.x86_64.rpm

Конвертируем в deb пакет:
$ sudo alien libzbxpgsql-0.1.1-1.el7.centos.x86_64.rpm

Устанавливаем пакет:
$ sudo dpkg -i libzbxpgsql_0.1.1-2_amd64.deb

В файле конфигурации агента /etc/zabbix/zabbix_agentd.conf настраиваем соединения с сервером и опции:
$ sudo mcedit /etc/zabbix/zabbix_agentd.conf
Server=адрессервера
ServerActive=адрессервера:порт
Hostname=doc.домен.ру


И перезапустим агента:
$ sudo service zabbix-agent restart

Сохраняем template_postgresql_server.xml
Открываем web интерфейс zabbix и переходим в Настройка > Шаблоны, кликаем Импорт конфигурации. Импортируем наш xml файл.

Настраиваем параметры для этого узла сети. Добавляем нужные шаблоны и Template PostgreSQL Server. Во вкладке Макросы вписываем параметры соединения с базой данных которую будем мониторить.
Как это выглядит



Через некоторое время появятся данные и можно строить график.
Как это выглядит




Данная статья составлена как документация для моего текущего работодателя. Комментарии, замечания и указания на неточности приветствуются.
Tags:проектированиеsaltsaltstackpuppetzabbixpowerdnswindowsjmxjavamonitoringpostgresql
Hubs: Abnormal programming Open source System Analysis and Design Puppet
+4
11.5k 47
Comments 1
Popular right now
Tech Lead DevOps Engineer
from 5,000 to 5,600 $Atto Trading Technologies LLCКиев
Senior Java Developer (REMOTE) до 300.000 ₽ /mnth
from 250,000 to 300,000 ₽OffsideGamingRemote job
Angular UI Team Lead
from 4,000 to 5,000 $AWWCOR Inc.Remote job
Java API Developer
from 3,300 to 5,000 $AWWCOR Inc.Remote job
Art Director/Head of Design Department
from 240,000 ₽Direct Line DevelopmentМосква