SaltStack 与 Ansible 选择?

对于统一管理工具大家会选择什么?最近比较亲来SaltStack 与Ansible。主要是因为他们都是Python写的而且较新,网上评论也很好。但是二者不知道选哪个好。二者都尝试过,但是由于是在学习环境,没有生产环境的检验不知道哪个更好。目前的感觉是1)Ansible是有个公司在支持,可能支持比较好。2)Ansible不用安装客户端,但是在ssh 公钥被禁的情况下就头大了。3)Ansible的资料较少而且官网doc非常卡。 欢迎大家用过SaltStack、Pupp…
关注者
317
被浏览
76587

8 个回答

身边有很多运维工程师,做了几年的运维自动化,但依然不能确定选择哪个工自动化工作?还有,怎样更优雅的实施运维自动化和避免事实当中的坑?

前两天我们一个Linux运维的社群组织了一场微信的讲座,恰好说到这个问题,可以供大家参考,本次分享邀请的是一个一线的运维工程师,他叫张强,马哥教育Linux大咖讲堂金牌讲师,现就职于伙伴智慧运维工程师,负责主线业务平台,3年linux一线经验,擅长shell脚本、自动化_发布、web应用等,现在关注自动化运维、分布式数据库,虚拟化技术。

内容基于一线分享的体验,每个人体验不同,欢迎大家交流。

——————

首先,我们来看一看自动化工具的比较:

Puppet也许是四款工具中最深入人心的。就可用操作、模块和用户界面而言,它是最全面的。Puppet呈现了数据中心协调的全貌,几乎涵盖每一个运行系统,为各大操作系统提供了深入的工具。初始设置比较简单,只需要在需要加以管理的每个系统上安装主服务器和客户端代理软件。命令行接口(CLI)简单直观,允许通过puppet命令下载和安装模块。然后,需要对配置文件进行更改,好让模块适合所需的任务;应接到指令的客户端与主服务器联系时,会更改配置文件,或者客户端通过立即触发更改配置文件的推送(push)来进行更改。

Ansible关注的重点是力求精简和快速,而且不需要在节点上安装代理软件。因此,Ansible通过SSH执行所有功能。需要管理的节点被添加到Ansible配置环境,SSH授权密钥被附加到每个节点上,这与运行Ansible的用户有关。一旦完成了这步,Ansible主服务器可以通过SSH与节点进行通信,执行所有必要的任务。Ansible可以使用Paramiko(基于SSH2协议的Python实现)或标准SSH用于通信,不过还有一种加速模式,允许更快速、更大规模的通信。

Salt类似Ansible,因为它也是基于CLI的工具,采用了推送方法实现客户端通信。它可以通过Git或通过程序包管理系统安装到主服务器和客户端上。客户端会向主服务器提出请求,请求在主服务器上得到接受后,就可以控制该客户端了。Salt可以通过普通的SSH与客户端进行通信,但如果使用名为minion的客户端代理软件,可以大大增强可扩展性。此外,Salt含有一个异步文件服务器,可以为客户端加快文件服务速度,这完全是Salt注重高扩展性的一个体现。与Ansible一样,你可以直接通过CLI,向客户端发出命令,比如启动服务或安装程序包;你也可以使用名为state的YAML配置文件,处理比较复杂的任务。还有“pillar”,这些是放在集中地方的数据集,YAML配置文件可以在运行期间访问它们。

总结:个人观点puppet最大缺点就是默认情况下Agent每隔30分钟向master同步状态,master主动推送功能比较薄弱(2.7版本),ansible基于SSH服务执行,如果服务器过多不建议使用,他是使用轮训的方式。Salt基于消息队列。性能相当好,适合大量生产环境。

SaltStack简介与特性

SaltStack 是一种基于 C/S 架构的服务器基础架构集中化管理平台,管理端称为 Master,客户端称为 Minion。SaltStack 具备配置管理、远程执行、监控等功能,一般可以理解为是简化版的 Puppet 和加强版的 Func。SaltStack 本身是基于 Python 语言开发实现,结合了轻量级的消息队列软件 ZeroMQ 与 Python 第三方模块(Pyzmq、PyCrypto、Pyjinjia2、python-msgpack 和 PyYAML 等)构建。

