如何创建简单的 Chef Cookbook 来管理 Ubuntu 上的基础设施

介绍


Chef 是一个配置管理系统,旨在使您能够以自动,可靠和可扩展的方式自动化和控制大量计算机。

在以往的教程中,我们研究了一些通用主厨术语,并讨论了如何安装主厨服务器,工作站,和节点(带有Cef 12Cef 11. 在本指南中,我们将使用这些指南作为跳出点开始谈论如何实现环境自动化.

在本文中,我们将讨论创建厨师厨师书的基本知识。厨师书是允许我们在远程节点上配置和执行厨师内部特定任务的配置单元。

在本指南中,我们将假设您是从我们完成的三台机器(https://www.digitalocean.com/community/articles/how-to-install-a-chef-server-workstation-and-client-on-ubuntu-vps-instances)开始的。

关键词: 基本厨房概念


烹饪书作为厨师使用的配置和策略细节的基本单位,将节点带入特定状态,这只是意味着厨师使用烹饪书来执行工作,并确保事物在节点上是应该的。

烹饪书通常用于处理一个特定的服务,应用程序或功能,例如,可以创建烹饪书以使用NTP来设置和同步节点的时间与特定的服务器。

烹饪书是在工作站上创建,然后上传到厨师服务器上。从那里,烹饪书中描述的食谱和策略可以分配给节点,作为节点的运行列表的一部分。

这样,您在烹饪书中写入的配置细节会应用于您想要遵循烹饪书中描述的场景的节点。

烹饪书被组织成一个完全自有目录结构. 有许多不同的目录和文件,用于不同的目的。

食谱


食谱是烹饪书的主要工作马,食谱可以包含多个食谱,或者依赖于外部食谱,食谱用来声明不同资源的状态。

厨师资源描述了系统的一部分及其所需状态,例如,一个资源可以说包 x 应该安装

食谱是指一份有关资源的列表,该列表告诉厨师如果执行食谱,系统应该如何看待。当厨师运行食谱时,厨师会检查每个资源是否符合声明的状态。

资源可以是许多不同的类型. 您可以在这里了解有关 不同的资源类型

*包装 :用于管理节点上的包 **服务 :用于管理节点的服务。 *用户 :管理节点上的用户 * :管理组 *template :用嵌入的红宝石模板管理文件 *cookbook_file :将文件从 cookbook 中的文件子目录转移到节点上的位置 *文件 :管理节点上文件的内容 *目录 :在节点上管理目录 *执行 :执行节点上的命令 *cron : 编辑节点上已有的克龙文件

属性


在厨师中,属性基本上是设置,想想它们是你可能想在烹饪书中使用的任何简单的关键值对。

有几种不同类型的属性可应用,每个属性具有不同的优先级级别,对一个节点运作的最终设置。在厨房级别,我们通常定义了我们正在配置的服务或系统的默认属性。

在创建厨师本时,我们可以在厨师本的属性子目录中为我们的服务设置属性,然后我们可以在厨师本的其他部分引用这些值。

◎ 檔案


烹饪书中的文件子目录包含我们将放置在使用烹饪书的节点上的任何静态文件。

例如,任何我们不太可能修改的简单配置文件都可以全部放置在文件子目录中,然后可以宣布一个资源,将文件从该目录移动到节点上的最终位置。

寺庙


模板类似于文件,但不是静态的. 模板文件以 .erb 扩展结束,这意味着它们包含嵌入式 Ruby。

这些主要用于替换属性值到文件中,以创建将放置在节点上的最终文件版本。

例如,如果我们有一个定义服务的默认端口的属性,则模板文件可以呼叫将该属性插入到该端口被声明的文件中的位置。

数据。rb


metadata.rb 文件被用来管理有关包的元数据,这包括包的名称、描述等。

它还包括类似依赖信息的内容,您可以指定该厨房需要运行哪些厨房,这将允许厨师服务器正确构建节点的运行列表,并确保所有零件都正确传输。

创建一个简单的烹饪书


为了展示与烹饪书一起工作的一些工作流程,我们将创建自己的烹饪书,这将是一个非常简单的烹饪书,在我们的节点上安装和配置 Nginx Web 服务器。

首先,我们需要进入我们工作站上的~/chef-repo目录:

1cd ~/chef-repo

一旦在那里,我们可以使用刀创建一本烹饪书,正如我们在以前的指南中提到的,刀是一种用于配置与厨师系统的大多数互动的工具,我们可以使用它来执行我们工作站的工作,也可以连接到厨师服务器或个别节点。

创建烹饪书的通用语法是:

knife cookbook create cookbook_name

由于我们的烹饪书将处理安装和配置 Nginx,我们将适当地命名我们的烹饪书:

1knife cookbook create nginx

1** Creating cookbook nginx
2** Creating README for cookbook: nginx
3** Creating CHANGELOG for cookbook: nginx
4** Creating metadata for cookbook: nginx

刀在这里做的是构建一个简单的结构在我们的厨师书目录为我们的新厨师书. 我们可以看到我们的厨师书结构通过导航到厨师书目录,并进入与厨师书名目录。

1cd cookbooks/nginx
2ls

1attributes CHANGELOG.md definitions files libraries metadata.rb providers README.md recipes resources	templates

正如你所看到的,这已经创建了一个文件夹和文件结构,我们可以使用它来构建我们的烹饪书。

创建一个简单的食谱


如果我们进入食谱子目录,我们可以看到里面已经有一个名为default.rb的文件:

1cd recipes
2ls

1default.rb

这是如果您引用nginx的食谱,将运行的食谱,这就是我们将添加我们的代码的地方。

使用您的文本编辑器打开文件:

1nano default.rb

1#
2# Cookbook Name:: nginx
3# Recipe:: default
4#
5# Copyright 2014, YOUR_COMPANY_NAME
6#
7# All rights reserved - Do Not Redistribute
8#

目前该文件中唯一的内容是评论标题。

我們可以開始計劃我們的 Nginx 網頁伺服器需要發生的事情,以便以我們想要的方式運行。

首先,我们显然需要确保软件已安装,我们可以通过先创建一个资源来做到这一点。

1package 'nginx' do
2  action :install
3end

第一行以资源类型(包)和资源名称()开头,其余的是一组行动和参数,声明我们希望资源发生什么。

在这个资源中,我们看到‘action :install’ 这个行告诉厨师,我们所描述的资源应该安装。运行此配方的节点会检查 Nginx 是否已安装。

在我们安装该服务后,我们可能希望在节点上调整其当前状态. 默认情况下,Ubuntu在安装后不会启动 Nginx,所以我们会想要改变:

1service 'nginx' do
2  action [ :enable, :start ]
3end

在这里,我们看到一个),我们现在想要启动该服务,并允许它在机器重新启动时自动启动。

由于这是一个简单的文件,我们不会修改,我们可以简单地声明我们想要的文件的位置,并告诉它在厨房里得到文件的位置:

1cookbook_file "/usr/share/nginx/www/index.html" do
2  source "index.html"
3  mode "0644"
4end

我們使用「cookbook_file」資源類型告訴 Chef 該檔案在廚房本身中可用,並可按位置傳送至位置。

在我们的情况下,我们在第一个行中指定我们试图创建的文件名称. 在行中,我们告诉它在烹饪书中搜索的文件名称. 厨师在烹饪书中的文件/默认子目录中搜索这个文件。

模式行设置了我们正在创建的文件上的权限,在这种情况下,我们允许 root 用户读取和写入权限,其他人读取权限。

保存并关闭此文件,当你完成。

创建索引文件


正如你所看到的,我们定义了一个cookbook_file资源,该资源应该将名为index.html的文件移动到节点上的文档根中。

我们应该把这个文件放在我们厨房的文件/默认子目录中。

1cd ~/chef-repo/cookbooks/nginx/files/default

在此目录中,我们将创建我们引用的文件:

1nano index.html

这个文件只是一个非常简单的HTML文档,旨在证明我们的资源以我们想要的方式运作。

把这个放在文件里:

1<html>
2  <head>
3    <title>Hello there</title>
4  </head>
5  <body>
6    <h1>This is a test</h1>
7    <p>Please work!</p>
8  </body>
9</html>

保存并关闭文件,当你完成。

创建一个帮助厨师书


在我们走得更远之前,让我们预先解决一个小问题,当我们的节点试图运行我们创建的烹饪书,就像现在一样,很可能它会失败。

这是因为它会尝试从 Ubuntu 存储库中安装 Nginx,而我们节点上的包数据库很可能已经过时了. 通常,我们在运行包命令之前运行sudo apt-get update

为了解决这个问题,我们可以创建一个简单的烹饪书,其唯一的目的是确保包数据库的更新。

我们可以使用我们以前使用的相同的刀语法来做到这一点,让我们把这本烹饪书称为apt:

1knife cookbook create apt

这将创建与我们第一次开始使用 Nginx 烹饪书时的类似目录结构。

让我们直接切割到追逐,并编辑我们新的烹饪书的默认食谱。

1nano ~/chef-repo/cookbooks/apt/recipes/default.rb

在此文件中,我们将声明一个执行资源,这只是定义我们想要在节点上运行的命令的一种方式。

我们的资源看起来像这样:

1execute "apt-get update" do
2  command "apt-get update"
3end

第一行给我们的资源一个名字. 在我们的情况下,我们是为了简单而称之为这个资源. 如果),那么这是实际执行的命令。

