Puppet自动化管理配置

 

 

Puppet:开源系统配置和管理工具

随着虚拟化和云计算技术的兴起,计算机集群的自动化管理和配置成为了数据中心运维管理的热点。对于 IaaS、Paas、Saas 来讲,随着业务需求的提高,后台计算机集群的数量也会线性增长。对于数据中心的运维人员来讲,如何自动化管理、配置这些大规模的计算机集群节点,对于数据中心的稳定运行以及运维成本控制都显得相当重要。html

Puppet 是一个开源系统配置管理工具,它有着简明的架构以及良好的扩展性;同时,Puppet 还提供了自有的系统配置描述语言以及完善的公用库,很是适合用于管理和部署大规模集群系统。node

Puppet 的系统架构

Puppet 使用简明的 C/S 架构,分为 Puppet Server 和 Puppet Node。mysql

图 1. Puppet 的架构

图 1. Puppet 的架构

Puppet Servernginx

Puppet Server 是配置和管理整个集群的大脑,管理着全部节点。系统管理员在 Puppet Server 上用 Puppet 特有的配置描述语言为各个节点编写配置文件 (manifest),配置文件描述了节点的目标状态——资源的集合。这些资源能够是文件、服务、软件包等等。各个节点会周期性的查询 Puppet Server,得到本身的最新配置文件,而且在本地应用这些配置文件,使得自身的资源和状态达到配置文件要求。web

Puppet Node(Agent)正则表达式

被 Puppet Master 管理着的计算机节点称为 Puppet node。Puppet node 会周期性的查询 Puppet Master,来获取本身的配置文件,而且在本地应用。在每次应用配置文件以后,Puppet node 会提供上传一份报告给 Puppet Master,以便之后的统计和分析。系统管理员也能够手动地在 Puppet Node 上执行命令,让 Puppet Node 当即查询 Puppet Server 获取自身最新的配置文件,而且在本地应用。redis

Puppet 的工做流程

Puppet 的工做流程能够归纳成这几步:定义、模拟、应用、报告。sql

图 2. Puppet 的工做流程

图 2. Puppet 的工做流程

定义 (Define)

管理员为各个节点编写配置文件,配置文件中定义了该节点所须要的资源的集合以及资源之间的关系。这些资源能够是文件、服务、软件包、可执行的命令等等。Puppet 内置的配置管理语言对这些资源提供了较为完整的底层抽象,减轻了编写配置文件的复杂度。shell

模拟 (Simulate)

根据节点的配置文件,咱们能够了解到该节点须要什么样的资源而且处于什么样的状态。配置文件描述了节点的状态,而不是具体的配置步骤。Puppet 会将配置文件 Manifest 编译成更为详细的一种配置文件 Catalog。经过 Catalog,Puppet 会根据节点的当前状态,模拟出节点达到该目标状态所须要的步骤。apache

应用 (Enforce)

节点周期性地向 Puppet Server 来请求本身最新的配置文件。Puppet 会将节点的实际状态与节点配置文件中所表述的目标状态作比较,并根据获得的所须要的步骤,对节点执行操做,使其达到配置文件所表述的状态。

报告 (Report)

当每次应用执行事后,节点都会给 Puppet Server 发送一份运行报告,报告该节点的状态,以便之后的分析和统计。

Puppet 配置语言介绍

Puppet 配置管理语言中的核心概念是资源,资源能够是一个软件包,一个文件,一种服务等等。一个节点的状态能够用资源的集合以及他们之间的关系来表示。管理员不须要详细地描述配置和部署系统的具体步骤,Puppet 只须要管理员来描述系统的目标状态,即资源的集合以及它们之间的关系。Puppet 内置的执行引擎会根据节点的现有状态将配置文件转化为具体的执行步骤而且执行。

在 Puppet 中,类是一系列相关资源的集合;模块是一系列类的集合。Puppet 内置提供了一些经常使用的类和模块,同时用户能够定义本身的类和模块。经过类和模块使用,配置模块重用和共享变的很是容易。

安装和配置

环境配置

因为 Puppet Server 和节点之间经过主机名来通讯,因此须要双方能够经过彼此的主机名来找到对应的 IP 地址。能够经过配置 DNS 或者配置/ets/hosts 文件来实现。

安装准备

在安装官方提供的开源版本的 Puppet 软件以前,Puppet Server 和 agent 首先须要都安装官方的软件源 (Puppet 对各类 Linux 发行版都有提供支持,本文以 Ubuntu 14.04 系统为例):

