Translate

понеділок, 14 березня 2016 р.

Foreman. Setup and Configuration

Foreman - це інструмент управління повним життєвим циклом серверів. Проект розпочав 6 років тому Ohad Levy, співробітник RedHat в Ізраїлі. Проект розвивається дуже активно та має обширне співтовариство. По замовчуванню працює з Puppet, з певними зауваженнями також може інтегруватись з Chef, Salt, а через систему плагінів і з Ansible.

Під управлінням повним життєвим циклом вузла розуміються такі етапи:

  • Установка - початкова установка операційної системи.
  • Конфігурація - установка та налаштування усього необхідного програмного забезпечення та налаштування самої операційної системи (додавання користувачів, налаштування мережевих інтерфейсів і т.п.)
  • Оновлення, Управління та Аудит - установка виправлень помилок софту, додавання змін до конфігурацій діючих програм, моніторинг вузлів на протязі усього життєвого циклу.

Щоб зрозуміти як Foreman забезпечує виконання цих етапів спочатку розглянемо його складові:


  • Веб-панель Foreman - панель для зручного адміністрування Puppet-модулями, групами та ін.
  • API - програмний інтерфейс Foreman.
  • DB - база даних Foreman. У якості бази може виступати як PosgreSQl, так і MySQL.
  • LDAP/AD - користувачі можуть авторизуватись через віддалені бази LDAP чи Active Directory, що дуже зручно навіть для відносно великих компаній.
  • Smart Proxy (DHCP, DNS, TFTP, CA) - група сервісів Foreman, що можуть перебувати як на одному вузлі, так і на різних. Відповідають за різні дії: provisioning нових серверів, збереження та підписання сертифікатів та ін. Таких проксі може бути декілька, наприклад для зв'язку із різними підмережами.
  • Puppet Master - майстер, що надає конфігурації за іменем хосту Puppet-агента. Foreman-інсталятор налаштовує майстер на роботу через Apache та Passenger.
  • Puppet Agents - агенти, що мають бути установлені на серверах, що адмініструються за допомогою Foreman.

Установка операційної системи (provisioning) в Foreman відбувається за наступною схемою. Спочатку ініціюється створення хосту через готові API-прив'язки (AWS, OpenStack, VMWare, Bare-Metal і т.п.). Далі хост стартує з PXE (Preboot Execution Environment) протоколу та надсилає broadcasts повідомлення в мережу для пошуку DHCP-серверу, що може обробити PXE-запити. На ці запити відповідає Smart Proxy Foreman-a (точніше DHCP-сервер, що входить до його складу) та надає хосту IP-адресу, що вже була обрана на початковому етапі в Foreman. Підключившись до мережі, хост запитує в PXE-сервера образ установки ОС, а останній в свою чергу надсилає у відповідь адресу TFTP-сервера, з якого хост і встановлює образ операційної системи.

Після установки, хост надсилає запит на підписання сертифікату. Після підписання, стосовно фактів, що надіслав хост, Foreman (Puppet Master) надасть необхідні маніфести, що його стосуються.


У попередній статті та і раніше підключення модулів та опис їх параметрів відбувалось через маніфест site.pp. Та наразі цю роль буде виконувати сам Foreman, виступаючи в ролі External Node Classifier (ENC) для Puppet.

Всі складові Foreman можуть лежати як на одному хосту, так і рознесені окремо для покращення рівня масштабованості. Я опишу перший варіант, а гарний приклад другого можна побачити тут.

Спочатку відредагуємо конфігураційний файл локального ssh-клієнту. Закоментуємо передачу типу локалі через ssh:

# vim /etc/ssh/ssh_config
...
#    SendEnv LANG LC_*
...

Інакше може виникнути помилка із установкою бази postgresql, яку потім необхідно буде перестворювати вручну.

Зробимо прив'язку домен-IP через /etc/hosts та задамо значення хостнеймів для клієнту і Foreman серверу відповідно:

# vim /etc/hostname
client.me

# vim /etc/hostname
foreman.me

# hostname --file /etc/hostname

# vim /etc/hosts

192.168.1.10     foreman.me foreman
192.168.1.11     client.me  client

За бажанням можна звісно ці зміни внести до DNS-серверу локальної мережі, якщо він звісно є.

Для синхронізації часу встановимо ntp на обох серверах:

# apt-get update && apt-get -y install ntp

# service ntp stop
 * Stopping NTP server ntpd

# ntpd -gq
ntpd: time slew -0.000338s

# service ntp start
 * Starting NTP server ntpd