因为它们是完全相同的,这并不重要。

保存并关闭文件。

现在我们有我们的新厨房,有几种方式,我们可以确保我们在我们的 Nginx 厨房之前执行此操作,我们可以将其添加到节点的运行列表之前 Nginx 厨房,但我们也可以将其绑在 Nginx 厨房本身。

这可能是更好的选择,因为我们不必记住在每一个我们想要为 Nginx 配置的节点上添加apt烹饪本之前的nginx烹饪本。

我們需要調整 Nginx 料理本中的幾件事,以便這樣發生。

1nano ~/chef-repo/cookbooks/nginx/recipes/default.rb

在这本烹饪书的顶部,在我们定义的其他资源之前,我们可以通过键入apt默认食谱阅读:

include_recipe "apt"

package 'nginx' do
  action :install
end

service 'nginx' do
  action [ :enable, :start ]
end

cookbook_file "/usr/share/nginx/www/index.html" do
  source "index.html"
  mode "0644"
end

保存并关闭文件。

我们需要编辑的另一个文件是 metadata.rb 文件. 这个文件在 Chef 服务器将运行列表发送到节点时被检查,以查看哪些其他食谱应该添加到运行列表中。

现在打开文件:

1nano ~/chef-repo/cookbooks/nginx/metadata.rb