下载官方软件源的安装包:

1
wget https://apt.puppetlabs.com/puppetlabs-release-pc1-trusty.deb

更新软件源:

1
2
sudo dpkg -i puppetlabs-release-pc1-trusty.deb
sudo apt-get update

安装 Puppet Server

1
sudo apt-get install puppetserver

启动 PuppetServer

1
sudo service puppetservice start

安装 PuppetAgent

1
sudo apt-get install puppet-agent

编辑/etc/puppetlabs/puppet/puppet.conf 文件,设置该 agent 的 puppet server 的地址:

1
2
[main]
server = puppetmaster

注:puppetmaster 是 puppetserver 的主机名。

启动 puppet service

1
sudo /opt/puppetlabs/bin/puppet resource service puppet ensure=running enable=true

编写第一个配置文件

第一个 Hello World 配置文件

做为第一个实例配置文件,咱们想让节点作一件最简单的事情:在/etc/文件夹下面建立一个文件 helloworld.txt,文件的内容是”hello world from puppet!\n”。

首先咱们在 puppetserver 上进入/etc/puppetlabs/code/environments/production/manifests 文件夹,建立 site.pp 文件:

1
2
3
4
5
6
7
8
9
10
11
12
node puppetagent {
 
file { 'helloworld':
 
    path => '/etc/helloworld.txt',
    owner  => 'root',
    group  => 'root',
    mode   => '655',
    content => "hello world from puppet!\n",
    }
 
}

site.pp 就是节点的配置文件,里面能够包含对各个节点的配置描述。在实例配置文件中,”puppetagent”就是节点的主机名。包含在 puppetagent 中的配置描述就是该节点的资源集合的描述。

配置文件建立好后,节点会周期性地查询 PuppetServer 来获取本身的配置文件并在本地应用。固然 Puppet 也支持手动获取本身的配置。在本例中,咱们经过手动的方式来进行配置更新。咱们在 PuppetAgent 上手动执行命令:

1
2
3
4
5
6
7
8
9
10
11
12
13
root@puppetAgent:/opt/puppetlabs/bin# ./puppet agent --test
2016-05-21 14:24:14.858673 WARN  puppetlabs.facter - locale environment variables were bad;
                          continuing with LANG=C LC_ALL=C
Info: Using configured environment 'production'
Info: Retrieving pluginfacts
Info: Retrieving plugin
Info: Caching catalog for puppetagent
Info: Applying configuration version '1463811856'
Notice: /Stage[main]/Main/Node[puppetagent]/File[helloworld]/ensure:
                         defined content as '{md5}c3aa68786c58c94ef6f3e2399920f268'
Notice: Applied catalog in 0.02 seconds
root@puppetAgent:/opt/puppetlabs/bin# cat /etc/helloworld.txt 
hello world from puppet!

咱们看到节点成功从 Puppet Server 获取配置文件,而且在本地应用,对应的文件成功建立。

进阶:执行脚本任务

做为进阶的任务,咱们但愿节点能够执行一些更加复杂一点的任务。咱们但愿节点能够从 PuppetServer 获取一个命令脚本,而且执行该脚本。

咱们首先在/etc/puppetlabs/code/environments/production/modules 中建立一个名叫”test”的模块,在 test 模块下面建立一个”files”文件夹。在这个文件夹里的文件是能够被节点获取的。而后咱们在这个”files”文件夹里建立一个 shell 脚本 test.sh,路径以下:

/etc/puppetlabs/code/environments/production/modules/test/files/test.sh

test.sh 文件内容:

1
2
touch /etc/helloworld.log
echo "helloworld" >> /etc/helloworld.log

该脚本会在/etc/目录下建立 helloworld.log 文件,而后在文件里添加”hello world”内容。

进入目录/etc/puppetlabs/code/environments/production/manifests,而后咱们再来编辑 site.pp 文件:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
node puppetagent {
file { 'test.sh':
  path => '/etc/test.sh',
  owner  => 'root',
  group  => 'root',
  mode   => '655',
  source => 'puppet:///modules/test/test.sh',
  }
exec { 'execute ':
  command => 'bash /etc/test.sh',
  require => File['test.sh'],
  path => ["/bin/"],
}
}

其中,咱们定义了两个资源:一个文件资源和一个执行命令资源。同时这两个资源有依赖关系,命令执行资源依赖于文件资源,因此 Puppet 会优先处理文件资源。执行命令资源会在文件资源存在后再执行。