Додамо puppet репозиторії на обох серверах:

# apt-get -y install ca-certificates
# wget https://apt.puppetlabs.com/puppetlabs-release-trusty.deb
# dpkg -i puppetlabs-release-trusty.deb

А репозиторії до Foreman лише на foreman.me:

# echo "deb http://deb.theforeman.org/ trusty 1.10" > /etc/apt/sources.list.d/foreman.list
# echo "deb http://deb.theforeman.org/ plugins 1.10" >> /etc/apt/sources.list.d/foreman.list
# wget -q http://deb.theforeman.org/pubkey.gpg -O- | apt-key add -

Установлюємо пакет для інсталяції Foreman:

# apt-get update && apt-get -y install foreman-installer

Та запускаємо автоматичний установщик:

# foreman-installer
Installing             Done                                               [100%] [.....................................................]
  Success!
  * Foreman is running at https://foreman.me
      Initial credentials are admin / LCc63ifBvBjZUyqs
  * Foreman Proxy is running at https://foreman.me:8443
  * Puppetmaster is running at port 8140
  The full log is at /var/log/foreman-installer/foreman-installer.log

foreman-installer - це пакет, що складається з Puppet-маніфестів для установки всього необхідного для роботи Foreman. Має багато різних опцій, завдяки яким можна наприклад змінити базу на MySQL чи відключити встановлення певних інтеграцій чи сервісів.

Перевіряємо в браузері https://foreman.me, використовуючи логін/пароль, що згенерував установщик у попередньому пункті:


Додамо вузол foreman.me до списку вузлів, котрими він же зможе управляти. Це можна зробити запустивши агент і запитавши дані з сервера (тобто виходить із самого себе):

# puppet agent --test

Отже, перший вузол було додано до серверу Foreman:


Тепер встановимо Puppet агент на клієнті client.me:

# aptitude install puppet

Дозволимо йому працювати у якості демону:

# vim /etc/default/puppet
...
START=yes
...

Такий режим роботи дозволить опитувати сервер кожні 30 хв.

Дозволимо оновлення puppet лише до мінорних версій:

# vim /etc/apt/preferences.d/00-puppet.pref

Package: puppet puppet-common
Pin: version 3.8*
Pin-Priority: 501

Відредагуємо основний конфіг клієнта до такого виду:

# vim /etc/puppet/puppet.conf

[main]
logdir=/var/log/puppet
vardir=/var/lib/puppet
ssldir=/var/lib/puppet/ssl
rundir=/var/run/puppet
factpath=$vardir/lib/facter

[agent]
server = foreman.me

Видаляємо секцію [master], а замість вписуємо [agent] з адресою Foreman-сервера після. Параметр templatedir також зайвий.

# service puppet start

Після запуску агента на клієнті, останній має відіслати запит на підписання Фореману (папет-майстру). Переглянути всі запити на сертифікацію можна наступним чином:  

# puppet cert list --all
  "client.me"  (SHA256) 52:9A:2A:17:A3:B1:E1:71:31:3D:FC:D3:70:66:7F:AD:61:D5:B4:0F:97:98:BB:FA:9A:C8:30:EF:33:4B:8E:B9
+ "foreman.me" (SHA256) 84:51:77:FD:12:84:E3:20:CF:56:9A:63:50:60:18:ED:55:70:D2:38:AD:AD:CD:81:99:9D:4B:01:75:6E:D9:11 (alt names: "DNS:foreman.me", "DNS:puppet", "DNS:puppet.me")

За відсутністю знака плюс навпроти запиту на сертифікацію можна побачити, що клієнту поки не дозволено опитувати сервер на предмет файлів конфігурацій.
Тож підпишемо запит клієнта:

# puppet cert sign client.me
Notice: Signed certificate request for client.me
Notice: Removing file Puppet::SSL::CertificateRequest client.me at '/var/lib/puppet/ssl/ca/requests/client.me.pem'

# puppet cert list --all
+ "client.me"  (SHA256) 7F:35:DD:1D:F9:3D:C0:EC:9E:D2:E6:28:02:7C:DC:40:94:86:F4:67:54:58:1A:51:BD:D7:43:23:C9:21:48:FA
+ "foreman.me" (SHA256) 24:A1:E4:3A:58:6E:C7:E0:99:64:65:74:A4:74:E3:10:C0:3E:06:05:EE:17:EC:E4:FD:59:C2:E5:6F:3C:3C:6B (alt names: "DNS:foreman.me", "DNS:puppet", "DNS:puppet.me")

