2011년 5월 27일 금요일

chef (인프라를 코드로 기술하는 방법)

Chef

개요

  • 정의: 인프라를 코드로 기술하는 방법
  • 공식사이트: chef
  • 지식: Unix, Ruby, Vagrant
  • 개념/용어
    • Turorial의 Overview를 보자.
    • workstation: Chef를 사용하는 사용자의 환경
      • knife: 인스톨 command
      • cookbooks: 인프라를 어떻게 할지 chef 코드로 나타냄
      • knife command를 사용해서 Chef Server로 설정을 보낸다.
    • Chef Server
      • cookbooks을 기본으로 해서 Nodes (서버의 구조)를 관리
      • 인프라의 구조를 cookbook으로 각 Nodes를 설정해줌
  • workstation 1대와 Nodes 1개로 해서 개념을 파악해 보자.

workstation을 설정해 보자.

  • ruby를 설치하자.
  • Chef를 설치하자. (OSX)
  • knife-solo를 설치하자
    sudo gem install knife-solo
  • Chef와 knife-sole가 올바르게 설치되었는지 확인하자.
    gem list

    chef (11.14.0.alpha.2)

    knife-solo (0.4.1)
  • knife 설정을 하자.
    knife configure
    기본값으로 입력한다.
    Configuration file written to /Users/mscho/.chef/knife.rb

node를 설정해 보자.

  • VirtualBox
  • Vagrant
  • Box centos64
vagrant init centos64
emacs Vagrantfile
27 config.vm.network “private_network”, ip: “192.168.33.20”
vagrant up
vagrant ssh-config —host hani
Host hani
  HostName 127.0.0.1
  User vagrant
  Port 2222
  UserKnownHostsFile /dev/null
  StrictHostKeyChecking no
  PasswordAuthentication no
  IdentityFile /Users/mscho/.vagrant.d/insecure_private_key
  IdentitiesOnly yes
  LogLevel FATAL
  • ssh 접속설정을 저장하자
    vagrant ssh-config —host hani >> ~/.ssh/config
  • ssh 접속해보자
    ssh hani

Chef repogitory를 만들자.

  • cookbook이 들어있는 곳
  1. chef repogitory (cookbook)을 만들자
  2. node를 Chef에 대응시키자.
  3. Cookbook을 만들자
  4. Cookbook을 node에 반영하자.

1. chef repogitory (cookbook)을 만들자

knife solo init chef-repo
Creating kitchen…
Creating knife.rb in kitchen…
Creating cupboards…
// chef-repo: chef repogitory (cookbook)
  • 여러폴더가 생긴것을 볼수 있다.
  • 이중 site-cookbooks, nodes 폴더를 주로 사용한다.

2. node를 Chef에 대응시키자.

cd chef-repo/
knife solo prepare hani
// hani: ssh로 설정한 가상머신 이름.
Bootstrapping Chef...
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100 15934  100 15934    0     0   1443      0  0:00:11  0:00:11 --:--:--  8137
Downloading Chef 11.14.0.alpha.2 for el...
downloading https://www.opscode.com/chef/metadata?v=11.14.0.alpha.2&prerelease=false&nightlies=false&p=el&pv=6&m=x86_64
  to file /tmp/install.sh.2435/metadata.txt
trying wget...
ERROR 404
Unable to retrieve a valid package!
Please file a bug report at http://tickets.opscode.com
Project: Chef
Component: Packages
Label: Omnibus
Version: 11.14.0.alpha.2

Please detail your operating system type, version and any other relevant details
Metadata URL: https://www.opscode.com/chef/metadata?v=11.14.0.alpha.2&prerelease=false&nightlies=false&p=el&pv=6&m=x86_64
Generating node config 'nodes/hani.json'...

3. Cookbook을 만들자

> knife cookbook create hello -o site-cookbooks/
** Creating cookbook hello
** Creating README for cookbook: hello
** Creating CHANGELOG for cookbook: hello
** Creating metadata for cookbook: hello

4. Cookbook을 node에 반영하자.

cd site-cookbooks/hello/recipes
emacs default.rb
#
# Cookbook Name:: hello
# Recipe:: default
#
# Copyright 2014, YOUR_COMPANY_NAME
#
# All rights reserved - Do Not Redistribute
#
log "hello world"
cd ~/chef-repo/nodes/
emacs hani.json
1{                                                                                                  
2    "run_list":[                                                                                   
3        "recipe[hello]"                                                                            
4    ]                                                                                              
5}
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 1 resources
Recipe: hello::default
  * log[hello world] action write

Chef Client finished, 1 resources updated