通过部署 SaltStack 环境,运维人员可以在成千上万台服务器上做到批量执行命令,根据不同的业务特性进行配置集中化管理、分发文件、采集系统数据及软件包的安装与管理等。

SaltStack 具有以下特性:

1、部署简单、方便;

2、支持大部分UNIX/Linux及Windows环境;

3、主从集中化管理;

4、配置简单、功能强大、扩展性强;

5、主控端(master)和被控端(minion)基于证书认证,安全可靠。

6、支持API及自定义模块,可通过Python轻松扩展。

SaltStack 的工作原理

SaltStack 采用 C/S 结构来对云环境内的服务器操作管理及配置管理。为了更好的理解它的工作方式及管理模型,将通过图形方式对其原理进行阐述。

SaltStack 客户端(Minion)在启动时,会自动生成一套密钥,包含私钥和公钥。之后将公钥发送给服务器端,服务器端验证并接受公钥,以此来建立可靠且加密的通信连接。同时通过消息队列 ZeroMQ 在客户端与服务端之间建立消息发布连接。具体通信原理图,如图 1 所示,命令执行如图 2 所示:

专业术语说明:

Minion 是 SaltStack 需要管理的客户端安装组件,会主动去连接 Master 端,并从 Master 端得到资源状态信息,同步资源管理信息。

Master 作为控制中心运行在主机服务器上,负责 Salt 命令运行和资源状态的管理。

ZeroMQ 是一款开源的消息队列软件,用于在 Minion 端与 Master 端建立系统通信桥梁。

Daemon 是运行于每一个成员内的守护进程,承担着发布消息及通信端口监听的功能。

原理图说明:

Minion 是 SaltStack 需要管理的客户端安装组件,会主动去连接 Master 端,并从 Master 端得到资源状态信息,同步资源管理信息。

Master 作为控制中心运行在主机服务器上,负责 Salt 命令运行和资源状态的管理。

Master 上执行某条指令通过队列下发到各个 Minions 去执行,并返回结果。

SaltStack 的架构设计

为了让大家更好的理解 SaltStack 集中化管理方面的优势,因此,根据项目的实际情况绘制了部署架构图,并在文中对架构图进行了详细说明。如图 3 所示:

说明:

SaltStack 的所有被管理客户端节点(如图 3 所示 DB 和 Web),都是通过密钥进行加密通信,使用端口为 4506。客户端与服务器端的内容传输,是通过消息队列完成,使用端口为 4505。Master 可以发送任何指令让 Minion 执行,salt 有很多可执行模块,比如说 CMD 模块,在安装 minion 的时候已经自带了,它们通常位于你的 python 库中,locate salt | grep /usr/ 可以看到 salt 自带的所有东西。

为了更好的理解架构用意,以下将展示主要的命令发布过程:

SaltStack 的 Master 与 Minion 之间通过 ZeroMq 进行消息传递,使用了 ZeroMq 的发布订阅模式,连接方式包括 TCP 和 IPC。

Salt 命令,将 cmd.run ls 命令从 salt.client.LocalClient.cmd_cli 发布到 Master,获取一个 Jodid,根据 jobid 获取命令执行结果。

Master 接收到命令后,将要执行的命令发送给客户端 minion。

Minion 从消息总线上接收到要处理的命令,交给 minion._handle_aes 处理。

Minion._handle_aes 发起一个本地线程调用 cmdmod 执行 ls 命令。线程执行完 ls 后,调用 Minion._return_pub 方法,将执行结果通过消息总线返回给 master。

Master 接收到客户端返回的结果,调用 master.handle_aes 方法将结果写的文件中。

Salt.client.LocalClient.cmd_cli 通过轮询获取 Job 执行结果,将结果输出到终端。

SaltStack 的安装与配置

对 SaltStack 有了一个初步的了解之后,通过实际案例操作进一步了解 SaltStack。

一、安装Salt

Salt需要epel源支持,所有安装前需要先安装epel源包。

1、salt-master

# yum -y install salt-master

2、salt-minion

# yum -y install salt-minion

二、配置Salt

1、master(/etc/salt/master)

# salt运行的用户,影响到salt的执行权限

user: root