У разі помилки (невірно заданого імені домена і т.п.) звісно можна його і видалити:

# puppet ca destroy something.me
Notice: Removing file Puppet::SSL::CertificateRequest something.me at '/var/lib/puppet/ssl/ca/requests/something.me.pem'
Deleted for client: Puppet::SSL::CertificateRequest

Для підписання запитів на сертифікацію можна також скористатись веб-панеллю Foreman. Для цього необхідно перейти до Infrastructure -> Smart Proxies -> Certificates та натиснути кнопку Sign :


Звідси ж можна і видалити запити чи вже авторизовані вузли.

Наразі до панелі управління додано 2 ноди:



Мало що можна зробити з Foreman без puppet-модулів, тому для початку завантажимо готовий з Puppetforge:

# puppet module install -i /etc/puppet/environments/production/modules puppetlabs/ntp

У директорії "/etc/puppet/environments/" можна створювати будь-яку кількість оточень з окремими модулями для кожного. Для імпорту доданого модуля необхідно натиснути Configure -> Classes та після натискання кнопки Import зміни будуть підтягнуті з сервера:


Ставимо галочку навпроти необхідного модуля та тиснемо Update:


І так ось вони мають відображатись в результаті правильно виконаних кроків:


Якщо модуль було написано вірно для використання в Foreman, деякі його параметри можна перезаписати на інші значення прямо в адмінці. Наприклад, щоб змінити пул серверів в модулі ntp, що можуть опитуватись для уточнення часу, необхідно перейти за такою адресою: Configure -> Classes -> Class name: ntp -> Smart Class Parameter. Обираємо ліворуч параметр servers, ставимо галку Override, Key type: array як на малюнку:


Та нарешті в Default value вписуємо новий список ntp-серверів:

["0.us.pool.ntp.org","1.us.pool.ntp.org","2.us.pool.ntp.org","3.us.pool.ntp.org"]

Деякі інші параметри класу також можна за необхідності перезаписати за такою ж схемою.

Щоб застосувати модуль до вузла, його необхідно правильно підключити. У якості піддослідного хосту для установки модуля ntp оберемо foreman.me. Для цього перейдемо за адресою Hosts -> All nodes -> Edit (праворуч від імені вузла):


Перейдемо на вкладку Puppet classes та додамо до хосту ntp клас натиснувши "+":


На вкладці Parameters видно, що параметр із ім’ям servers модуля ntp було нами ж і перезаписано:


Тиснемо Submit і протягом 30 хвилин (по-замовчуванню) пакет ntp зі зміненим конфігураційним файлом буде встановлено на потрібний вузол.
Або ж можна пришвидшити перебіг подій запустивши запит на отримання змін на самому вузлі:

# puppet agent --test

І врешті решт всі зміни будуть відображені в панелі Foreman.

Тут же є інформація про доступні факти (з facter), можна переглянути звіти (Reports), YAML з підключеними класами та конфігурацією вузла, графіки успішності запусків та інше.

Як я вже згадував, модуль(клас) має бути коректно написаний задля можливості зміни його параметрів в Foreman. Тому далі я приведу приклад написання такого модуля для установки та налаштування веб-сервера Apache.

Створимо структуру директорій для модуля:

# mkdir -p apache/{manifests,templates}

# vim manifests/init.pp

# Manage Apache
class apache (

    $vhost_domain = $apache::params::vhost_domain,
    $vhost_root   = $apache::params::vhost_root

    ) {

    package { 'apache2-mpm-prefork': ensure => installed }

    service { 'apache2':
        ensure  => running,
        enable  => true,
        require => Package['apache2-mpm-prefork'],
    }

    file { "/etc/apache2/sites-available/${vhost_domain}.conf":
        content => template('apache/vhost.erb'),
        require => Package['apache2-mpm-prefork'],
        notify  => Exec["enable-${vhost_domain}-vhost"],
    }

    file { "/var/www/${vhost_root}":
        ensure  => 'directory',
        recurse => true,
        owner   => www-data,
        group   => www-data,
        require => File["/etc/apache2/sites-available/${vhost_domain}.conf"],
        notify  => Service['apache2'],
    }

    file { "/var/www/${vhost_root}/index.html":
        content => template('apache/index.html.erb'),
        owner   => www-data,
        group   => www-data,
        require => File["/var/www/${vhost_root}"],
    }

    exec { "enable-${vhost_domain}-vhost":
        command     => "/usr/sbin/a2ensite ${vhost_domain}.conf",
        require     => File["/etc/apache2/sites-available/${vhost_domain}.conf"],
        refreshonly => true,
        notify      => Service['apache2'],
    }

}