chef를 사용해서 vim 패키지를 설치해 보자.

  • vim이 설치되었는지 확인하자.
    ssh hani
    vim
  • 설치가 안된것을 확인했으니 빠져나가자.
    exit
  • site-cookbooks/hello/recipes/default.rb 를 편집하자.
#
# Cookbook Name:: hello
# Recipe:: default
#
# Copyright 2014, YOUR_COMPANY_NAME
#
# All rights reserved - Do Not Redistribute
#
# log "hello world"

package "vim-enhanced" do
  action :install
end
패키지를 설치할때는
  1. package 라고 적고(리소스라고 부른다.)
  2. “vim-enhanced” 패키지명
  3. action : install 동작: 인스톨
  4. end
그리고 나서 knife를 실행하면 된다.
knife solo cook hani
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 1 resources
Recipe: hello::default
  * package[vim-enhanced] action install
    - install version 7.2.411-1.8.el6 of package vim-enhanced

Chef Client finished, 1 resources updated

service 로 iptables

방화벽 설정을 꺼보자.
#
# Cookbook Name:: hello
# Recipe:: default
#
# Copyright 2014, YOUR_COMPANY_NAME
#
# All rights reserved - Do Not Redistribute
#
# log "hello world"

package "vim-enhanced" do
  action :install
end

service "iptables" do
  action :stop
end
설정을 했으니 실행해보자.
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 2 resources
Recipe: hello::default
  * package[vim-enhanced] action install (up to date)
  * service[iptables] action stop
    - stop service service[iptables]

Chef Client finished, 1 resources updated
접속해서 방화벽이 올바르게 되었는지 확인해 보자.
sudo service iptables status
iptables: Firewall is not running.
방화벽을 끄는것과 함께, 서비스를 시작하지 않게 해보자.
[ , ]를 사용해서 연속되게 설정을 할 수 있다.
service "iptables" do
  action [:stop, :disable]
end
실행해 보자.
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 2 resources
Recipe: hello::default
  * package[vim-enhanced] action install (up to date)
  * service[iptables] action stop (up to date)
  * service[iptables] action disable
    - disable service service[iptables]

Chef Client finished, 1 resources updated
방화벽이 꺼진것을 확인할수 있다.

php mtsql-server httpd

php mysql-server http를 설치해보자.
루비 명령이 사용할 수 있으므로 %w{php mysql-server http}를 각각 p라고 선언해서 사용하자.
%w{php mysql-server httpd}.each do |p|
  package p do
    action :install
  end
end

service "httpd" do
  action [:start, :enable]
end
설정된 것을 실행해서 확인해 보자.
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 6 resources
Recipe: hello::default
  * package[vim-enhanced] action install (up to date)
  * service[iptables] action stop (up to date)
  * service[iptables] action disable (up to date)
  * package[php] action install
    - install version 5.3.3-27.el6_5 of package php

  * package[mysql-server] action install
    - install version 5.1.73-3.el6_5 of package mysql-server

  * package[httpd] action install (up to date)
  * service[httpd] action start
    - start service service[httpd]

  * service[httpd] action enable
    - enable service service[httpd]

Chef Client finished, 4 resources updated

template 리소스 를 사용해보자.

템플릿을 사용해서 웹설정, 포트 변경, index.html과 같은 것을 외부에서 변경해 줄 수있다.
index.html을 만들고 이것을 템플릿으로 사용해 보자.
template "index.html" do 
  path "/var/www/html/index.html"
  source "index.html.erb"
  mode 0644
end
팀플릿이 맞게 되었는지 확인해 보자.
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 7 resources
Recipe: hello::default
  * package[vim-enhanced] action install (up to date)
  * service[iptables] action stop (up to date)
  * service[iptables] action disable (up to date)
  * package[php] action install (up to date)
  * package[mysql-server] action install (up to date)
  * package[httpd] action install (up to date)
  * service[httpd] action start (up to date)
  * service[httpd] action enable (up to date)
  * template[index.html] action create
    - create new file /var/www/html/index.html
    - update content in file /var/www/html/index.html from none to 799cf0
        --- /var/www/html/index.html    2014-05-27 07:24:24.864287020 +0000
        +++ /tmp/chef-rendered-template20140527-5056-15jwa06    2014-05-27 07:24:24.866287020 +0000
        @@ -1 +1,4 @@
        +<html>
        +Hello world from chef!!!
        +</html>
    - change mode from '' to '0644'