#salt的运行线程,开的线程越多一般处理的速度越快,但一般不要超过CPU的个数

worker_threads: 10

# master的管理端口

publish_port : 4505

# master跟minion的通讯端口,用于文件服务,认证,接受返回结果等

ret_port : 4506

# 如果这个master运行的salt-syndic连接到了一个更高层级的master,那么这个参数需要配置成连接到的这个高层级master的监听端口

syndic_master_port : 4506

# 指定pid文件位置

pidfile: /var/run/salt-master.pid

# saltstack 可以控制的文件系统的开始位置

root_dir: /

# 日志文件地址

log_file: /var/log/salt_master.log

# 分组设置

nodegroups:

group_all: '*'

# salt state执行时候的根目录

file_roots:

base:

- /etc/salt/

# 设置pillar 的根目录

pillar_roots:

base:

- /etc/pillar

2、配置minion(/etc/salt/minion)

master: mail #这块的mail指的是在/etc/hosts文件中所定义的主机名

id: node1

3、启动salt

service salt-master start

service salt-minion start

# saltstack 是使用python2的语言编写,对python3的兼容性不好,请使用python2的环境

4、认证命令介绍

salt-key #证书管理

# salt-key –L #查看所有minion-key

# salt-key –a #接受某个minion-key

# salt-key –A #接受所有minion-key

# salt-key –d #删除某个minion-key

# salt-key –D #删除所有minion-key

5、salt命令介绍

命令格式:salt [options] [arguments]

例:salt \* cmd.run 'uptime'

SaltStack minion匹配方式

1、 Glob(salt默认的target类型,使用shell的通配符来指定一个或多个Minion ID)

# salt \* test.ping 或 salt ‘*’ test.ping

2、pcre兼容正则表达式

# salt –E ‘^[m|M]in.[e|o|u]n$’ test.ping

3、Subnet(通过指定一个IPv4地址或一个CIDR的IPv4子网)

# salt –S 192.168.0.42 test.ping

# salt –s 192.168.0.0/16 test.ping

4、Grains(salt可以通过操作系统、CPU架构及自定义信息等机器特征进行target Minion)

# salt –G ‘os:Ubuntu’ test.ping

# Salt –G ‘os_family:Debian’ test.ping

5、pillar(salt支持通过pillar数据进行匹配)

# Salt –I ‘my_val:my_val’ test.ping

6、混合(compound)

# Salt –C ‘web* or G@os:Arch’ test.ping

7、节点组(Nodegroup)

节点组需要事先定义,配置方法如下:

# vim /etc/salt/master

nodegroups:

node: 'L@node1,node2’

# salt -N node test.ping

SaltStack常用模块

1、status模块(查看系统信息)

# salt "*" status.diskstats #查看磁盘信息

# salt "*" status.meminfo #查看内存信息

# salt "*" status.w #w命令返回信息

2、查看所有module列表

3、查看指定module的所有function方法

4、查看指定module用法

5、具体模块的使用(例子)

同时到指定机器查看

cmd.run模块的使用

Grains

Static bits of information that a minion collects about the system when the minion first starts.

The grains interface is made available to Salt modules and components so that the right salt minion commands are automatically available on the right systems.

以上是官方的解释,大致意思是说grains是minion第一次启动的时候采集的静态数据,可以用在salt的模块和其他组件中。例如,当os_family的Grain数据为Centos时,则会使用yum工具组件来进行软件包管理。Grains会在Minion进程启动时加载,并缓存在内存中。这样salt-minion进程就无须每次操作都重新检索系统来获取Grain,极大的提高了Minion的性能。

1、我们这里简单做一个输出测试,可以看到minion节点的一些信息如下:

查看具体每一项信息

2、应用场景:

grains的特性–每次启动汇报、静态决定了它没有pillar灵活,要知道pillar是随时可变的,只要在master端修改了那一般都会立刻生效的。所以grains更适合做一些静态的属性值的采集,例如设备的角色(role),磁盘个数(disk_num),操作系统版本等诸如此类非常固定的属性。简单总结起来grains的用途如下:

(1),grains可以在state系统应用中,用户配置管理模块。

(2),grains可以在target中使用,用来匹配minion,比如os,用-G。