在文件的底部,你可以添加这个行:

name             'nginx'
maintainer       'YOUR_COMPANY_NAME'
maintainer_email 'YOUR_EMAIL'
license          'All rights reserved'
description      'Installs/Configures nginx'
long_description IO.read(File.join(File.dirname(__FILE__), 'README.md'))
version          '0.1.0'

depends "apt"

完成后,我们的 Nginx 烹饪书现在依靠我们的 apt 烹饪书来处理包数据库更新。

将烹饪书添加到您的节点


现在我们的基本烹饪书已经完成,我们可以将它们上传到我们的厨师服务器上。

我们可以通过打字来单独做到这一点:

1knife cookbook upload apt
2knife cookbook upload nginx

或者,我们可以通过键入上传一切:

1knife cookbook upload -a

无论如何,我们的食谱将上传到厨师服务器。

现在,我们可以修改我们的节点的运行列表,我们可以轻松地通过键入:

knife node edit name_of_node

如果您需要找到可用的节点的名称,您可以键入:

1knife node list

1client1

对于我们的目的,当我们输入此时,我们会得到一个看起来像这样的文件:

1knife node edit client1

 1{
 2  "name": "client1",
 3  "chef_environment": "_default",
 4  "normal": {
 5    "tags": [
 6
 7    ]
 8  },
 9  "run_list": [
10
11  ]
12}

在此操作之前,您可能需要设置 EDITOR 环境变量,您可以通过键入:

export EDITOR=name_of_editor

正如你所看到的,这是一个简单的JSON文档,描述了我们节点的某些方面,我们可以看到一个run_list阵列,目前是空的。

我们可以使用格式将我们的 Nginx 烹饪书添加到该阵列中:

"recipe[name_of_recipe]"

当我们完成时,我们的文件应该是这样的:

 1{
 2  "name": "client1",
 3  "chef_environment": "_default",
 4  "normal": {
 5    "tags": [
 6
 7    ]
 8  },
 9  "run_list": [
10    "recipe[nginx]"
11  ]
12}

保存并关闭文件以执行新设置。

现在,我们可以 SSH 进入我们的节点并运行 Chef 客户端软件. 这将导致客户端检查 Chef 服务器. 一旦它这样做,它将看到新的运行列表已分配给它。

SSH 进入您的节点,然后运行此操作:

1sudo chef-client

 1Starting Chef Client, version 11.8.2
 2resolving cookbooks for run list: ["nginx"]
 3Synchronizing Cookbooks:
 4  - apt
 5  - nginx
 6Compiling Cookbooks...
 7Converging 4 resources
 8Recipe: apt::default
 9  * execute[apt-get update] action run
10    - execute apt-get update
11
12Recipe: nginx::default
13  * package[nginx] action install (up to date)
14  * service[nginx] action enable
15    - enable service service[nginx]
16
17  * service[nginx] action start (up to date)
18  * cookbook_file[/usr/share/nginx/www/index.html] action create (up to date)
19Chef Client finished, 2 resources updated

正如你所看到的,我们的 apt 烹饪书被发送并运行,即使它不在我们创建的运行列表中,这是因为厨师智能地解决了依赖并修改了实际运行列表,然后在节点上执行它。

注意 :有不同的方法来确保一本烹饪书或食谱在另一个之前运行。

我们可以通过访问我们的节点的IP地址或域名来验证此功能:

http://node_domain_or_IP

你应该看到一些看起来像这样的东西:

Chef node Nginx

恭喜,您已使用厨师厨师书设置了您的第一个节点!

结论


虽然这是一个非常简单的例子,可能不会在手动配置服务器上节省您很多时间,但希望您可以开始看到这种构建基础设施的方法的可能性。

它不仅允许快速部署和配置不同类型的服务器,还确保您知道所有机器的确切配置,这使您能够验证和测试您的基础设施,并为您提供快速重新部署基础设施所需的框架。

By Justin Ellingwood
Published At
Categories with 技术
comments powered by Disqus