Chef Client finished, 1 resources updated
  • template에 변수를 사용해 보자.
    • owner 라는 별수를 node에 추가하자.
    • name 도 추가해 놓자.
{
    "owner": {
    "name": "hephaex"
    },
    "run_list":[
    "recipe[hello]"
    ]
}
node에서 json으로 owner와 name을 읽어오자.
<html>
Hello world from chef!!! created by <%= node['owner']['name'] %>.
</html>
직접 template를 바꿀수도 있다.
그전에 플렛폼등을 루비를 이용해서 확인해 보자.
ohai paltform
ohai platform
[
“mac_os_x”
]

아파치 설정을 바꿔보자.

  • 아파치 설정을 복사하자.
    ssh hani
    cp /etc/httpd/conf/httpd.conf /vagrant/
    exit
  • 템플릿으로 저장하자.
    cp httpd.conf chef-repo/site-cookbooks/hello/templates/default/httpd.conf.erb
  • default.rb를 열어서 템플릿을 연결해 주자.
template "httpd.conf" do
  path "/etc/httpd/conf/httpd.conf"
  source "httpd.conf.erb"
end
  • httpd.conf.erb 를 수정하자.
#Listen 12.34.56.78:80
# Listen 80
Listen <%= node['httpd']['port'] %>
  • node를 수정해 보자.
    {
      "httpd": {
      "port": 80
      },
      "owner": {
      "name": "hephaex"
      },
      "run_list":[
      "recipe[hello]"
      ]
    }
    
knife solo cook hani
Running Chef on hani...
Checking Chef version...
Uploading the kitchen...
Generating solo config...
Running Chef...
Starting Chef Client, version 11.8.0
Compiling Cookbooks...
Converging 8 resources
Recipe: hello::default
  * package[vim-enhanced] action install (up to date)
  * service[iptables] action stop (up to date)
  * service[iptables] action disable (up to date)
  * package[php] action install (up to date)
  * package[mysql-server] action install (up to date)
  * package[httpd] action install (up to date)
  * service[httpd] action start (up to date)
  * service[httpd] action enable (up to date)
  * template[index.html] action create
    - update content in file /var/www/html/index.html from 799cf0 to 2a3a4c
        --- /var/www/html/index.html    2014-05-27 07:24:24.866287020 +0000
        +++ /tmp/chef-rendered-template20140527-6604-nbyy2l    2014-05-27 07:58:49.401286974 +0000
        @@ -1,4 +1,6 @@
         <html>
        -Hello world from chef!!!
        +Hello world from chef!!! 
        +centos!
        +created by hephaex.
         </html>

  * template[httpd.conf] action create
    - update content in file /etc/httpd/conf/httpd.conf from beb8a6 to fd4260
        --- /etc/httpd/conf/httpd.conf    2014-03-20 10:17:58.000000000 +0000
        +++ /tmp/chef-rendered-template20140527-6604-1pfwo9v    2014-05-27 07:58:49.448286974 +0000
        @@ -133,8 +133,8 @@
         # prevent Apache from glomming onto all bound IP addresses (0.0.0.0)
         #
         #Listen 12.34.56.78:80
        +# Listen 80
         Listen 80
        -
         #
         # Dynamic Shared Object (DSO) Support
         #

Chef Client finished, 2 resources updated
  • http 설정이 바뀌면 자동으로 재기동하게 해주자.
    cookbook의 template을 바꿔주자.
    template "httpd.conf" do
    path "/etc/httpd/conf/httpd.conf"
    source "httpd.conf.erb"
    notifies :restart, 'service[httpd]'
    mode 0644
    end
    
    node 설정을 바꿔주자.
      "httpd": {
      "port": 8080
      },
    
  • 실행해서 포트 변경과 재기동이 되는지 확인해보자.
    knife solo cook hani
  * template[httpd.conf] action create
    - update content in file /etc/httpd/conf/httpd.conf from fd4260 to 48e804
        --- /etc/httpd/conf/httpd.conf    2014-05-27 07:58:49.448286974 +0000
        +++ /tmp/chef-rendered-template20140527-7022-16luazh    2014-05-27 08:04:57.930286965 +0000
        @@ -134,7 +134,7 @@
         #
         #Listen 12.34.56.78:80
         # Listen 80
        -Listen 80
        +Listen 8080
         #
         # Dynamic Shared Object (DSO) Support
         #

  * service[httpd] action restart
    - restart service service[httpd]

Chef Client finished, 2 resources updated

맺음말

chef를 이용해서 여러대의 서버를 자신의 입맛에 맞게 수정할 수도 있다.
이것을 이용해서 공동된 개발 환경을 만들고 개발자가 그 동일한 환경에서 작업을 한 이후에 서비스를 개시하게 할 수도 있다.