(3),grains可以用于信息查询,grains保存着收集到的客户端的信息。

那么我们就可以得到一个大致的判断,如果你想定义的属性值是经常变化的,那请采用pillar,如果是很固定、不易变的那请用grains。

3、grains优先级

grains可以保持在minion端、通过master端下发等多个方式来分发。但不同的方法有不同的优先级的(由低到高):

(1). /etc/salt/grains

(2) /etc/salt/minion

(3)./srv/salt/_grains/ master端_grains目录下

优先级顺序依次为存在在minion端/etc/salt/minion配置文件中的同名grains会覆盖/etc/salt/grains文件中的值,而通过master端_grains目录下grains文件下发的值可以会覆盖minion端的所有同名值。比较拗口,总之记得,通过master下发的grains优先级是最高的可,/etc/salt/minion次之,/etc/salt/grains最低(core grains不大懂,就不讨论了,这个比/etc/salt/grains还低)。

4、grains的下发

grains的下发大致可以分为两个思路:

(1)自定义的(_grains)可以通过state.highstate、saltutil.sync_grains、saltutil.sync_all 等方法批量下发,切记所有在_grains目录下的所有自定义grains值都会下发到minion,这是血的教训。

(2)固定存放在minion端配置文件中,如grains、minion文件中,可以通过file manager的方法去批量下发/etc/salt/grains等配置文件实现grains的批量下发,当然了也通过别的方式把这个文件批量下发下去,都是ok的。

对比:

(1)通过state.highstate 下发的grains好处是无须重启minion即可生效,但通过下发/etc/salt/grains文件下发的grains值则必须重启minion端服务才可以生效。

(2)自定义的_grains每次在highstate调用的时候就会自动下发、刷新,而/etc/salt/grains文件的则不会。

Pillar

在大多数场景中,Pillar的表现行为和Grain一致,但有个很大的区别是:Pillar在Master上进行定义,存在于一个集中化的路径。Pillar数据是与特定minion关联的,也就是说每一个minion都只能看到自己的数据,所以Pillar可以用来传递敏感数据(在Salt的设计中,Pillar使用独立的加密session,也是为了保证敏感数据的安全性)。

Pillar可以用在那些地方:

1、敏感数据

例如ssh key,加密证书等,由于Pillar使用独立的加密session,可以确保这些敏感数据不被其他minion看到。

2、变量

可以在Pillar中处理平台差异性,比如针对不同的操作系统设置软件包的名字,然后在State中引用。

3、其他任何数据

可以在Pillar中添加任何需要用到的数据。比如定义用户和UID的对应关系,mnion的角色等。

4、用在Targetting中

Pillar可以用来选择minion,使用-I选项。

定义Pillar:

master配置文件中定义:

默认情况下,master配置文件中的所有数据都添加到Pillar中,且对所有minion可用。如果要禁用这一默认值,可以在master配置文件中添加如下数据,重启服务后生效:

pillar_opts: False

使用SLS文件定义Pillar

Pillar使用与State相似的SLS文件。Pillar文件放在master配置文件中pillar_roots定义的目录下。示例如下:

pillar_roots:

base:

- /srv/pillar

下面这段代码定义了base环境下的Pillar文件保存在/srv/pillar/目录下。与State相似,Pillar也有top file,也使用相同的匹配方式将数据应用到minion上。示例如下:

# cat /srv/pillar/top.sls:

base:

'*':

- packages

# cat /srv/pillar/packages.sls:

{% if grains['os'] == 'RedHat' %}

apache: httpd

git: git

{% elif grains['os'] == 'Debian' %}

apache: apache2

git: git-core

{% endif %}

base环境中所有的minion都具有packages中定义的数据。Pillar采用与file server相同的文件映射方式,在本例中,packages映射到文件/srv/pillar/packages.sls。注意key与value要用冒号加空格分隔,没有空格的话将解析失败。

如何知道minion拥有那些Pillar数据?

在Master上修改pillar文件后,需要用以下命令刷新minion上的数据:

使用Pillar获取自定义数据:

State

简述:SLS(代表SaLt State文件)是Salt State系统的核心。SLS描述了系统的目标状态,由格式简单的数据构成。这经常被称作配置管理

