跳转至

第十二节 角色

  • 创建一个网页服务器角色
  • 属性和角色
  • 角色和搜索
  • 角色菜谱

角色可以帮助我们将基础架构内的不同服务分类如图

Alt Image Text

角色可以用来表示基础架构内的不同服务器:

  • 负载均衡服务器
  • 应用程序服务器
  • 数据库组存
  • 数据库
  • 监视服务器

可以通过角色方便地指定配方单和属性,将某台服务器配置成理想的服务器。通过使用角色可以同时将许多节点配置成某种服务器而无需重复工作

除了这些明显的角色(比如”网页服务器“)以外,将些常用的功能集合在一起作为一个角色也是很常见的。最明显的例子是创建一个包含墓础架构内银一个节点都需要 行的配方单基本角色,然后让每个其他角色包含这个基本角色。

1、创建一个网页服务器角色

我们可以使用和创建数据包的同样方法创建角色。默认清况下,我们将角色文件保存在chef-playground目录下的roles目录。

$ cd chap10/chef-playground
$  chef-zero --port 9501
>> Starting Chef Zero (v14.0.13)...
>> WEBrick (v1.5.0) on Rack (v2.0.7) is listening at http://127.0.0.1:9501
>> Press CTRL+C to stop
$ cd chef-playground

$ knife upload nodes
Created nodes/snowman.json
Created nodes/susu.json
Created nodes/atwood.json
$ mkdir roles

我们将创建一个.json文件来表示角色的数据。

一个最基本的角色包含name:(名字)、 description:(描述)和run_list(运行清单)。

一个角色可以用来把一个很长的配方单清单组织成一个单位。下面我们使用示例14-I中所示的代码创建chef-playground/roles/webserver.json文件

$ touch roles/webserver.json 
{
  "name": "webserver",
  "description": "Web Server",
  "json_class": "Chef::Role",
  "chef_type": "role",
  "run_list": [
    "recipe[motd]",
    "recipe[users]",
    "recipe[apache]"
  ]
}

然后运行knife role from file命令将webserver.json作为参数传递,在Chef服务器中创建这个角色。

和数据包一样knife role from file命令假设webserver.json位于名为roles的子目录中,而不是在当前目录

$ knife role from file webserver.json
Updated Role webserver

紧接着让我们运行knife show role查看刚刚在服务器上创建的webserver角色

$ knife role show webserver
chef_type:           role
default_attributes:
description:         Web Server
env_run_lists:
json_class:          Chef::Role
name:                webserver
override_attributes:
run_list:
  recipe[motd]
  recipe[users]
  recipe[apache]

可以通过knife node set命令在服务器上设定节点的运行清单。让我们将snowman节点的 运行清单设定为刚刚创建的webserver角色

$ knife node run_list set snowman "role[webserver]"
snowman:
  run_list: role[webserver]

Chef运行时,运行清单中的网页服务器(webserver)角色将展开至该角色的运行清单

  • recipe[motd]
  • recipe[users]
  • recipe[apache]

角色是一个强大的抽象概念,它允许你按功能将基础架构加以分类。一个角色包含很多配方单是很常见的如果没有角色功能,想象一下你需要重复将数十个配方单一添加 到数百个节点的每个运行清单中。角色使这项工作变得十分容易。

**2、属性和角色 **

角色同时可以包含属性。

让我们创建一个.json文件来表示一个基本角色。这个角色包含我们在前面推荐运行在每个节点上的chef-client::delete_validationchef-client::default配方单。

在这个案例中,我们同时需要设定一个属性告chef-client::default配方单我们希望使用 runit作为init_style的值。

touch roles/base.json

{
    "name": "base",
    "description": "Common recipes for all nodes",
    "json_class": "Chef::Role",
    "chef_type": "role",
    "run_list": [
      "recipe[chef-client::delete_validation]",
      "recipe[chef-client]"
    ],
    "default_attributes": {
      "chef_client": {
        "init_style": "runit"
      }
    }
  }
$ knife role from file base.json
Updated Role base
 knife role show base
chef_type:           role
default_attributes:
  chef_client:
    init_style: runit
description:         Common recipes for all nodes
env_run_lists:
json_class:          Chef::Role
name:                base
override_attributes:
run_list:
  recipe[chef-client::delete_validation]
  recipe[chef-client]

我们推荐在角色中只使用默认优先级的属性这样可以让多个来源的属性组合更容易理解

由于角色可以包含属性兔色中的属胜也在所有属性中佣有它的优先级。

我们展示属性优先级的结构,

  • 角色的属性可以重写配方单或属性文件中定义的属性
  • 但优先级比ohai定义的自动属性要低
  • 角色中的属性设计为全局设定
  • 并比在菜诗中设定的属性拥有更高的优先级。

Alt Image Text

3、角色和搜索

Chef搜索功能支持角色。以下例子展示如何搜索包含某个配方单的角色。注意,必须使用\字符来转义查询字符串中的[]

$ knife search role "run_list:recipe\[apache\]"
1 items found

chef_type:           role
default_attributes:
description:         Web Server
env_run_lists:
json_class:          Chef::Role
name:                webserver
override_attributes:
run_list:
  recipe[motd]
  recipe[users]
  recipe[apache]