咱们看下客户端的执行结果:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
root@puppetAgent:/opt/puppetlabs/bin# ./puppet agent --test
2016-05-21 15:39:39.817370 WARN  puppetlabs.facter - locale environment variables were bad;
                                 continuing with LANG=C LC_ALL=C
Info: Using configured environment 'production'
Info: Retrieving pluginfacts
Info: Retrieving plugin
Info: Caching catalog for puppetagent
Info: Applying configuration version '1463816381'
Notice: /Stage[main]/Main/Node[puppetagent]/File[test.sh]/ensure:
                                 defined content as '{md5}2ce060ad2ddab2fe416ca8fb6f8da32a'
Notice: /Stage[main]/Main/Node[puppetagent]/Exec[execute ]/returns: executed successfully
Notice: Applied catalog in 0.05 seconds
root@puppetAgent:/opt/puppetlabs/bin# cat /etc/helloworld.log 
helloworld

咱们能够看到,helloworld.log 文件被正确的建立,说明脚本文件被正确地执行。

总结

Puppet 是基于 Ruby 的开源系统配置和管理工具,它提供的独特的系统配置语言极大程度地简化了系统管理员管理和配置系统的过程。本文首先介绍了 Puppet 的系统架构和工做流程,而且介绍了 Puppet 独特的系统配置语言,以后咱们简单介绍了安装和配置 Puppet 的具体步骤。最后,本文以两个实例介绍了如何在 Puppet 中为节点编写配置文件,来达到建立文件和执行命令的效果。但愿本文能对系统管理员,Puppet 初学者有所帮助。

 

1、puppet 介绍

一、puppet是什么

  puppet是一个IT基础设施自动化管理工具,它可以帮助系统管理员管理基础设施的整个生命周期: 供应(provisioning)、配置(configuration)、联动(orchestration)及报告(reporting)。
  基于puppet ,可实现自动化重复任务、快速部署关键性应用以及在本地或云端完成主动管理变动和快速扩展架构规模等。
  遵循GPL 协议(2.7.0-), 基于ruby语言开发。
  2.7.0 之后使用(Apache 2.0 license)
  对于系统管理员是抽象的,只依赖于rubyfacter
  能管理多达40 多种资源,例如:fileusergrouphostpackageservicecronexecyum repo等。

二、puppet的工做机制

1)工做模型

  puppet 经过声明性、基于模型的方法进行IT自动化管理。
  定义:经过puppet 的声明性配置语言定义基础设置配置的目标状态;
  模拟:强制应用改变的配置以前先进行模拟性应用;
  强制:自动、强制部署达成目标状态,纠正任何偏离的配置;
  报告:报告当下状态及目标状态的不一样,以及达成目标状态所进行的任何强制性改变;
puppet三层模型
  puppet三层模型以下:

puppet三层模型
 
puppet三层模型

2)工做流程

工做流程
 
工做流程

3)使用模型

  puppet的使用模型分为单机使用模型master/agent模型,下面咱们来看看这两个模型的原理图。
单机使用模型
  实现定义多个manifests --> complier --> catalog --> apply

单机使用模型工做原理
 
单机使用模型工做原理

master/agent模型
  master/agent模型实现的是集中式管理,即 agent 端周期性向 master 端发起请求,请求本身须要的数据。而后在本身的机器上运行,并将结果返回给 master 端。
  架构和工做原理以下:
架构

master/agent模式架构
 
master/agent模式架构

工做原理

master/agent模式工做原理
 
master/agent模式工做原理

三、puppet 名词解释

  • 资源:是puppet的核心,经过资源申报,定义在资源清单中。至关于ansible中的模块,只是抽象的更加完全。
  • 类:一组资源清单。
  • 模块:包含多个类。至关于ansible中的角色
  • 站点清单:以主机为核心,应用哪些模块。

2、puppet 资源详解

  接下来,咱们就以单机模式来具体介绍一下puppet的各个部分。

一、程序安装及环境

  首先,咱们仍是来安装一下puppetpuppet的安装可使用源码安装,也可使用rpm(官方提供)、epel源、官方提供的yum仓库来安装(经过下载官方提供的rpm包能够指定官方的yum仓库)。
  在这里,咱们就是用 yum 安装的方式。

