Chef CentOS v11: различия между версиями
Sirmax (обсуждение | вклад) |
Sirmax (обсуждение | вклад) |
||
(не показано 58 промежуточных версий этого же участника) | |||
Строка 1: | Строка 1: | ||
+ | [[Категория:Linux]] |
||
+ | [[Категория:Chef]] |
||
+ | [[Категория:Autodeploy]] |
||
+ | [[Категория:Ruby]] |
||
+ | |||
=Chef сервер под CentOS 6.3= |
=Chef сервер под CentOS 6.3= |
||
<B>Все очень призрачно...</B> |
<B>Все очень призрачно...</B> |
||
Строка 11: | Строка 16: | ||
Я брал здесь: |
Я брал здесь: |
||
<PRE> |
<PRE> |
||
− | + | https://opscode-omnitruck-release.s3.amazonaws.com/el/6/x86_64/chef-server-11.0.4-1.el6.x86_64.rpm |
|
+ | https://opscode-omnitruck-release.s3.amazonaws.com/el/6/x86_64/chef-11.4.0-1.el6.x86_64.rpm |
||
</PRE> |
</PRE> |
||
Но вообще-то узнать последнюю версию можно тут: http://www.opscode.com/chef/install/ |
Но вообще-то узнать последнюю версию можно тут: http://www.opscode.com/chef/install/ |
||
Строка 19: | Строка 25: | ||
<BR> |
<BR> |
||
Немного забегая вперед, вот мой вывод: |
Немного забегая вперед, вот мой вывод: |
||
+ | {{Root|<nowiki>#initctl list |
||
− | <PRE> |
||
− | initctl list |
||
rc stop/waiting |
rc stop/waiting |
||
lxc-sysinit stop/waiting |
lxc-sysinit stop/waiting |
||
Строка 41: | Строка 46: | ||
rcS-sulogin stop/waiting |
rcS-sulogin stop/waiting |
||
serial stop/waiting |
serial stop/waiting |
||
− | </ |
+ | </nowiki>}} |
− | |||
− | |||
− | |||
==Конфигурация== |
==Конфигурация== |
||
Запускаю: |
Запускаю: |
||
+ | {{Root|<nowiki>#chef-server-ctl reconfigure |
||
− | <PRE> |
||
+ | </nowiki>}} |
||
− | chef-server-ctl reconfigure |
||
+ | |||
− | </PRE> |
||
+ | {{Note|"Зависание": |
||
− | У меня на стадии запуска RabbitMQ произошло зависание. Я ре-стартовал контейнер и запустил заново конфигурацию - все прошло успешно. (Рестартовать контейнер это БЫСТРО и удобно - гарантировано убьются все процессы которые хотя бы в теории могут взаимодействовать с chef-server) |
||
+ | У меня на стадии запуска RabbitMQ произошло зависание. Я ре-стартовал контейнер и запустил заново конфигурацию - все прошло успешно. (Рестартовать контейнер это БЫСТРО и удобно - гарантировано убьются все процессы которые хотя бы в теории могут взаимодействовать с chef-server)}} |
||
После завершения длительного процесса у меня запущен весь комплекс сервисов: |
После завершения длительного процесса у меня запущен весь комплекс сервисов: |
||
+ | {{Root|<nowiki># ps -auxfw |
||
− | <PRE> |
||
+ | <skipped> |
||
root 699 0.0 0.0 4136 444 ? Ss 13:47 0:00 runsvdir -P /opt/chef-server/service log: .................................................................................................................................... |
root 699 0.0 0.0 4136 444 ? Ss 13:47 0:00 runsvdir -P /opt/chef-server/service log: .................................................................................................................................... |
||
root 700 0.0 0.0 3984 248 ? Ss 13:47 0:00 \_ runsv rabbitmq |
root 700 0.0 0.0 3984 248 ? Ss 13:47 0:00 \_ runsv rabbitmq |
||
Строка 119: | Строка 123: | ||
496 1576 0.0 0.0 78244 1332 ? S 13:49 0:00 \_ nginx: cache manager process |
496 1576 0.0 0.0 78244 1332 ? S 13:49 0:00 \_ nginx: cache manager process |
||
496 719 0.0 0.0 10876 252 ? S 13:47 0:00 /opt/chef-server/embedded/lib/erlang/erts-5.9.2/bin/epmd -daemon |
496 719 0.0 0.0 10876 252 ? S 13:47 0:00 /opt/chef-server/embedded/lib/erlang/erts-5.9.2/bin/epmd -daemon |
||
+ | </nowiki>}} |
||
− | </PRE> |
||
− | |||
− | |||
− | |||
− | |||
==Базовое тестирование== |
==Базовое тестирование== |
||
+ | {{Root|<nowiki> |
||
− | <PRE> |
||
chef-server-ctl test |
chef-server-ctl test |
||
− | </ |
+ | </nowiki>}} |
+ | |||
Достаточно длительный процесс (по крайне мере на ограниченных ресурсах контейнера)<BR> |
Достаточно длительный процесс (по крайне мере на ограниченных ресурсах контейнера)<BR> |
||
У меня возникли некоторые проблемы (пока я не выявил сказалось ли это на работоспособности сервера) |
У меня возникли некоторые проблемы (пока я не выявил сказалось ли это на работоспособности сервера) |
||
Строка 196: | Строка 197: | ||
==настройка knife== |
==настройка knife== |
||
+ | Для работы с 10-м шефом использовался "нож", в 11 он тоже присутствует |
||
+ | Подкладываю в ~/.chef файлы ключей: |
||
+ | {{Root|<nowiki> |
||
− | scp root@chef-server:/etc/chef-server/admin.pem . |
||
+ | mkdir /root/.chef/ |
||
− | scp root@chef-server:/etc/chef-server/chef-validator.pem . |
||
+ | cp /etc/chef-server/chef-validator.pem ~/.chef/ |
||
+ | cp /etc/chef-server/admin.pem ~/.chef/</nowiki>}} |
||
+ | Запускаем <B>knife configure -i</B> |
||
− | Use knife configure -i to create an initial ~/.chef/knife.rb and new administrative API user for yourself. Use the FQDN of your newly installed Chef Server, with HTTPS. The validation key needs to be copied over from the Chef Server from /etc/chef-server/chef-validator.pem to ~/.chef to use it for automatically bootstrapping nodes with knife bootstrap. |
||
+ | {{Root|<nowiki>#knife configure -i |
||
− | 1 |
||
+ | Overwrite /root/.chef/knife.rb? (Y/N) |
||
+ | I have no idea what to do with |
||
+ | Just say Y or N, please. |
||
+ | Overwrite /root/.chef/knife.rb? (Y/N) Y |
||
+ | Please enter the chef server URL: [http://localhost:4000] https://172.31.0.2:443 |
||
+ | Please enter a name for the new user: [root] |
||
+ | Please enter the existing admin name: [admin] |
||
+ | Please enter the location of the existing admin's private key: [/etc/chef/admin.pem] ~/.chef/admin.pem |
||
+ | Please enter the validation clientname: [chef-validator] |
||
+ | Please enter the location of the validation key: [/etc/chef/validation.pem] ~/.chef/chef-validator.pem |
||
+ | Please enter the path to a chef repository (or leave blank): |
||
+ | Creating initial API user... |
||
+ | Please enter a password for the new user: |
||
+ | Created user[root] |
||
+ | Configuration file written to /root/.chef/knife.rb</nowiki>}} |
||
+ | Обратить внимание - у меня при указании localhost вместо https://172.31.0.2:443 не работал бутстрап |
||
− | |||
+ | Нод пока нет, но все равно проверяю ... |
||
− | % knife configure -i |
||
+ | {{Root|<nowiki>#knife node list</nowiki>}} |
||
− | |||
− | The .chef/knife.rb file should look something like this: |
||
− | |||
− | |||
+ | Конфиг .chef/knife.rb выглядит где-то так: |
||
+ | <PRE> |
||
log_level :info |
log_level :info |
||
log_location STDOUT |
log_location STDOUT |
||
− | node_name ' |
+ | node_name 'root' |
− | client_key '/ |
+ | client_key '/root/.chef/root.pem' |
validation_client_name 'chef-validator' |
validation_client_name 'chef-validator' |
||
− | validation_key '/ |
+ | validation_key '/root/.chef/chef-validator.pem' |
− | chef_server_url 'https:// |
+ | chef_server_url 'https://localhost:443' |
− | syntax_check_cache_path '/ |
+ | syntax_check_cache_path '/root/.chef/syntax_check_cache' |
+ | </PRE> |
||
+ | {{Root|<nowiki>#knife client list |
||
− | Your Chef Server is now ready to use. Test connectivity as your user with knife: |
||
− | |||
− | |||
− | % knife client list |
||
chef-validator |
chef-validator |
||
− | chef-webui |
+ | chef-webui</nowiki>}} |
+ | |||
− | % knife user list |
||
+ | {{Root|<nowiki>#knife user list |
||
admin |
admin |
||
+ | root</nowiki>}} |
||
− | jtimberman |
||
+ | ==chef-server-ctl== |
||
− | In previous versions of Open Source Chef Server, users were API clients. In Chef 11, users are separate entities on the Server. |
||
+ | Управлять сервером теперь тоже по новому. Вобщем, хелп понятный - особо расписывать нечего. chef-server]# chef-server-ctl status |
||
+ | |||
+ | {{Root|#chef-server-ctl status |
||
+ | run: bookshelf: (pid 1226) 9024s; run: log: (pid 1225) 9024s |
||
+ | run: chef-expander: (pid 1162) 9030s; run: log: (pid 1161) 9030s |
||
+ | run: chef-server-webui: (pid 1391) 9002s; run: log: (pid 1390) 9002s |
||
+ | run: chef-solr: (pid 1136) 9031s; run: log: (pid 1135) 9031s |
||
+ | run: erchef: (pid 1578) 8984s; run: log: (pid 1271) 9018s |
||
+ | run: nginx: (pid 1558) 8986s; run: log: (pid 1557) 8986s |
||
+ | run: postgresql: (pid 1036) 9042s; run: log: (pid 1035) 9042s |
||
+ | run: rabbitmq: (pid 702) 9059s; run: log: (pid 701) 9059s |
||
+ | }} |
||
+ | |||
+ | ==Настройка клиентов== |
||
+ | Самый простой способ - это сделать chef bootstrap |
||
+ | Звучит смешно но это так ) |
||
+ | <PRE> |
||
+ | #knife bootstrap 172.31.0.5 --node-name 172.31.0.5 |
||
+ | Bootstrapping Chef on 172.31.0.5 |
||
+ | Failed to authenticate root - trying password auth |
||
+ | </PRE> |
||
+ | |||
+ | После чего на клиенте можно запускать |
||
+ | <PRE> |
||
+ | # chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: [] |
||
+ | Synchronizing Cookbooks: |
||
+ | Compiling Cookbooks... |
||
+ | [2013-02-18T08:03:14-05:00] WARN: Node 172.31.0.5 has an empty run list. |
||
+ | Converging 0 resources |
||
+ | Chef Client finished, 0 resources updated |
||
+ | </PRE> |
||
+ | ==Важно== |
||
+ | Везде используются FQDN потому без записей в в DNS или /etc/hosts не обойтись. |
||
+ | <PRE> |
||
+ | Например когда у меня hostname сервера резолвился в 127.0.0.1 то именно этот адрес передавался в запросах и клиенты пробовали получить с него данные. |
||
+ | Ничего, конечно же, не работало. |
||
+ | |||
+ | Лечить так:<BR> |
||
+ | Было: |
||
+ | <PRE> |
||
+ | 127.0.0.1 localhost centos-chefserver |
||
+ | 172.31.0.2 centos-chefserver |
||
+ | </PRE> |
||
+ | Нужно: |
||
+ | <PRE> |
||
+ | 127.0.0.1 localhost |
||
+ | 172.31.0.2 centos-chefserver |
||
+ | </PRE> |
||
+ | И потом |
||
+ | <PRE> |
||
+ | chef-server-ctl reconfigure |
||
+ | </PRE> |
||
+ | |||
+ | =Поваренные книги и рецепты, роли и вообще конфигурация сервера= |
||
+ | ==cookbook== |
||
+ | Создать поваренную книгу: |
||
+ | <PRE> |
||
+ | #knife cookbook create demo |
||
+ | ** Creating cookbook demo |
||
+ | ** Creating README for cookbook: demo |
||
+ | ** Creating CHANGELOG for cookbook: demo |
||
+ | ** Creating metadata for cookbook: demo |
||
+ | </PRE> |
||
+ | <PRE> |
||
+ | ls -lsa /var/chef/cookbooks/demo/ |
||
+ | total 52 |
||
+ | 4 drwxr-xr-x 10 root root 4096 Фев 18 07:58 . |
||
+ | 4 drwxr-xr-x 4 root root 4096 Фев 18 08:05 .. |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 attributes |
||
+ | 4 -rw-r--r-- 1 root root 406 Фев 18 07:58 CHANGELOG.md |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 definitions |
||
+ | 4 drwxr-xr-x 3 root root 4096 Фев 18 07:58 files |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 libraries |
||
+ | 4 -rw-r--r-- 1 root root 272 Фев 18 07:58 metadata.rb |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 providers |
||
+ | 4 -rw-r--r-- 1 root root 1431 Фев 18 07:58 README.md |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 08:04 recipes |
||
+ | 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 resources |
||
+ | 4 drwxr-xr-x 3 root root 4096 Фев 18 07:58 templates |
||
+ | </PRE> |
||
+ | |||
+ | <PRE> |
||
+ | cat /var/chef/cookbooks/demo/recipes/default.rb |
||
+ | |||
+ | package "ntp" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | |||
+ | package "mc" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | service "ntpd" do |
||
+ | supports :status => true, :restart => true, :reload => true |
||
+ | action [ :enable, :start ] |
||
+ | end |
||
+ | |||
+ | |||
+ | |||
+ | </PRE> |
||
+ | |||
+ | <PRE> |
||
+ | # knife cookbook upload demo |
||
+ | Uploading demo [0.1.0] |
||
+ | Uploaded 1 cookbook. |
||
+ | </PRE> |
||
+ | |||
+ | ==role== |
||
+ | <PRE> |
||
+ | EDITOR=mcedit knife role create demo_role |
||
+ | </PRE> |
||
+ | <PRE> |
||
+ | { |
||
+ | "name": "demo_role", |
||
+ | "description": "", |
||
+ | "json_class": "Chef::Role", |
||
+ | "default_attributes": { |
||
+ | }, |
||
+ | "override_attributes": { |
||
+ | }, |
||
+ | "chef_type": "role", |
||
+ | "run_list": [ |
||
+ | |||
+ | ], |
||
+ | "env_run_lists": { |
||
+ | } |
||
+ | } |
||
+ | </PRE> |
||
+ | Добавить наш кукбук: |
||
+ | <PRE> |
||
+ | { |
||
+ | "name": "demo_role", |
||
+ | "description": "", |
||
+ | "json_class": "Chef::Role", |
||
+ | "default_attributes": { |
||
+ | }, |
||
+ | "override_attributes": { |
||
+ | }, |
||
+ | "chef_type": "role", |
||
+ | "run_list": [ |
||
+ | "recipe[demo]" |
||
+ | ], |
||
+ | "env_run_lists": { |
||
+ | } |
||
+ | } |
||
+ | </PRE> |
||
+ | |||
+ | ==run_list== |
||
+ | <PRE> |
||
+ | knife node run_list 172.31.0.5 add role[demo_role] |
||
+ | 172.31.0.5: |
||
+ | run_list: role[demo_role] |
||
+ | </PRE> |
||
+ | |||
+ | Если есть роль но нет рецептов, это не ошибка |
||
+ | <PRE> |
||
+ | chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: [] |
||
+ | Synchronizing Cookbooks: |
||
+ | Compiling Cookbooks... |
||
+ | Converging 0 resources |
||
+ | Chef Client finished, 0 resources updated |
||
+ | </PRE> |
||
+ | |||
+ | |||
+ | После добавления нашего рецепта к роли: |
||
+ | |||
+ | <PRE> |
||
+ | chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: ["demo"] |
||
+ | Synchronizing Cookbooks: |
||
+ | - demo |
||
+ | Compiling Cookbooks... |
||
+ | Converging 3 resources |
||
+ | Recipe: demo::default |
||
+ | * package[ntp] action install |
||
+ | - install version 4.2.4p8-2.el6.centos of package ntp |
||
+ | |||
+ | * package[mc] action install (up to date) |
||
+ | * service[ntpd] action enable |
||
+ | - enable service service[ntpd] |
||
+ | |||
+ | * service[ntpd] action start |
||
+ | - start service service[ntpd] |
||
+ | |||
+ | Chef Client finished, 3 resources updated |
||
+ | </PRE> |
||
+ | Проверяем: |
||
+ | <PRE> |
||
+ | # ps -auxfw |
||
+ | USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND |
||
+ | root 1 0.0 0.0 116136 1628 ? Ss 07:49 0:00 /sbin/init |
||
+ | root 8 0.0 0.0 52688 1676 ? Ss 07:49 0:00 login -- root |
||
+ | root 209 0.0 0.0 11480 1776 console Ss+ 07:49 0:00 \_ -bash |
||
+ | root 165 0.0 0.0 245088 1352 ? Sl 07:49 0:00 /sbin/rsyslogd -i /var/run/syslogd.pid -c 5 |
||
+ | root 201 0.0 0.0 4108 588 tty1 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty1 |
||
+ | root 203 0.0 0.0 4108 584 tty2 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty2 |
||
+ | root 205 0.0 0.0 4108 584 tty3 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty3 |
||
+ | root 207 0.0 0.0 4108 588 tty4 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty4 |
||
+ | root 265 0.0 0.0 64120 1168 ? Ss 07:55 0:00 /usr/sbin/sshd |
||
+ | root 875 0.0 0.0 91712 3908 ? Ss 08:22 0:00 \_ sshd: root@pts/0 |
||
+ | root 877 0.0 0.0 108344 1896 pts/0 Ss 08:22 0:00 \_ -bash |
||
+ | root 2102 0.0 0.0 110196 1064 pts/0 R+ 11:01 0:00 \_ ps -auxfw |
||
+ | ntp 2099 0.0 0.0 30208 1612 ? Ss 09:15 0:00 ntpd -u ntp:ntp -p /var/run/ntpd.pid -g |
||
+ | </PRE> |
||
+ | |||
+ | =Особенности - то чего нет в puppet= |
||
+ | ==Поиск== |
||
+ | <PRE> |
||
+ | knife search node "role:demo_role" |
||
+ | </PRE> |
||
+ | <PRE> |
||
+ | knife node show 172.31.0.5 -Fj |
||
+ | { |
||
+ | "name": "172.31.0.5", |
||
+ | "chef_environment": "_default", |
||
+ | "run_list": [ |
||
+ | "role[demo_role]" |
||
+ | ], |
||
+ | "normal": { |
||
+ | "tags": [ |
||
+ | |||
+ | ] |
||
+ | } |
||
+ | } |
||
+ | </PRE> |
||
+ | |||
+ | ==Переменные (например состояние ноды)== |
||
+ | ===рецепт=== |
||
+ | приведем рецепт к такому виду: |
||
+ | <PRE> |
||
+ | package "ntp" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | |||
+ | package "mc" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | service "ntpd" do |
||
+ | supports :status => true, :restart => true, :reload => true |
||
+ | action [ :enable, :start ] |
||
+ | end |
||
+ | |||
+ | #puts node.to_s |
||
+ | node.set[:demo][:demo_variable]='text' |
||
+ | node.save |
||
+ | </PRE> |
||
+ | |||
+ | Запустим его: |
||
+ | <PRE> |
||
+ | chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: ["demo"] |
||
+ | Synchronizing Cookbooks: |
||
+ | - demo |
||
+ | Compiling Cookbooks... |
||
+ | Converging 3 resources |
||
+ | Recipe: demo::default |
||
+ | * package[ntp] action install (up to date) |
||
+ | * package[mc] action install (up to date) |
||
+ | * service[ntpd] action enable (up to date) |
||
+ | * service[ntpd] action start (up to date) |
||
+ | Chef Client finished, 0 resources updated |
||
+ | </PRE> |
||
+ | И теперь мы можем наблюдать переменную в св-вах ноды. |
||
+ | <PRE> |
||
+ | knife node show 172.31.0.5 -Fj |
||
+ | { |
||
+ | "name": "172.31.0.5", |
||
+ | "chef_environment": "_default", |
||
+ | "run_list": [ |
||
+ | "role[demo_role]" |
||
+ | ], |
||
+ | "normal": { |
||
+ | "tags": [ |
||
+ | |||
+ | ], |
||
+ | "demo": { |
||
+ | "demo_variable": "text" |
||
+ | } |
||
+ | } |
||
+ | } |
||
+ | </PRE> |
||
+ | |||
+ | |||
+ | |||
+ | Для чего это нужно? Например для вот таких конструкций: |
||
+ | <PRE> |
||
+ | puts node.to_s |
||
+ | #node.set[:demo][:demo_variable]='text' |
||
+ | #node.save |
||
+ | puts node[:demo][:demo_variable].to_s |
||
+ | |||
+ | if node[:demo][:demo_variable].to_s == "test" |
||
+ | Chef::Log.info("OK") |
||
+ | else |
||
+ | Chef::Log.info("node[:demo][:demo_variable] = "+node[:demo][:demo_variable].to_s) |
||
+ | end |
||
+ | </PRE> |
||
+ | "если перемення установлен действие А, если нет Б". Забавно?) |
||
+ | |||
+ | |||
+ | ==Боевой пример - "кластер"== |
||
+ | Задача - установить 3 ноды, на ноде 1 <B>СТРОГО ПОСЛЕ ЗАВЕРШЕНИЯ УСТАНОВКЕ НА ВСЕХ НОДАХ</B> сделать набор post-install шагов. |
||
+ | |||
+ | ===Определить параметры кластера=== |
||
+ | Это живой пример, потому определяю параметры так как я это делал на живом кластеер |
||
+ | |||
+ | ===Рецепт=== |
||
+ | /var/chef/cookbooks/demo/attributes/default.rb - файл с пре-определнными атрибутами. У нас всего один атрибут - ip address мастер-ноды |
||
+ | |||
+ | <PRE> |
||
+ | set[:demo][:master_node] = "172.31.0.5" |
||
+ | </PRE> |
||
+ | Рецепт приводим к такому виду: |
||
+ | <PRE> |
||
+ | puts "===="+node[:demo][:master_node].to_s+"===" |
||
+ | puts "===="+node[:ipaddress].to_s+"===" |
||
+ | |||
+ | |||
+ | if node[:demo][:master_node].to_s == node[:ipaddress].to_s |
||
+ | puts "Master detected" |
||
+ | |||
+ | package "ntp" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | |||
+ | package "mc" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | service "ntpd" do |
||
+ | supports :status => true, :restart => true, :reload => true |
||
+ | action [ :enable, :start ] |
||
+ | end |
||
+ | puts "=== Master node is installed ===" |
||
+ | node.set[:demo][:is_installed]=1 |
||
+ | node.save |
||
+ | else |
||
+ | |||
+ | package "httpd" do |
||
+ | action :install |
||
+ | provider Chef::Provider::Package::Yum |
||
+ | end |
||
+ | |||
+ | service "httpd" do |
||
+ | supports :status => true, :restart => true, :reload => true |
||
+ | action [ :enable, :start ] |
||
+ | end |
||
+ | puts "=== Slave node is installed ===" |
||
+ | node.set[:demo][:is_installed]=1 |
||
+ | node.save |
||
+ | end |
||
+ | |||
+ | </PRE> |
||
+ | Этот код следует читать примерно так |
||
+ | * Если нода - мастре - то установить один паке (ntp) и выставить переменную "установка сделана" |
||
+ | * если нода - слейв то совсем другое ПО но так же поднять флаг "установлено" |
||
+ | * выводить на экран что-то вроде дебага что бы было ясно по какой из веток двигается процесс |
||
+ | |||
+ | Проверяем: |
||
+ | ====нода 1 (мастрер)==== |
||
+ | <PRE> |
||
+ | chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: ["demo"] |
||
+ | Synchronizing Cookbooks: |
||
+ | - demo |
||
+ | Compiling Cookbooks... |
||
+ | ====172.31.0.5=== |
||
+ | ====172.31.0.5=== |
||
+ | Master detected |
||
+ | === Master node is installed === |
||
+ | Converging 3 resources |
||
+ | Recipe: demo::default |
||
+ | * package[ntp] action install (up to date) |
||
+ | * package[mc] action install (up to date) |
||
+ | * service[ntpd] action enable (up to date) |
||
+ | * service[ntpd] action start (up to date) |
||
+ | Chef Client finished, 0 resources updated |
||
+ | </PRE> |
||
+ | |||
+ | ====нода 2 (слейв)==== |
||
+ | Не забываем добавить ноде роль: |
||
+ | <PRE> |
||
+ | knife node run_list 172.31.0.3 add role[demo_role] |
||
+ | </PRE> |
||
+ | |||
+ | |||
+ | <PRE> |
||
+ | chef-client |
||
+ | Starting Chef Client, version 11.4.0 |
||
+ | resolving cookbooks for run list: ["demo"] |
||
+ | Synchronizing Cookbooks: |
||
+ | - demo |
||
+ | Compiling Cookbooks... |
||
+ | ====172.31.0.5=== |
||
+ | ====172.31.0.3=== |
||
+ | Slave node detected |
||
+ | === Slave node is installed === |
||
+ | Converging 2 resources |
||
+ | Recipe: demo::default |
||
+ | * package[httpd] action install |
||
+ | - install version 2.2.15-15.el6.centos.1 of package httpd |
||
+ | |||
+ | * service[httpd] action enable |
||
+ | - enable service service[httpd] |
||
+ | |||
+ | * service[httpd] action start |
||
+ | - start service service[httpd] |
||
+ | |||
+ | Chef Client finished, 3 resources updated |
||
+ | </PRE> |
||
+ | Как видим, поставился совсем другой набор софта! |
||
+ | <PRE> |
||
+ | ps -auxfw |
||
+ | USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND |
||
+ | <skipped> |
||
+ | root 2313 0.0 0.0 173524 3764 ? Ss 12:49 0:00 /usr/sbin/httpd |
||
+ | apache 2315 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2316 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2317 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2318 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2319 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2320 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2321 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | apache 2322 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd |
||
+ | </PRE> |
||
+ | |||
+ | ===рабочий кусок кода для нашего примера=== |
||
+ | <PRE> |
||
+ | # Выставить флаг готовности |
||
+ | node.set[:demo][:post_install]=1 |
||
+ | node.save |
||
+ | |||
+ | puts "==nodes list==" |
||
+ | demo_nodes=search(:node, "(role:demo_role OR roles:demo_role)") |
||
+ | # |
||
+ | |||
+ | demo_nodes.each do |demo_node| |
||
+ | puts demo_node[:ipaddress].to_s+"___"+demo_node.to_s |
||
+ | |||
+ | # проверить есть ли у ноды атрибуты вообще на случай если на ней ни разу не запускался chef-client |
||
+ | if demo_node.attribute?('demo') |
||
+ | |||
+ | # если мастер: |
||
+ | if demo_node[:demo][:master_node].to_s == demo_node[:ipaddress].to_s |
||
+ | puts "is installed ( master) = "+demo_node[:demo][:is_installed].to_s |
||
+ | else |
||
+ | puts "is installed ( slave) = "+demo_node[:demo][:is_installed].to_s |
||
+ | end |
||
+ | puts "Check [:is_installed] variable:"+demo_node[:demo][:is_installed].to_s |
||
+ | if demo_node[:demo][:is_installed] != 1 |
||
+ | puts "node "+ demo_node[:ipaddress].to_s+" is not ready" |
||
+ | node.set[:demo][:post_install]=0 |
||
+ | node.save |
||
+ | end |
||
+ | else |
||
+ | # эта секция отработает если есть хотя бы одна нода которая на сервере указана как demo на самом деле не запускала клиента |
||
+ | puts "at least one node is not configured! "+demo_node[:ipaddress] |
||
+ | node.set[:demo][:post_install]=0 |
||
+ | node.save |
||
+ | end |
||
+ | end |
||
+ | |||
+ | if node[:demo][:post_install] == 1 |
||
+ | if node[:demo][:master_node].to_s == node[:ipaddress].to_s |
||
+ | puts "Do post-install for master" |
||
+ | else |
||
+ | puts "Do post-install for slave" |
||
+ | end |
||
+ | else |
||
+ | puts "not ready for post-install" |
||
+ | end |
||
+ | </PRE> |
||
+ | Логика работы такая |
||
+ | * Проверить есть ли demo_node.attribute?('demo'). его не будет если ноде прописана роль демо, но реально chef-client еще ни разу не запускался. |
||
+ | ** если атрибута нет - вывод однозначен, кластер не готов к Post-Install |
||
+ | ** если атрибут есть - дополнительные проверки |
||
+ | * для каждой ноды выполнить проверку demo_node[:demo][:is_installed] != 1. Если хотя бы одна нода не имеет атрибута is_installed==1 то установить атрибут post_install]=0 |
||
+ | В результате исполнения этого кода мы можем точно знать - на какой стадии установки у нас находится кластер и предпринимать действия на основе этого знанеия. |
||
− | The chef-server-ctl command is used on the Chef Server system for management. It has built-in help (-h) that will display the various sub-commands. |
Текущая версия на 16:28, 28 февраля 2013
Chef сервер под CentOS 6.3
Все очень призрачно...
За пару месяцев что я работаю с шефом произошли заметные изменения в процедуре установки. Точнее, новая процедура отличается от старой практически на 100%.
Я делаю установку внутри линукс-контейнера, потому я допускаю что есть отличия от установки на "нормальную" систему.
Скачать
Я брал здесь:
https://opscode-omnitruck-release.s3.amazonaws.com/el/6/x86_64/chef-server-11.0.4-1.el6.x86_64.rpm https://opscode-omnitruck-release.s3.amazonaws.com/el/6/x86_64/chef-11.4.0-1.el6.x86_64.rpm
Но вообще-то узнать последнюю версию можно тут: http://www.opscode.com/chef/install/
Мне не очень нравится идея комбайна - эта РПМка тянет внутри себя кучу всего, включая Postgress, RabbitMQ и т.д.
Управляется все через новый механизм initctl
Немного забегая вперед, вот мой вывод:
Конфигурация
Запускаю:
После завершения длительного процесса у меня запущен весь комплекс сервисов:
Базовое тестирование
Достаточно длительный процесс (по крайне мере на ограниченных ресурсах контейнера)
У меня возникли некоторые проблемы (пока я не выявил сказалось ли это на работоспособности сервера)
Search API endpoint /search/environment GET when searching for a single environment by name should have more than just the target of our environment search on the system should return status code 200 and a single environment POST targeted toward many environments with body of {"possibly_nested"=>["default_attributes", "top", "middle", "bottom"], "the_name"=>["name"], "not_found"=>["foo", "bar", "baz", "totally_not_a_real_field"], "empty"=>[]} should succeed, and return multiple environments (FAILED - 1) /search/node GET when searching for a single node by name should have more than just the target of our node search on the system should return status code 200 and a single node POST
Failures: 1) Search API endpoint /search/environment POST targeted toward many environments with body of {"possibly_nested"=>["default_attributes", "top", "middle", "bottom"], "the_name"=>["name"], "not_found"=>["foo", "bar", "baz", "totally_not_a_real_field"], "empty"=>[]} should succeed, and return multiple environments Failure/Error: r.should look_like search_success_response 'total' should match '6', but we got '7' instead. # ./lib/pedant/rspec/search_util.rb:99:in `block (2 levels) in performing_a_search' # ./lib/pedant/rspec/search_util.rb:670:in `with_search_polling' # ./lib/pedant/rspec/search_util.rb:86:in `block in performing_a_search' Finished in 5 minutes 43.13 seconds 70 examples, 1 failure Failed examples: rspec ./lib/pedant/rspec/search_util.rb:85 # Search API endpoint /search/environment POST targeted toward many environments with body of {"possibly_nested"=>["default_attributes", "top", "middle", "bottom"], "the_name"=>["name"], "not_found"=>["foo", "bar", "baz", "totally_not_a_real_field"], "empty"=>[]} should succeed, and return multiple environments
Если я понимаю правильно - ответ содержит 7 результатов вместо ожидаемых 6 но в json ниже я не могу найти ни 6 ни 7 атрибутов. Тут есть неясность.
{ "possibly_nested"=> [ "default_attributes", "top", "middle", "bottom" ], "the_name"=> [ "name" ], "not_found"=> [ "foo", "bar", "baz", "totally_not_a_real_field" ], "empty"=> [ ] }
настройка knife
Для работы с 10-м шефом использовался "нож", в 11 он тоже присутствует Подкладываю в ~/.chef файлы ключей:
Запускаем knife configure -i
Обратить внимание - у меня при указании localhost вместо https://172.31.0.2:443 не работал бутстрап
Нод пока нет, но все равно проверяю ...
Конфиг .chef/knife.rb выглядит где-то так:
log_level :info log_location STDOUT node_name 'root' client_key '/root/.chef/root.pem' validation_client_name 'chef-validator' validation_key '/root/.chef/chef-validator.pem' chef_server_url 'https://localhost:443' syntax_check_cache_path '/root/.chef/syntax_check_cache'
chef-server-ctl
Управлять сервером теперь тоже по новому. Вобщем, хелп понятный - особо расписывать нечего. chef-server]# chef-server-ctl status
run: bookshelf: (pid 1226) 9024s; run: log: (pid 1225) 9024s run: chef-expander: (pid 1162) 9030s; run: log: (pid 1161) 9030s run: chef-server-webui: (pid 1391) 9002s; run: log: (pid 1390) 9002s run: chef-solr: (pid 1136) 9031s; run: log: (pid 1135) 9031s run: erchef: (pid 1578) 8984s; run: log: (pid 1271) 9018s run: nginx: (pid 1558) 8986s; run: log: (pid 1557) 8986s run: postgresql: (pid 1036) 9042s; run: log: (pid 1035) 9042s run: rabbitmq: (pid 702) 9059s; run: log: (pid 701) 9059s
Настройка клиентов
Самый простой способ - это сделать chef bootstrap Звучит смешно но это так )
#knife bootstrap 172.31.0.5 --node-name 172.31.0.5 Bootstrapping Chef on 172.31.0.5 Failed to authenticate root - trying password auth
После чего на клиенте можно запускать
# chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: [] Synchronizing Cookbooks: Compiling Cookbooks... [2013-02-18T08:03:14-05:00] WARN: Node 172.31.0.5 has an empty run list. Converging 0 resources Chef Client finished, 0 resources updated
Важно
Везде используются FQDN потому без записей в в DNS или /etc/hosts не обойтись.
Например когда у меня hostname сервера резолвился в 127.0.0.1 то именно этот адрес передавался в запросах и клиенты пробовали получить с него данные. Ничего, конечно же, не работало. Лечить так:<BR> Было: <PRE> 127.0.0.1 localhost centos-chefserver 172.31.0.2 centos-chefserver
Нужно:
127.0.0.1 localhost 172.31.0.2 centos-chefserver
И потом
chef-server-ctl reconfigure
Поваренные книги и рецепты, роли и вообще конфигурация сервера
cookbook
Создать поваренную книгу:
#knife cookbook create demo ** Creating cookbook demo ** Creating README for cookbook: demo ** Creating CHANGELOG for cookbook: demo ** Creating metadata for cookbook: demo
ls -lsa /var/chef/cookbooks/demo/ total 52 4 drwxr-xr-x 10 root root 4096 Фев 18 07:58 . 4 drwxr-xr-x 4 root root 4096 Фев 18 08:05 .. 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 attributes 4 -rw-r--r-- 1 root root 406 Фев 18 07:58 CHANGELOG.md 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 definitions 4 drwxr-xr-x 3 root root 4096 Фев 18 07:58 files 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 libraries 4 -rw-r--r-- 1 root root 272 Фев 18 07:58 metadata.rb 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 providers 4 -rw-r--r-- 1 root root 1431 Фев 18 07:58 README.md 4 drwxr-xr-x 2 root root 4096 Фев 18 08:04 recipes 4 drwxr-xr-x 2 root root 4096 Фев 18 07:58 resources 4 drwxr-xr-x 3 root root 4096 Фев 18 07:58 templates
cat /var/chef/cookbooks/demo/recipes/default.rb package "ntp" do action :install provider Chef::Provider::Package::Yum end package "mc" do action :install provider Chef::Provider::Package::Yum end service "ntpd" do supports :status => true, :restart => true, :reload => true action [ :enable, :start ] end
# knife cookbook upload demo Uploading demo [0.1.0] Uploaded 1 cookbook.
role
EDITOR=mcedit knife role create demo_role
{ "name": "demo_role", "description": "", "json_class": "Chef::Role", "default_attributes": { }, "override_attributes": { }, "chef_type": "role", "run_list": [ ], "env_run_lists": { } }
Добавить наш кукбук:
{ "name": "demo_role", "description": "", "json_class": "Chef::Role", "default_attributes": { }, "override_attributes": { }, "chef_type": "role", "run_list": [ "recipe[demo]" ], "env_run_lists": { } }
run_list
knife node run_list 172.31.0.5 add role[demo_role] 172.31.0.5: run_list: role[demo_role]
Если есть роль но нет рецептов, это не ошибка
chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: [] Synchronizing Cookbooks: Compiling Cookbooks... Converging 0 resources Chef Client finished, 0 resources updated
После добавления нашего рецепта к роли:
chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: ["demo"] Synchronizing Cookbooks: - demo Compiling Cookbooks... Converging 3 resources Recipe: demo::default * package[ntp] action install - install version 4.2.4p8-2.el6.centos of package ntp * package[mc] action install (up to date) * service[ntpd] action enable - enable service service[ntpd] * service[ntpd] action start - start service service[ntpd] Chef Client finished, 3 resources updated
Проверяем:
# ps -auxfw USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND root 1 0.0 0.0 116136 1628 ? Ss 07:49 0:00 /sbin/init root 8 0.0 0.0 52688 1676 ? Ss 07:49 0:00 login -- root root 209 0.0 0.0 11480 1776 console Ss+ 07:49 0:00 \_ -bash root 165 0.0 0.0 245088 1352 ? Sl 07:49 0:00 /sbin/rsyslogd -i /var/run/syslogd.pid -c 5 root 201 0.0 0.0 4108 588 tty1 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty1 root 203 0.0 0.0 4108 584 tty2 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty2 root 205 0.0 0.0 4108 584 tty3 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty3 root 207 0.0 0.0 4108 588 tty4 Ss+ 07:49 0:00 /sbin/mingetty /dev/tty4 root 265 0.0 0.0 64120 1168 ? Ss 07:55 0:00 /usr/sbin/sshd root 875 0.0 0.0 91712 3908 ? Ss 08:22 0:00 \_ sshd: root@pts/0 root 877 0.0 0.0 108344 1896 pts/0 Ss 08:22 0:00 \_ -bash root 2102 0.0 0.0 110196 1064 pts/0 R+ 11:01 0:00 \_ ps -auxfw ntp 2099 0.0 0.0 30208 1612 ? Ss 09:15 0:00 ntpd -u ntp:ntp -p /var/run/ntpd.pid -g
Особенности - то чего нет в puppet
Поиск
knife search node "role:demo_role"
knife node show 172.31.0.5 -Fj { "name": "172.31.0.5", "chef_environment": "_default", "run_list": [ "role[demo_role]" ], "normal": { "tags": [ ] } }
Переменные (например состояние ноды)
рецепт
приведем рецепт к такому виду:
package "ntp" do action :install provider Chef::Provider::Package::Yum end package "mc" do action :install provider Chef::Provider::Package::Yum end service "ntpd" do supports :status => true, :restart => true, :reload => true action [ :enable, :start ] end #puts node.to_s node.set[:demo][:demo_variable]='text' node.save
Запустим его:
chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: ["demo"] Synchronizing Cookbooks: - demo Compiling Cookbooks... Converging 3 resources Recipe: demo::default * package[ntp] action install (up to date) * package[mc] action install (up to date) * service[ntpd] action enable (up to date) * service[ntpd] action start (up to date) Chef Client finished, 0 resources updated
И теперь мы можем наблюдать переменную в св-вах ноды.
knife node show 172.31.0.5 -Fj { "name": "172.31.0.5", "chef_environment": "_default", "run_list": [ "role[demo_role]" ], "normal": { "tags": [ ], "demo": { "demo_variable": "text" } } }
Для чего это нужно? Например для вот таких конструкций:
puts node.to_s #node.set[:demo][:demo_variable]='text' #node.save puts node[:demo][:demo_variable].to_s if node[:demo][:demo_variable].to_s == "test" Chef::Log.info("OK") else Chef::Log.info("node[:demo][:demo_variable] = "+node[:demo][:demo_variable].to_s) end
"если перемення установлен действие А, если нет Б". Забавно?)
Боевой пример - "кластер"
Задача - установить 3 ноды, на ноде 1 СТРОГО ПОСЛЕ ЗАВЕРШЕНИЯ УСТАНОВКЕ НА ВСЕХ НОДАХ сделать набор post-install шагов.
Определить параметры кластера
Это живой пример, потому определяю параметры так как я это делал на живом кластеер
Рецепт
/var/chef/cookbooks/demo/attributes/default.rb - файл с пре-определнными атрибутами. У нас всего один атрибут - ip address мастер-ноды
set[:demo][:master_node] = "172.31.0.5"
Рецепт приводим к такому виду:
puts "===="+node[:demo][:master_node].to_s+"===" puts "===="+node[:ipaddress].to_s+"===" if node[:demo][:master_node].to_s == node[:ipaddress].to_s puts "Master detected" package "ntp" do action :install provider Chef::Provider::Package::Yum end package "mc" do action :install provider Chef::Provider::Package::Yum end service "ntpd" do supports :status => true, :restart => true, :reload => true action [ :enable, :start ] end puts "=== Master node is installed ===" node.set[:demo][:is_installed]=1 node.save else package "httpd" do action :install provider Chef::Provider::Package::Yum end service "httpd" do supports :status => true, :restart => true, :reload => true action [ :enable, :start ] end puts "=== Slave node is installed ===" node.set[:demo][:is_installed]=1 node.save end
Этот код следует читать примерно так
- Если нода - мастре - то установить один паке (ntp) и выставить переменную "установка сделана"
- если нода - слейв то совсем другое ПО но так же поднять флаг "установлено"
- выводить на экран что-то вроде дебага что бы было ясно по какой из веток двигается процесс
Проверяем:
нода 1 (мастрер)
chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: ["demo"] Synchronizing Cookbooks: - demo Compiling Cookbooks... ====172.31.0.5=== ====172.31.0.5=== Master detected === Master node is installed === Converging 3 resources Recipe: demo::default * package[ntp] action install (up to date) * package[mc] action install (up to date) * service[ntpd] action enable (up to date) * service[ntpd] action start (up to date) Chef Client finished, 0 resources updated
нода 2 (слейв)
Не забываем добавить ноде роль:
knife node run_list 172.31.0.3 add role[demo_role]
chef-client Starting Chef Client, version 11.4.0 resolving cookbooks for run list: ["demo"] Synchronizing Cookbooks: - demo Compiling Cookbooks... ====172.31.0.5=== ====172.31.0.3=== Slave node detected === Slave node is installed === Converging 2 resources Recipe: demo::default * package[httpd] action install - install version 2.2.15-15.el6.centos.1 of package httpd * service[httpd] action enable - enable service service[httpd] * service[httpd] action start - start service service[httpd] Chef Client finished, 3 resources updated
Как видим, поставился совсем другой набор софта!
ps -auxfw USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND <skipped> root 2313 0.0 0.0 173524 3764 ? Ss 12:49 0:00 /usr/sbin/httpd apache 2315 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2316 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2317 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2318 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2319 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2320 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2321 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd apache 2322 0.0 0.0 173524 2240 ? S 12:49 0:00 \_ /usr/sbin/httpd
рабочий кусок кода для нашего примера
# Выставить флаг готовности node.set[:demo][:post_install]=1 node.save puts "==nodes list==" demo_nodes=search(:node, "(role:demo_role OR roles:demo_role)") # demo_nodes.each do |demo_node| puts demo_node[:ipaddress].to_s+"___"+demo_node.to_s # проверить есть ли у ноды атрибуты вообще на случай если на ней ни разу не запускался chef-client if demo_node.attribute?('demo') # если мастер: if demo_node[:demo][:master_node].to_s == demo_node[:ipaddress].to_s puts "is installed ( master) = "+demo_node[:demo][:is_installed].to_s else puts "is installed ( slave) = "+demo_node[:demo][:is_installed].to_s end puts "Check [:is_installed] variable:"+demo_node[:demo][:is_installed].to_s if demo_node[:demo][:is_installed] != 1 puts "node "+ demo_node[:ipaddress].to_s+" is not ready" node.set[:demo][:post_install]=0 node.save end else # эта секция отработает если есть хотя бы одна нода которая на сервере указана как demo на самом деле не запускала клиента puts "at least one node is not configured! "+demo_node[:ipaddress] node.set[:demo][:post_install]=0 node.save end end if node[:demo][:post_install] == 1 if node[:demo][:master_node].to_s == node[:ipaddress].to_s puts "Do post-install for master" else puts "Do post-install for slave" end else puts "not ready for post-install" end
Логика работы такая
- Проверить есть ли demo_node.attribute?('demo'). его не будет если ноде прописана роль демо, но реально chef-client еще ни разу не запускался.
- если атрибута нет - вывод однозначен, кластер не готов к Post-Install
- если атрибут есть - дополнительные проверки
- для каждой ноды выполнить проверку demo_node[:demo][:is_installed] != 1. Если хотя бы одна нода не имеет атрибута is_installed==1 то установить атрибут post_install]=0
В результате исполнения этого кода мы можем точно знать - на какой стадии установки у нас находится кластер и предпринимать действия на основе этого знанеия.