由于在角色中的运行清单可以展开(包含其他角色或配方单),要搜索一个节点的运行清单中有两种方法:

knife search node "recipe:<recipe_name>"

When you do not want the search to include the expanded set of recipes within roles

knife search node "recipes:<recipe name>"

When you do want the search to expand role references

让我们重新来看早先使用的webserver角色案例

  • webserver角色加人到snowman节点的运行清单中。当Chef运行时webserver角色展开实际节点将运行以下web server角色的运行清单中包含的配方单:

  • recipe[motd]

  • recipe[users]
  • recipe[apache]

然而如果通过recipe:进行搜索,比如搜索recipe[apache::config]结果中不会得到 snowman节点:

$ knife search node "recipe:apache"
2 items found

Node Name:   atwood
Environment: _default
FQDN:        atwood.playground.local
IP:          192.168.33.31
Run List:    recipe[apache], recipe[motd]
Roles:       
Recipes:     apache, motd
Platform:    centos 6.5
Tags:        

Node Name:   susu
Environment: _default
FQDN:        susu.playground.local
IP:          192.168.33.33
Run List:    recipe[apache], recipe[motd]
Roles:       
Recipes:     apache, motd
Platform:    centos 6.5
Tags:        

因为snowman节点的运行清单中并没有直接引用recipe[apache::config] snowman节包含"role[webserner]"角色展开后才包含"recipe[apache]"配方单。

然而如果使用recipes:进行搜索结果中会得到snowman节点.

NOTE

Similar to the square bracket characters ([]), the colon (::) characters in a cookbook recipe reference must be individually escaped on a command line with the backslash (\) character: chef-client\:\:config. This is treated as if it were chef-client::config.

  knife search node "recipes:apache"
3 items found

Node Name:   atwood
Environment: _default
FQDN:        atwood.playground.local
IP:          192.168.33.31
Run List:    recipe[apache], recipe[motd]
Roles:       
Recipes:     apache, motd
Platform:    centos 6.5
Tags:        

Node Name:   snowman
Environment: _default
FQDN:        snowman.playground.local
IP:          192.168.33.32
Run List:    role[webserver]
Roles:       
Recipes:     apache, motd, motd-attributes
Platform:    ubuntu 14.04
Tags:        

Node Name:   susu
Environment: _default
FQDN:        susu.playground.local
IP:          192.168.33.33
Run List:    recipe[apache], recipe[motd]
Roles:       
Recipes:     apache, motd
Platform:    centos 6.5
Tags: 

劝于通过角色搜索节点也一样可以指定是否展开角色的运行清单

knife search node role:<role_name>

When you do not want the search to include the expanded set of role references

knife search node "roles:<role_name>"

When you do want the search to expand role references

4、角色菜谱

当一个角色被改变时,它会实时影响整个基础架构。然而目前角色还不支持多版本.

通常,运行清单对此的影响最大。举例而言Chef基础架构的其中一名工程师决定将recipe[apache]配方单从我们本章前面使用的webserver角色中移除假设这位工程师

这样做因为她不想让网页服务器默认使用Apache而想让开发菜谱的工程师决定使用Apache还是Nginx服务器

{
  "name": "webserver",
  "description": "Web Server",
  "json_class": "Chef::Role",
  "chef_type": "role",
  "run_list": [
    "recipe[motd]",
    "recipe[users]"
  ]
}

如果webserver角色在基础架构中被广泛使用,以上的改变就会对假设recipe[apache]配 方单会在webserver角色中存在的菜谱造成意料之外的影响。

相反,如果工程师们都相当 谨慎而不敢对现有角色做出改变,则会造成拥有许多功能类似但名字不同的角色。

举例而言Chef工程师可能会创建两个新的角色webserver-apachewebservex-nginx更请楚地表明她想用这些来补充现有的webserver角色的意图

因为菜谱是支持版本的许多Chef工程师使用角色菜谱来代替角色中的运行清单 它们仍然使用角色中的属性只是把运行清单移到了菜谱中。

一个配方单可以通过使用include_recipe命令来轻松模拟运行清单例.

如在我们的实例中可以创建一个webserver菜谱:

include_recipe "motd"
include_recipe "user"
include_recipe "apache"

作为分类用途以及使用角色属性,节点仍然适用webserver角色,webserver角色的运行清单中仅包含webserver菜谱。这样,我们仍然可以通过搜索找到所有网页服务器:

knife search node role:webserver

在这个情景中,webserver角色的运行清单为空,节点的运行清单则包含 recipe[webserver]菜谱(也可以将recipe[webserver]菜谱作为webserver角色的唯一运行清单项目,然后节点仍然包含webserver角色)。

菜谱支持多版本,配合使用下一章将会介绍的环境功能,你可以指定哪些节点使用哪些特定版本的菜谱。这称为节点的版本计划

5、本节小结

  • 创建一个网页服务器角色
  • 属性和角色
  • 角色和搜索
  • 角色菜谱
$ knife role from file webserver.json
$ knife role show webserver
$ knife node run_list set snowman "role[webserver]"
$ knife search role "run_list:recipe\[apache\]"
$ knife search node "recipes:<recipe name>"
$ knife search node "recipe:apache"
$ knife search node "roles:<role_name>"
$ knife search node role:webserver