yum install -y puppet

  安装完成事后,咱们能够经过rpm -ql puppet | less来查看一下包中都有一些什么文件。
  其中主配置文件为/etc/puppet/puppet.conf,使用的主程序为/usr/bin/puppet

二、puppet 资源简介

1)资源抽象

   puppet 从如下三个维度来对资源完成抽象:

  1. 类似的资源被抽象成同一种资源**“类型”** ,如程序包资源、用户资源及服务资源等;
  2. 将资源属性或状态的描述与其实现方式剥离开来,如仅说明安装一个程序包而不用关心其具体是经过yum、pkgadd、ports或是其它方式实现;
  3. 仅描述资源的目标状态,也即指望其实现的结果,而不是其具体过程,如“肯定nginx 运行起来” 而不是具体描述为“运行nginx命令将其启动起来”;

  这三个也被称做puppet 的资源抽象层(RAL)
  RAL 由type( 类型) 和provider( 提供者,即不一样OS 上的特定实现)组成。
  

2)资源定义

  资源定义经过向资源类型的属性赋值来实现,可称为资源类型实例化;
  定义了资源实例的文件即清单,manifest;
  定义资源的语法以下:

type {'title':
	attribute1 	=> value1,
	atrribute2	=> value2,
	……
}

  注意:type必须使用小写字符;title是一个字符串,在同一类型中必须唯一;每个属性之间须要用“,”隔开,最后一个“,”可省略。
  例如,能够同时有名为nginx 的“service”资源和“package”资源,但在“package” 类型的资源中只能有一个名为“nginx”的资源。

3)资源属性中的三个特殊属性:

  • Namevar:可简称为name;
  • ensure:资源的目标状态;
  • Provider:指明资源的管理接口;

三、经常使用资源总结

1)查看资源
  咱们可使用puppet describe来打印有关Puppet资源类型,提供者和元参数的帮助。使用语法以下:

puppet describe [-h|--help] [-s|--short] [-p|--providers] [-l|--list] [-m|--meta] [type]
	-l:列出全部资源类型;
	-s:显示指定类型的简要帮助信息;
	-m:显示指定类型的元参数,通常与-s一同使用;

2)group:管理系统上的用户组。
  查看使用帮助信息:

enter description here
 
group使用帮助
属性:
	name:组名,能够省略,若是省略,将继承title的值;
	gid:GID;
	system:是否为系统组,true OR false;
	ensure:目标状态,present/absent;
	members:成员用户;

  简单举例以下:

vim group.pp
	group{'mygrp':
        name => 'mygrp',
        ensure => present,
        gid => 2000,
	}

  咱们能够来运行一下:

enter description here
 
运行写好的group资源

  
3)user:管理系统上的用户。
  查看使用帮助信息:

enter description here
 
user使用帮助
属性:
	name:用户名,能够省略,若是省略,将继承title的值;
	uid: UID;
	gid:基本组ID;
	groups:附加组,不能包含基本组;
	comment:注释; 
	expiry:过时时间 ;
	home:用户的家目录; 
	shell:默认shell类型;
	system:是否为系统用户 ;
	ensure:present/absent;
	password:加密后的密码串;

  简单举例以下:

vim user1.pp
	user{'keerr':
        ensure => present,
        system => false,
        comment => 'Test User',
        shell => '/bin/tcsh',
        home => '/data/keerr',
        managehome => true,
        groups => 'mygrp',
        uid => 3000,
	}

4)package:puppet的管理软件包。
  查看使用帮助信息:

enter description here
 
package使用帮助
属性:
	ensure:installed, present, latest, absent, any version string (implies present)
	name:包名,能够省略,若是省略,将继承title的值;
	source:程序包来源,仅对不会自动下载相关程序包的provider有用,例如rpm或dpkg;
	provider:指明安装方式;

  简单举例以下:

vim package1.pp
	package{'nginx':
   		ensure  => installed,
    	procider    =>  yum
	}

5)service:定义服务的状态
  查看使用帮助信息:

puppet describe service -s -m
enter description here
 
service使用帮助
属性:
	ensure:服务的目标状态,值有true(running)和false(stopped) 
	enable:是否开机自动启动,值有true和false
	name:服务名称,能够省略,若是省略,将继承title的值
	path:服务脚本路径,默认为/etc/init.d/下
	start:定制启动命令
	stop:定制关闭命令
	restart:定制重启命令
	status:定制状态

  简单举例以下:

vim service1.pp
	service{'nginx':
  	  	ensure  => true,
    	enable  => false
	}