top.sls是配置管理的入口文件,一切都是从这里开始,在master 主机上,默认存放在/srv/salt/目录.

top.sls 默认从 base 标签开始解析执行,下一级是操作的目标,可以通过正则,grain模块,或分组名,来进行匹配,再下一级是要执行的state文件,不包换扩展名。

创建/srv/salt/top.sls

state实战

我们前阵子在做DevOps这块的调研,应该说在中小规模的公司里,Saltstack和Ansible这两块选用的人都不少。

大家选择这两个平台所做的依据,其实上面各个答主也基本都有提到。
1、是否需要每台机器部署agent(客户端)
很多选用ansible的朋友,都是因为agentless这个原因,觉得要维护agent很麻烦。
而一些使用saltstack比较顺的朋友,觉得这个问题无所谓,agent出问题的概率有,但不高。

其实ansible也支持agent的方式,即所谓的“pull”的模式,就是通过一个客户端去拉取要执行的任务。

2、大规模并发的能力
这方面的对比已经比较多了,因为实现机制的差异,也导致saltstack在这方面是占优的。
不过对于几十台-200台规模的兄弟来讲,ansible的性能也可接受。

注:我前期调研的大多数都是中下企业,服务器规模一般不超过200台,所以对这个问题不算太看重。如果一次操作的机器过千台,可能还是用saltstack效率更高一些。

补充-20161114:我们正在改造ansible的执行架构,采用基于MQ的agent机制,以支持比较大规模(1000-10000台)的服务器的批量自动化运维。这样,在这种存在大规模运维的需求的客户这里,也可以应用丰富的ansible的Playbook了。

3、二次开发扩展的能力
ansible和saltstack都是基于python的,而python在运维开发这个圈子里接受度还是非常高的,二次开发的人员相对也好招。
这也是这两个工具相对于puppet和chef更容易被接受度原因,这两个曾经的主流工具都是基于ruby,而现在ruby的活跃度越来越低了,要招人也不容易。

ansible和saltstack都具备很好的二次开发扩展能力,可以写YAML编排。

4、开源社区的对接
在github上,ansbile有18300多颗星,salt有6700多颗星。
直接按关键字搜索,ansible的相关项目也更多一些。

这些指标虽然不能直接说明什么,但很多技术人员会关注自己所使用的技术的活跃度。
一般来说,越活跃的开源项目,得到的关注会更高些,功能完善和问题解决的效率也会更高。

5、学习的门槛
从第一次使用来讲,ansible的部署配置会更简单一些。
从官方文档的质量来看,saltstack就比ansible要好一些。

从国内的中文资料来说,ansbile和saltstack好像各有2-3本中文书。
这两家的国内用户组也分别在做一些技术资料翻译的工作。

6、操作界面的友好程度
试用过Ansible的Tower,但实在是不喜欢这种操作习惯,只能说勉强可用。
saltstack的没仔细用过,但看过朋友搭建的环境,感觉官方的UI还可以,基本够用了。

Ansible的最初设计定位就不是一个完整的运维管理系统,因此官方UI粗糙些也在预料之中。

7、第三方工具的丰富程度
ansibe有一个galaxy站点:Ansible Galaxy
这个站点集合了3000多个第三方开发的Role/Playbook。

salt也有一些预先写好的Formulas(Formulas are pre-written Salt States)
官方地址:Salt Formulas
github地址:Salt Stack Formulas · GitHub
目前已有的Formulas大概在200个左右,比ansible galaxy少了一个数量级,不过大部分常用软件也覆盖到了。

8、现有用户使用的规模
根据rightscale的调研报告:
Ansible在2015年有10%的用户选用,而2016年有20%的用户选用。
Saltstack在2015年有6%的用户选用,而2016年有9%的用户选用。

9、对Windows支持的友好程度
这一方面我没有直接的经验,感谢 @小菘Barry 提供的如下反馈:
“ansible对windows的支持简直不忍直视,agentless只是对于linux的,windows要安装bug修复补丁,powershell还要3.0,还要安装python。还不如salt方便。”
这一点供大家参考。

我们自己目前是用的Ansible,但正在结合我们自己的DevOps平台,重新给Ansible开发一套WEB UI。