Не буду зупинятись на деталях роботи модуля. Тут ми встановили Apache, додали його в автозавантаження, додали новий віртуальний хост, активували його. Далі ми створили директорію для файлів віртуального хосту та index.html, побудувавши його з темплейту index.html.erb.

Власне для можливості змінювати параметри класу через Foreman, його необхідно робити параметризованим. Для роботи нашого класу apache необхідно йому передати дві змінні vhost_domain та vhost_root, дефолтні значення яких мають бути описані в params.pp класу:

# vim manifests/params.pp

class apache::params {

    $vhost_domain = 'example.com',
    $vhost_root   = 'html',

}

Темплейти index.html.erb та vhost.erb мають наступний вигляд:

# vim templates/index.html.erb

<h1>This is <%= @vhost_domain %> site!</h1>%

# vim templates/vhost.erb

<VirtualHost *:80>
    ServerName <%= @vhost_domain %>
    DocumentRoot /var/www/<%= @vhost_root %>
    ErrorLog /var/log/apache2/<%= @vhost_domain %>-error_log
    CustomLog /var/log/apache2/<%= @vhost_domain %>-access_log common

    <Directory /var/www/<%= @vhost_root %>>
        Allow from all
        Options +Includes +Indexes +FollowSymLinks
        AllowOverride all
    </Directory>
</VirtualHost>

Звісно, я не найкращий автор модулів. Цей скоріше приведено як приклад.

Копіюємо модуль на Foreman в /etc/puppet/environments/production/modules. Тиснемо Import from foreman.me, як і у випадку з ntp модулем і вже на наступній сторінці клікаємо Update:


Після додавання бачимо, що можна змінювати 2 параметра як і було заплановано під час написання модуля.


Редагуємо параметри класу, перейшовши на вкладку Smart Class Parameters:

Ставимо галочку Override для кожного із параметрів і вписуємо свої бажані значення. Для vhost_domain (ServerName для apache2) я обрав myhost.me:


А для vhost_root (DocumentRoot для apache2) я обрав ім'я myhost:


Виходячи з поданого вище модуля для Apache, повний шлях для DocumentRoot буде створений додаванням /var/www/ до змінної vhost_root у vhost.erb темплейті.

Зберігаємо це все і підключаємо до хосту client.me. Переходимо за адресою All Hosts -> Edit (client.me) -> Puppet Classes і додаємо наш новостворений клас apache до Included Classes:


На наступній вкладці Parameters можна побачити які параметри ми перезаписуємо в даному класі для цього оточення:


Ба, більше - тут же можна перезаписати ці ж параметри окремо для самого вузла, а не лише для всього середовища (environment), як ми вище і робили:


Ми додатково перезаписали параметр vhost_root окремо для вузлу client.me. Тож наразі DocumentRoot для  цього хосту буде знаходитись за адресою /var/www/myhost_changed.

Тиснемо Submit і чекаємо виконання класу на client.me. Або ж запускаємо його власноруч:

# puppet agent -tv

Ну і ось результати наших потуг (при умові, що домен myhost.me прив'язаний до 192.168.1.11):


Для зручності, можна об'єднувати класи в конфігураційні групи:


Отже до групу Regular Apache Host ввійшло 2 класи: ntp та apache. Наразі для додавання їх скопом варто додати лише цю конфігураційну групу:



Це далеко не всі можливості Foreman. Як я вже говорив у вступі до статті, його також можна використовувати у якості ресурсу, що може створювати сервери з нуля, використовуючи вже готові API прив'язки до, наприклад, VMWare чи AWS. А конфігурація для цього всього також є прямо в адмінці Foreman:


Посилання:
http://theforeman.org/manuals/1.10/index.html
https://www.digitalocean.com/community/tutorials/how-to-use-foreman-to-manage-puppet-nodes-on-ubuntu-14-04
https://blog.codecentric.de/en/2014/04/foreman-complete-lifecycle-management-tool/
https://prezi.com/heph6y7kzole/introduction-to-foreman/
https://deviantony.wordpress.com/2014/06/21/setup-a-scalable-puppet-environment-with-foreman-on-ubuntu-12-04/
http://www.olindata.com/blog/2014/01/puppet-management-gui-comparison
http://www.unixmen.com/how-to-install-foreman-with-puppet-in-centos-and-ubuntu/
http://www.slideshare.net/tullis/linux-host-orchestration-with-foreman-with-puppet-and-gitlab

Немає коментарів:

Дописати коментар