6)file:管理文件、目录、软连接
  查看使用帮助信息:

enter description here
 
file使用帮助
属性:
	ensure:目标状态,值有absent,present,file,directory和link
		file:类型为普通文件,其内容由content属性生成或复制由source属性指向的文件路径来建立;
		link:类型为符号连接文件,必须由target属性指明其连接的目标文件;
		directory:类型为目录,可经过source指向的路径复制生成,recurse属性指明是否递归复制;
	path:文件路径;
	source:源文件;
	content:文件内容;
	target:符号连接的目标文件; 
	owner:定义文件的属主;
	group:定义文件的属组;
	mode:定义文件的权限;
	atime/ctime/mtime:时间戳;

  简单举例以下:

vim file1.pp
	file{'aaa':
   	 	path    => '/data/aaa',
    	source  => '/etc/aaa',
    	owner   => 'keerr',
    	mode    => '611',
	}

7)exec:执行命令,慎用。一般用来执行外部命令
  查看使用帮助信息:

puppet describe exec -s -m
enter description here
 
exec使用帮助
属性:
	command(namevar):要运行的命令;
	cwd:指定运行该命令的目录;
	creates:文件路径,仅此路径表示的文件不存在时,command方才执行;
	user/group:运行命令的用户身份;
	path:指定命令执行的搜索路径;
	onlyif:此属性指定一个命令,此命令正常(退出码为0)运行时,当前command才会运行;
	unless:此属性指定一个命令,此命令非正常(退出码为非0)运行时,当前command才会运行;
	refresh:从新执行当前command的替代命令;
	refreshonly:仅接收到订阅的资源的通知时方才运行;

  简单举例以下:

vim exec1.pp
	exec{'cmd':
   	 	command => 'mkdir /data/testdir',
    	path => ['/bin','/sbin','/usr/bin','/usr/sbin'],
	#   path => '/bin:/sbin:/usr/bin:/usr/sbin',
	}

8)cron:定义周期性任务
  查看使用帮助信息:

enter description here
 
cron使用帮助
属性:
	command:要执行的任务(命令或脚本);
	ensure:目标状态,present/absent;
	hour:时;
	minute:分;
	monthday:日;
	month:月;
	weekday:周;
	user:以哪一个用户的身份运行命令(默认为root);
	target:添加为哪一个用户的任务;
	name:cron job的名称;

  简单举例以下:

vim cron1.pp
	cron{'timesync':
    	command => '/usr/sbin/ntpdata 172.16.0.1',
    	ensure  => present,
    	minute  => '*/3',
    	user    => 'root',
	}

  咱们能够运行一下,查看咱们的crontab,来看看该任务是否已经被添加:

[root@master manifests]# puppet apply -v --noop cron1.pp 		#试运行
[root@master manifests]# puppet apply -v  cron1.pp 				#运行
[root@master manifests]# crontab -l				#查看计划任务
# HEADER: This file was autogenerated at 2017-12-14 15:05:05 +0800 by puppet.
# HEADER: While it can still be managed manually, it is definitely not recommended.
# HEADER: Note particularly that the comments starting with 'Puppet Name' should
# HEADER: not be deleted, as doing so could cause duplicate cron jobs.
# Puppet Name: timesync
*/3 * * * * /usr/sbin/ntpdata 172.16.0.1

9)notify:调试输出
  查看使用帮助信息:

enter description here

 

属性:
	message:记录的信息
	name:信息名称

 该选项通常用于master/agent模式中,来记录一些操做的时间,好比从新安装了一个程序呀,或者重启了应用等等。会直接输出到代理机的运行日志中。


  以上,就是咱们常见的8个资源。其他的资源咱们可使用puppet describe -l来列出,上文中也已经说过了~

四、资源的特殊属性

  puppet中也提供了beforerequirenotifysubscribe四个参数来定义资源之间的依赖关系和通知关系。

before:表示须要依赖于某个资源
require:表示应该先执行本资源,在执行别的资源
notify:A notify B:B依赖于A,且A发生改变后会通知B;
subscribe:B subscribe A:B依赖于A,且B监控A资源的变化产生的事件;

  同时,依赖关系还可使用->~>来表示:

-> 表示后资源须要依赖前资源
~> 表示前资源变更通知后资源调用

  举例以下:

vim file.pp
	file{'test.txt':					#定义一个文件
		path   => '/data/test.txt',
		ensure  => file,
		source  => '/etc/fstab',
	}

	file{'test.symlink':				#依赖文件创建超连接
		path   => '/data/test.symlink',
		ensure  => link,
		target  => '/data/test.txt',
		require => File['test.txt'],
	}

	file{'test.dir':					#定义一个目录
		path   => '/data/test.dir',
		ensure  => directory,
		source  => '/etc/yum.repo.d/',
		recurse => true,
	}

  咱们还可使用在最下面统一写依赖关系的方式来定义:

vim redis.pp
	package{'reids':
		ensure  => installed,
	}

	file{'/etc/redis.conf':
		source  => '/root/manifets/files/redis.conf',
		ensure  => file,
		owner   => redis,
		group   => root,
		mode    => '0640',
	}

	service{'redis':
		ensure  => running,
		enable  => true,
		hasrestart => true,
	}

	Package['redis'] -> File['/etc/redis.conf'] -> Service['redis']	#定义依赖关系

tag 标签

  如同 anssible 同样,puppet 也能够定义“标签”——tag,打了标签之后,咱们在运行资源的时候就能够只运行某个打过标签的部分,而非所有。这样就更方便于咱们的操做。
 一个资源中,能够有一个tag也能够有多个。具体使用语法以下:

type{'title':
	...
    tag => 'TAG1',
}
            
type{'title':
    ...
    tag => ['TAG1','TAG2',...],
}

  调用时的语法以下:

puppet apply --tags TAG1,TAG2,... FILE.PP

实例
  首先,咱们去修改一下redis.pp文件,添加一个标签进去

vim redis.pp
	package{'redis':
		ensure  => installed,
	}

	file{'/etc/redis.conf':
		source  => '/root/manifets/file/redis.conf',
		ensure  => file,
		owner   => redis,
		group   => root,
		mode    => '0640',
		tag    => 'instconf'		#定义标签
	}

	service{'redis':
		ensure  => running,
		enable  => true,
		hasrestart => true,
	}

	Package['redis'] -> File['/etc/redis.conf'] -> Service['redis']

  而后,咱们手动先开启redis服务:

systemctl start redis

  如今,咱们去修改一下file目录下的配置文件:

vim file/redis.conf 
	requirepass keerya

  接着,咱们就去运行redis.pp,咱们的配置文件已经修改过了,如今想要实现的就是重启该服务,实现,须要使用密码keer登陆:

puppet apply -v --tags instconf redis.pp
enter description here
 
redis.pp运行结果

  如今,咱们就去登陆一下redis看看是否生效:

redis-cli -a keerya
enter description here
 
redis验证

  验证成功,实验完成。

五、puppet 变量

  puppet 变量以“$”开头,赋值操做符为“=”,语法为$variable_name=value
数据类型:

  字符型:引号无关紧要;但单引号为强引用双引号为弱引用;支持转义符;
  数值型:默认均识别为字符串,仅在数值上下文才以数值对待;
  数组:[]中以逗号分隔元素列表;
  布尔型值:true, false;不能加引号;
  hash:{}中以逗号分隔k/v数据列表; 键为字符型,值为任意puppet支持的类型;{ ‘mon’ => ‘Monday’, ‘tue’ => ‘Tuesday’, };
  undef:从未被声明的变量的值类型;

正则表达式:

  (?<ENABLED OPTION>:<PATTERN>)
  (?-<DISABLED OPTION>:<PATTERN>)
  OPTIONS:
    i:忽略字符大小写;
    m:把.当换行符;
    x:忽略<PATTERN>中的空白字符;
  (?i-mx:PATTERN)
注意:不能赋值给变量,仅能用在接受=~!~操做符的位置;

1)puppet的变量种类

  puppet 种类有三种,为facts内建变量用户自定义变量
facts:
  由facter提供;top scope;
内建变量:
  master端变量
    $servername, $serverip, $serverversion
  agent端变量
    $clientcert, $clientversion, $environment
  parser变量
    $module_name
用户自定义变量

2)变量的做用域

  不一样的变量也有其不一样的做用域。咱们称之为Scope
  做用域有三种,top scope,node scope,class scope。
  其生效范围排序为:top scope > node scope > class scope

enter description here
 
变量生效范围

  其优先级排序为:top scope < node scope < class scope

六、puppet 流程控制语句

  puppet 支持if 语句case 语句selector 语句

1)if 语句

  if语句支持单分支,双分支和多分支。具体语法以下:

单分支:
	if CONDITION {
		statement
		……
	}

双分支:
	if CONDITION {
		statement
		……
	}
	else{
		statement
		……		
	}

多分支:
	if CONDITION {
		statement
		……
	}
	elsif CONDITION{
		statement
		……
	}
	else{
		statement
		……		
	}

  其中,CONDITION的给定方式有以下三种:

  • 变量
  • 比较表达式
  • 有返回值的函数

举例

vim if.pp
	if $operatingsystemmajrelease == '7' {
		$db_pkg='mariadb-server'
	}else{
		$db_pkg='mysql-server'
	}

	package{"$db_pkg":
		ensure => installed,
	}

2)case 语句

  相似 if 语句,case 语句会从多个代码块中选择一个分支执行,这跟其它编程语言中的 case 语句功能一致。
  case 语句会接受一个控制表达式和一组 case 代码块,并执行第一个匹配到控制表达式的块。
  使用语法以下:

case CONTROL_EXPRESSION {
	case1: { ... }
	case2: { ... }
	case3: { ... }
	……
	default: { ... }
}

  其中,CONTROL_EXPRESSION的给定方式有以下三种:

  • 变量
  • 表达式
  • 有返回值的函数

  各case的给定方式有以下五种:

  • 直接字串;
  • 变量
  • 有返回值的函数
  • 正则表达式模式;
  • default

举例

vim case.pp
	case $osfamily {
		"RedHat": { $webserver='httpd' }
		/(?i-mx:debian)/: { $webserver='apache2' }
		default: { $webserver='httpd' }
	}

	package{"$webserver":
		ensure  => installed,    before  => [ File['httpd.conf'], Service['httpd'] ],
	}

	file{'httpd.conf':
		path    => '/etc/httpd/conf/httpd.conf',
		source  => '/root/manifests/httpd.conf',
		ensure  => file,
	}

	service{'httpd':
		ensure  => running,
		enable  => true,    restart => 'systemctl restart httpd.service',
		subscribe => File['httpd.conf'],
	}

3)selector 语句

  Selector 只能用于指望出现直接值(plain value) 的地方,这包括变量赋值、资源属性、函数参数、资源标题、其它 selector。
  selector 不能用于一个已经嵌套于于selector 的case 中,也不能用于一个已经嵌套于case 的case 语句中。
  具体语法以下:

CONTROL_VARIABLE ? {
	case1 => value1,
	case2 => value2,
	...
	default => valueN,
}

  其中,CONTROL_EXPRESSION的给定方式有以下三种:

  • 变量
  • 表达式
  • 有返回值的函数

  各case的给定方式有以下五种:

  • 直接子串;
  • 变量;
  • 有返回值的函数;
  • 正则表达式模式;
  • default

  selectors 使用要点:

  1. 整个selector 语句会被看成一个单独的值,puppet 会将控制变量按列出的次序与每一个case 进行比较,并在遇到一个匹配的 case 后,将其值做为整个语句的值进行返回,并忽略后面的其它 case。
  2. 控制变量与各 case 比较的方式与 case 语句相同,但若是没有任何一个 case 与控制变量匹配时,puppet 在编译时将会返回一个错误,所以,实践中,其必须提供default case。
  3. selector 的控制变量只能是变量或有返回值的函数,切记不能使用表达式。
  4. 其各 case 能够是直接值(须要加引号) 、变量、能调用返回值的函数、正则表达式模式或 default。
  5. 但与 case 语句所不一样的是,selector 的各 case 不能使用列表。
  6. selector 的各 case 的值能够是一个除了 hash 之外的直接值、变量、能调用返回值的函数或其它的 selector。

举例

vim selector.pp
	$pkgname = $operatingsystem ? {
		/(?i-mx:(ubuntu|debian))/       => 'apache2',
		/(?i-mx:(redhat|fedora|centos))/        => 'httpd',
		default => 'httpd',
	}
	package{"$pkgname":
		ensure  => installed,
	}
 

写在后面

  以上,咱们本次的介绍就告一段落,剩余的部分,请看下回分解。

做者:珂儿吖

出处:http://www.cnblogs.com/keerya/

本文版权归做者和博客园共有,欢迎转载,但未经做者赞成必须保留此段声明,且在文章页面明显位置给出原文链接,不然保留追究法律责任的权利。 你们写文都不容易,但愿尊重劳动成果哟~

相关文章
相关标签/搜索