news 2026/4/23 17:18:30

6-ansible自动化运维

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
6-ansible自动化运维

ansible自动化运维

1、部署ansible

#安装软件,创建配置文件及域名解析[root@Rocky9 ~]dnf -yinstallansible#安装ansible软件[root@Rocky9 ~]mkdiransible#创建工作目录[root@Rocky9 ~]cdansible/[root@Rocky9 ansible]vimansible.cfg#创建配置文件[defaults]host_key_checking=false#不启用主机秘钥inventory=inventory#定义主机清单为当前目录的inventory #注意不能出现注释[root@Rocky9 ansible]viminventory#定义主机清单[webservers]web1ansible_host=192.168.88.110 web2ansible_host=192.168.88.120[clients]client1ansible_host=192.168.88.130[all:vars]ansible_user=rootansible_ssh_pass=666666#向/etc/hosts添加域名解析[root@Rocky9 ansible]sed-i'/::1/a 192.168.88.110 web1'/etc/hosts[root@Rocky9 ansible]sed-i'/::1/a 192.168.88.120 web2'/etc/hosts[root@Rocky9 ansible]sed-i'/::1/a 192.168.88.130 client'/etc/hosts[root@Rocky9 ansible]cat/etc/hosts127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4 ::1 localhost localhost.localdomain localhost6 localhost6.localdomain6192.168.88.130 client192.168.88.120 web2192.168.88.110 web1#设置免密登录[root@Rocky9 ansible]ssh-keygen#生成公钥私钥[root@Rocky9 ansible]ssh-copy-id192.168.88.130[root@Rocky9 ansible]ssh-copy-id192.168.88.110[root@Rocky9 ansible]ssh-copy-id192.168.88.120#测试连接[root@Rocky9 ansible]ansible all --list-hosts#查看可控主机hosts(3): web1 web2 client1[root@Rocky9 ansible]ansible all -mping#测试连接性

2、adhoc临时命令

语法:ansible 主机或组列表 -m 模块 -a"参数"# -a是可选的[root@Rocky9 ansible]ansible-doc -l|grepyum#根据名称查找模块[root@Rocky9 ansible]ansible-doc yum#查看帮助目录/EXAMPLES#使用查找功能,能查看使用案例

(1)command模块

[root@Rocky9 ansible]ansible all -mcommand-a"mkdir /root/abc.txt"#-m command可以省略不写web2|CHANGED|rc=0>>web1|CHANGED|rc=0>>client1|CHANGED|rc=0>>[root@Rocky9 ansible]ansible all -a"sudo shutdown -h now"#command模块不支持管道和重定向

(2)shell模块

#和command命令效果相似,支持管道和重定向[root@Rocky9 ansible]ansible all -m shell -a"cat /etc/passwd | wc -l"client1|CHANGED|rc=0>>20web2|CHANGED|rc=0>>20web1|CHANGED|rc=0>>20

(3)script模块

#执行shell脚本[root@Rocky9 ansible]vimtest.sh#!/bin/bashforiin{1..3}douseradduser$idone[root@Rocky9 ansible]ansible all -m script -a"test.sh"#执行脚本内容

(4)file模块

- 可以创建文件、目录、链接等,还可以修改权限、属性等 - 常用的选项: - path:指定文件路径 - owner:设置文件所有者 - group:设置文件所属组 - state:状态。touch表示创建文件,directory表示创建目录,link表示创建软链接,absent表示删除 - mode:设置权限 下面两个是创建软链接时使用的 - src:source的简写,源 - dest:destination的简写,目标[root@Rocky9 ansible]ansible all -mfile-a'name=/root/abc.txt state=touch'#创建文件[root@Rocky9 ansible]ansible all -mfile-a'name=/root/ab.d state=directory'#创建目录[root@Rocky9 ansible]ansible all -mfile-a'src=/etc/hostname dest=/root/haha state=link'#创建软链接

(5)copy模块

"用途:从ansible本机将文件复制到其他被控制的机器 src:源。控制端的文件路径 dest:目标。被控制端的文件路径 content:内容。需要写到文件中的内容 [root@Rocky9 ansible] ansible all -m copy -a 'src=/etc/hostname dest=/root/' #拷贝本机文件到目标机 [root@Rocky9 ansible] ansible all -m copy -a 'content="hahahhha"dest=/opt/abc'#直接写入内容到目标机文件

(6)fetch模块

"用途:将文件从被控制主机取回到ansible主机 src:源。被控制端的文件路径 dest:目标。控制端的文件路径[root@Rocky9 ansible]ansible all -m fetch -a'src=/etc/hostname dest=/root/'#将所有目标机的hostname文件保存到本机[root@Rocky9 ansible]ls/root anaconda-ks.cfg ansible client1 good web1 web2#每台主机的文件独立的目录

(7)lineinfile模块

"用途:用于确保存目标文件中有某一行内容,也可以替换一行 path:待修改的文件路径 line:写入文件的一行内容 regexp:正则表达式,用于查找文件中的内容 [root@Rocky9 ansible] ansible all -m lineinfile -a 'path=/etc/issue line="hello world"' #webservers组中的主机,/etc/issue中一定要有一行Hello World。如果该行不存在,则默认添加到文件结尾 [root@Rocky9 ansible] ansible all -m lineinfile -a 'path=/etc/issue line="ci le mei" regexp="hello"'#查找包含hello的行,将整行内容更换为ci le mei

(8)replace模块

"用途:replace可以替换关键词"path:待修改的文件路径 replace:将正则表达式查到的内容,替换成replace的内容 regexp:正则表达式,用于查找文件中的内容[root@Rocky9 ansible]ansible all -m replace -a'path=/etc/issue regexp="ci" replace="ccccccc"'#issue文件内的ci替换为ccccccc

(9)user模块

name:待创建的用户名 uid:用户ID group:设置主组 groups:设置附加组 home:设置家目录 password:设置用户密码 state:状态。present表示创建,它是默认选项。absent表示删除 remove:删除家目录、邮箱等。值为yes或true都可以。[root@Rocky9 ansible]ansible all -m user -a'name=abc state=present groups=bin'#创建用户,附加组设置为bin[root@Rocky9 ansible]ansible all -m user -a'name=user66 password={{"123"|password_hash("sha512") }}'[root@Rocky9 ansible]ansible webservers -m user -a"name=lisi uid=1010 group=adm groups=daemon,root home=/home/lisi"#创建用户指定名称、uid、基本组、附加组、家目录[root@Rocky9 ansible]ansible webservers -m user -a"name=zhangsan state=absent"#删除用户[root@Rocky9 ansible]ansible webservers -m user -a"name=lisi state=absent remove=yes"#删除用户同时删除家目录

(10)group模块

name:待创建的组名 gid:组的ID号 state:present表示创建,它是默认选项。absent表示删除[root@AAAAA ansible]ansible all -m group -a'name=group01 state=present'[root@R9 an]ansible all -m group -a'name=group01 state=absent'

(11)yum_repository模块

用于配置yum[root@R9 an]ansible all -mfile-a'path=/etc/yum.repos.d/rocky-lan.repo state=absent'#删除原来的yum源[root@R9 an]ansible all -m yum_repository -a'file=dvd.repo name=dvd description=appstream baseurl=file:///mnt/AppStream gpgcheck=no enabled=yes'[root@R9 an]ansible all -m yum_repository -a'file=dvd.repo name=dvd1 description=baseos baseurl=file:///mnt/BaseOS gpgcheck=no enabled=yes'#配置第二个库时,文件名一致[root@R9 an]ansible all -mmount-a'path=/mnt src=/dev/sr0 state=mounted fstype=iso9660'#永久挂载[root@R9 an]ansible all -a'yum repolist'client1|CHANGED|rc=0>>仓库id仓库名称 dvd appstream dvd1 baseos web2|CHANGED|rc=0>>仓库id仓库名称 dvd appstream dvd1 baseos web1|CHANGED|rc=0>>仓库id仓库名称 dvd appstream dvd1 baseos

(12)yum模块

用于安装软件 name:包名 state:状态。present表示安装,如果已安装则忽略;latest表示安装或升级到最新版本;absent表示卸载。[root@R9 an]ansible all -m yum -a'name=tar state=present'[root@R9 an]ansible all -m yum -a'name=net-tools,wget'[root@R9 an]ansible all -m yum -a'name=wget state=absent'

(13)service模块

用于控制服务。启动、关闭、重启、开机自启。 常用选项: name:控制的服务名 state:started表示启动;stopped表示关闭;restarted表示重启 enabled:yes表示设置开机自启;no表示设置开机不要自启。[root@R9 an]ansible all -mservice-a'name=httpd state=started enabled=yes'

(14)创建卷组lvg模块

创建、删除卷组,修改卷组大小 常用选项: vg:定义卷组名。vg:volume group pvs:由哪些物理卷构成。pvs:physical volumes[root@R9 an]ansible all -m yum -a'name=lvm2'[root@R9 an]ansible all -m lvg -a'vg=vg1 pvs=/dev/nvme0n2'#创建卷组[root@R9 an]ansible all -a'vgs'[root@R9 an]ansible all -m lvg -a'vg=vg1 pvs=/dev/nvme0n2,/dev/nvme0n3'#扩容卷组[root@R9 an]ansible all -m lvg -a'vg=vg1 state=absent'#删除卷组

(15)创建逻辑卷lvol模块

创建、删除逻辑卷,修改逻辑卷大小 常用选项: vg:指定在哪个卷组上创建逻辑卷 lv:创建的逻辑卷名。lv:logical volume size:逻辑卷的大小,不写单位,以M为单位[root@R9 an]ansible all -m lvol -a'vg=vg1 lv=lv1 size=2G'#创建逻辑卷[root@R9 an]ansible all -a'lvs'[root@R9 an]ansible all -m lvol -a'vg=vg1 lv=lv1 size=6G'#扩容逻辑卷[root@R9 an]ansible all -m lvol -a'vg=vg1 lv=lv1 state=absent force=yes'#删除逻辑卷

(16)格式化filesystem模块

用于格式化,也就是创建文件系统 常用选项: fstype:指定文件系统类型 dev:指定要格式化的设备,可以是分区,可以是逻辑卷[root@R9 an]ansible all -m filesystem -a'fstype=xfs dev=/dev/vg1/lv1'#格式化[root@R9 an]ansible all -a'blkid /dev/vg1/lv1'

(17)挂载mount模块

用于挂载文件系统 常用选项: path:挂载点。如果挂载点不存在,自动创建。 src:待挂载的设备 fstype:文件系统类型 state:mounted,表示永久挂载[root@R9 an]ansible all -mmount-a'path=/data src=/dev/vg1/lv1 state=mounted fstype=xfs'#挂载[root@R9 an]ansible all -mmount-a'path=/data state=absent'#卸载

(18)parted分区模块

用于硬盘分区管理 常用选项: device:待分区的设备 number:分区编号 state:present表示创建,absent表示删除 part_start:分区的起始位置,不写表示从开头 part_end:表示分区的结束位置,不写表示到结尾

(19)firewalld模块

用于配置防火墙的模块 常用选项: port:声明端口 permanent:永久生效,但不会立即生效 immediate:立即生效,临时生效 state:enabled,放行;disabled拒绝# 配置防火墙规则,放行http协议[root@pubserver ansible]# vim firewall.yml----name:configure webservershosts:webserverstasks:-name:install nginx pkg# 这里通过yum模块装httpdyum:name:nginxstate:present-name:start nginx service# 这里通过service模块启httpd服务service:name:nginxstate:startedenabled:yes-name:install firewalld pkg# 这里通过yum模块安装firewalldyum:name:firewalldstate:present-name:start firewalld service# 这里通过service模块启service服务service:name:firewalldstate:startedenabled:yes-name:set firewalld rules# 通过firewalld模块开放80端口firewalld:port:80/tcppermanent:yesimmediate:yesstate:enabled

(20)template模块

copy模块可以上传文件,但是文件内容固定 template模块可以上传具有特定格式的文件(如文件中包含变量) 当远程主机接收到文件之后,文件中的变量将会变成具体的值 template模块上传的文件,使用的语法叫Jinja2。 常用选项: src:要上传的文件 dest:目标文件路径# 使用template模块将含有变量的文件上传到webservers组中的主机[root@pubserver ansible]# vim index.htmlWelcome to{{ansible_hostname}}on{{ansible_eth0.ipv4.address}}[root@pubserver ansible]# vim templ.yml----name:upload indexhosts:webserverstasks:-name:create web indextemplate:src:index.htmldest:/usr/share/nginx/html/index.html

3、playbook

yaml文件的文件名,一般以yml或yaml作为扩展名 文件一般以---作为第一行,不是必须的,但是常用 键值对使用冒号:表示,冒号后面必须有空格。 数组使用-表示,-后面必须有空格。 相同的层级必须有相同的缩进。如果缩进不对,则有语法错误。每一级缩进,建议2个空格。 全文不能使用tab,必须使用空格。----name:testhosts:alltasks:-name:ping testping:

(1)文件处理剧本

# 在dbs组的主机和web1上创建/tmp/demo目录,权限是0755。将控制端/etc/hosts拷贝到目标主机的/tmp/demo中[root@R9 an]vim file.yaml----name:create fileshosts:alltasks:-name:dirfile:path:/tmp/demostate:directorymode:'0755'-name:cpcopy:src:/etc/hostsdest:/tmp/dem
# 在webservers组中的主机上,创建用户bob,附加组是adm;在db1主机上,创建/tmp/hi.txt,其内容为Hello World.[root@R9 an]vim test02.yaml----name:userhosts:webserverstasks:-name:useruser:name:bobgroups:adm-name:filehosts:clientstasks:-name:filecopy:content:"hello world"dest:/tmp/hi.txt
#通过copy模块创建/tmp/1.txt,文件中有两行内容,分别是Hello World和ni hao[root@R9 an]touch /root/1.txt[root@R9 an]vim test03.yaml----name:1hosts:alltasks:-name:1-1copy:dest:/root/1.txtcontent:|hello world nihao

(2)用户管理剧本

#在webservers组中的主机上创建john用户,它的uid是1040,主组是daemon,密码为123、[root@R9 an]vimtest04.yaml --- - name:1hosts: webservers tasks: - name:1-1 user: name:joinuid:1040password:"{{'123'|password_hash('sha512')}}"- name:1-2 group: name: daemony

(3)磁盘管理剧本

[root@R9 an]vim test05.yaml----name:1hosts:alltasks:-name:parted#分区1parted:device:/dev/nvme0n2number:1part_end:1GiBstate:present-name:new parted#第二次分区parted:device:/dev/nvme0n2number:2part_start:1GiBpart_end:6GiBstate:present-name:create vg#创建卷组vg1lvg:vg:vg1pvs:/dev/nvme0n2p1,/dev/nvme0n2p2-name:create lv#创建逻辑卷lvol:vg:vg1lv:lv1size:1G-name:filesystem#格式化文件系统filesystem:fstype:xfsdev:/dev/vg1/lv1-name:mounted#挂载mount:path:/datasrc:/dev/vg1/lv1state:mountedfstype:xfs

(4)软件安装剧本

# 在webservers组中的主机上,安装httpd、php、php-mysqlnd[root@R9 an]vim pkg.yaml----name:install pkghosts:alltasks:-name:install pkgyum:name:httpd,php,php-mysqlndstate:present-name:install groupyum:name:"@Development Tools"-name:updateyum:name:"*"state:latest

4、ansible变量

(1)facts变量

常用的facts变量 ansible_all_ipv4_addresses:所有的IPV4地址 ansible_bios_version:BIOS版本信息 ansible_memtotal_mb:总内存大小 ansible_hostname:主机名[root@R9 an]ansible webservers -m setup#查看所有facts变量[root@R9 an]ansible webservers -m setup -a"filter=ansible_all_ipv4_addresses"#查看所有的IPV4地址,filter是过滤的意思[root@pubserver ansible]ansible webservers -m setup -a"filter=ansible_memfree_mb"# 查看可用内存# 显示远程主机的主机名和内存大小。在ansible中,变量使用{{}}表示# debug模块用于输出信息,常用的参数是msg,用于输出指定内容[root@pubserver ansible]# vim debug.yml--- - name: displayhostinfo hosts: webservers tasks: - name: displayhostnameand memory debug:# debug是模块,它的选项msg可以输出指定信息msg:"hostname: {{ansible_hostname}}; mem: {{ansible_memtotal_mb}} MB"

(2)inventory变量

# 使用inventory变量。[root@pubserver ansible]# vim inventory[webservers]web1 web2[dbs]db1 username="wangwu"# 定义主机变量的方法[webservers:vars]# 定义组变量的方法,:vars是固定格式username="zhaoliu"# 通过变量创建用户[root@pubserver ansible]# vim var1.yml----name:webservers create userhosts:webserverstasks:-name:create useruser:name:"{{username}}"state:present-name:create user in dbshosts:dbstasks:-name:create some usersuser:name:"{{username}}"state:present

(3)playbook定义变量

# 在webservers组中的主机上创建用户jack,他的密码是123456[root@pubserver ansible]# vim user_jack.yml----name:create userhosts:webserversvars:# 固定格式,用于声明变量username:"jack"# 此处引号可有可无mima:"123456"# 此处引号是需要的,表示数字字符tasks:-name:create some usersuser:name:"{{username}}"# {}出现在开头,必须有引号state:presentpassword:"{{mima|password_hash('sha512')}}"

(4)在文件中定义变量

# 将变量定义在文件中[root@pubserver ansible]# vim vars.yml # 文件名自定义---yonghu:rosemima:abcd[root@pubserver ansible]# vim user_rose.yml----name:create userhosts:webserversvars_files:vars.yml# vars_files用于声明变量文件tasks:-name:create some usersuser:name:"{{yonghu}}"# 这里的变量来自于vars.ymlstate:presentpassword:"{{mima|password_hash('sha512')}}"

5、进阶语法

(1)错误处理

# 编辑myerr.yml,如果myslqd服务无法启动,则忽略它[root@pubserver ansible]# vim myerr.yml----name:my errorshosts:webserverstasks:-name:start mysqld serviceservice:name:mysqldstate:startedenabled:yesignore_errors:yes# 即使这个任务失败了,也要继续执行下去-name:touch a filefile:path:/tmp/service.txtstate:touch#通过全局设置,无论哪个任务出现问题,都要忽略[root@pubserver ansible]# vim myerr.yml----name:my errorshosts:webserversignore_errors:yestasks:-name:start mysqld serviceservice:name:mysqldstate:startedenabled:yes-name:touch a filefile:path:/tmp/mysql.txtstate:touch

(2)触发执行任务

通过handlers定义触发执行的任务 handlers中定义的任务,不是一定会执行的 在tasks中定义的任务,通过notify关键通知handlers中的哪个任务要执行 只有tasks中的任务状态是changed才会进行通知。# 修改Playbook,只有配置文件变化了,才重启服务[root@pubserver ansible]# vim trigger.yml----name:configure nginxhosts:webserversvars:http_port:"80"tasks:-name:upload nginx.conftemplate:src:./nginx.confdest:/etc/nginx/nginx.confnotify:restart nginx# 通知restart httpd需要执行handlers:-name:restart nginxservice:name:nginxstate:restarted# 第一次运行Playbook,因为第1个任务是黄色的changed,所以handlers中的任务也被触发执行

(3)when条件

只有满足某一条件时,才执行任务 常用的操作符: ==:相等!=:不等>:大于 <:小于 <=:小于等于>=:大于等于 多个条件或以使用and或or进行连接 when表达式中的变量,可以不使用{{}}# 当dbs组中的主机内存大于2G的时候,才安装mysql-server[root@pubserver ansible]# vim when1.yml----name:install mysql-serverhosts:dbstasks:-name:install mysql-server pkgyum:name:mysql-serverstate:presentwhen:ansible_memtotal_mb>2048# 如果目标主机没有2GB内存,则不会安装mysqld-server# 多条件。系统发行版是Rocky8才执行任务# /etc/motd中的内容,将会在用户登陆时显示在屏幕上[root@pubserver ansible]# vim motd_____________ < hello world>-------------\ ^__^ \ (oo)\_______ (__)\ )\/\||----w|||||[root@pubserver ansible]# vim when2.yml----name:when conditionhosts:webserverstasks:-name:modify /etc/motdcopy:dest:/etc/motdsrc:motdwhen:># 以下三行合并成一行ansible_distribution == "Rocky" and ansible_distribution_major_version == "8"

(4)regitster注册变量

register是一个关键字,可以将任务执行的结果赋值给指定的变量名称。这个变量可以在后续任务中使用。 register模块可以捕获各种类型的输出,包括stdout、stderr、rc、changed等。它可以与其他模块一起使用,例如“when”条件、“loop”循环等。# 在web1组的主机上执行任务,创建/tmp/regfile1.txt,并打印创建结果[root@pubserver ansible]# vim reg1.yml----name:create file /tmp/regfile1.txthosts:web1tasks:-name:create filefile:path:/tmp/rgefile1.txtstate:touchregister:result-name:display outputdebug:msg:"{{result}}"# 在web1主机上执行任务,创建文件/tmp/ademo/abc。如果创建不成功,则通过debug输出create failed[root@pubserver ansible]# vim reg2.yml----name:create file /tmp/ademo/abchosts:web1ignore_errors:yestasks:-name:create filefile:path:/tmp/ademo/abcstate:touchregister:result-name:debug outputdebug:msg:"create failed"when:result.failed

(5)block任务快

可以通过block关键字,将多个任务组合到一起 可以将整个block任务组,一起控制是否要执行# 如果webservers组中的主机系统发行版是Rocky,则安装并启动nginx[root@pubserver ansible]# vim block1.yml----name:block taskshosts:webserverstasks:-name:define a group of tasksblock:-name:install nginx# 通过yum安装nginxyum:name:nginxstate:present-name:start nginx# 通过service启动nginx服务service:name:nginxstate:startedenabled:yeswhen:ansible_distribution=="Rocky"# 条件为真才会执行上面的任务

(6)rescue和always

block和rescue、always联合使用: block中的任务都成功,rescue中的任务不执行 block中的任务出现失败(failed),rescue中的任务执行 block中的任务不管怎么样,always中的任务总是执行[root@pubserver ansible]# vim block2.yml----name:block testhosts:webserverstasks:-name:block / rescue / always test1block:-name:touch a filefile:path:/tmp/test1.txtstate:touchrescue:-name:touch file test2.txtfile:path:/tmp/test2.txtstate:touchalways:-name:touch file test3.txtfile:path:/tmp/test3.txtstate:touch# 执行playbook web1上将会出现/tmp/test1.txt和/tmp/test3.txt

(7)loop循环

相当于shell中for循环 ansible中循环用到的变量名是固定的,叫item# 在test组中的主机上创建5个目录/tmp/{aaa,bbb,ccc,ddd,eee}[root@pubserver ansible]# vim loop1.yml----name:use loophosts:webserverstasks:-name:create directoryfile:path:/tmp/{{item}}state:directoryloop:[aaa,bbb,ccc,ddd,eee]# 上面写法,也可以改为:----name:use loophosts:webserverstasks:-name:create directoryfile:path:/tmp/{{item}}state:directoryloop:-aaa-bbb-ccc-ddd-eee# 使用复杂变量。创建zhangsan用户,密码是123;创建lisi用户,密码是456# item是固定的,用于表示循环中的变量# 循环时,loop中每个-后面的内容作为一个整体赋值给item。# loop中{}中的内容是自己定义的,写法为key:val# 取值时使用句点表示。如下例中取出用户名就是{{item.uname}}[root@pubserver ansible]# vim loop_user.yml----name:create usershosts:webserverstasks:-name:create multiple usersuser:name:"{{item.uname}}"password:"{{item.upass|password_hash('sha512')}}"loop:-{"uname":"zhangsan","upass":"123"}-{"uname":"lisi","upass":"456"}

(8)role角色

为了实现playbook重用,可以使用role角色 角色role相当于把任务打散,放到不同的目录中 再把一些固定的值,如用户名、软件包、服务等,用变量来表示 role角色定义好之后,可以在其他playbook中直接调用# 使用常规playbook,修改/etc/motd的内容# 1. 创建motd模板文件[root@pubserver ansible]# vim motdHostname:{{ansible_hostname}}# facts变量,主机名Date:{{ansible_date_time.date}}# facts变量,日期Contact to:{{admin}}# 自定义变量# 2. 编写playbook[root@pubserver ansible]# vim motd.yml----name:modifty /etc/motdhosts:webserversvars:admin:root@tedu.cn# 自定义名为admin的变量tasks:-name:modify motdtemplate:src:motddest:/etc/motd[root@pubserver ansible]# ansible-playbook motd.yml[root@web1 ~]# cat /etc/motdHostname:web1Date:2021-11-01Contact to:root@tedu.cn# 创建角色# 1. 声明角色存放的位置[root@pubserver ansible]# vim ansible.cfg[defaults]inventory = hosts roles_path = roles# 定义角色存在当前目录的roles子目录中# 2. 创建角色目录[root@pubserver ansible]# mkdir roles# 3. 创建名为motd的角色[root@pubserver ansible]# ansible-galaxy init roles/motd[root@pubserver ansible]# ls roles/motd# 生成了motd角色目录[root@pubserver ansible]# yum install -y tree[root@pubserver ansible]# tree roles/motd/roles/motd/ ├── defaults# 定义变量的目录,优先级最低│ └── main.yml ├── files# 保存上传的文件(如copy模块用到的文件)├── handlers# handlers任务写到这个目录的main.yml中│ └── main.yml ├── meta# 保存说明数据,如角色作者、版本等│ └── main.yml ├── README.md# 保存角色如何使用之类的说明├── tasks# 保存任务│ └── main.yml ├── templates# 保存template模块上传的模板文件├── tests# 保存测试用的playbook。可选│ ├── inventory │ └── test.yml └── vars# 定义变量的位置,推荐使用的位置└── main.yml# 4. 将不同的内容分别写到对应目录的main.yml中# 4.1 创建motd模板文件[root@pubserver ansible]# vim roles/motd/templates/motdHostname:{{ansible_hostname}}Date:{{ansible_date_time.date}}Contact to:{{admin}}# 4.2 创建变量[root@pubserver ansible]# vim roles/motd/vars/main.yml # 追加一行admin:zzg@tedu.cn# 4.3 创建任务[root@pubserver ansible]# vim roles/motd/tasks/main.yml # 追加-name:modify motdtemplate:src:motd# 这里的文件,自动到templates目录下查找dest:/etc/motd# 5. 创建playbook,调用motd角色[root@pubserver ansible]# vim role_motd.yml----name:modify motd with rolehosts:webserversroles:-motd# 6. 执行playbook[root@pubserver ansible]# ansible-playbook role_motd.yml
版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/21 2:33:19

基于Spring Boot+Vue的大型超市前后台系统

目录 项目介绍 演示视频 系统展示 代码实现 推荐项目 项目开发总结 为什么选择我 源码获取 博主介绍&#xff1a;✌全网粉丝30W,csdn特邀作者、博客专家、CSDN新星计划导师、Java领域优质创作者,博客之星、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领…

作者头像 李华
网站建设 2026/4/23 10:15:16

RN 图像处理(裁剪、压缩、滤镜)性能很差怎么办?

[toc] 在 React Native 项目里&#xff0c;只要碰到“图片处理”四个字&#xff0c;十有八九跑不掉一句话&#xff1a;卡。尤其是裁剪、压缩、批量处理大图的时候&#xff0c;JS 线程基本“当场升天”&#xff0c;UI 直接卡住不动。 为什么 React Native 在图片处理上这么吃力&…

作者头像 李华
网站建设 2026/4/23 14:27:51

锐角三角函数学习笔记(1)

一、定义 sin&#xff08;正弦&#xff09;对边/斜边 cos&#xff08;余弦&#xff09;邻边/斜边 tan&#xff08;正切&#xff09;对边/邻边 cot&#xff08;余切&#xff09;邻边/对边 变形&#xff1a; 对边sin斜边 邻边cos斜边 对边tan邻边二、特殊角的三角函数 ①30 sin30…

作者头像 李华
网站建设 2026/4/23 12:53:03

YOLOv11涨点改进 | 全网独家创新、Neck特征融合改进篇 | TGRS 2025 | 引入STFFM 时空特征融合模块创新点,通过注意力引导融合,背景噪声抑制,促进小目标特征增强,助力有效涨点

一、本文介绍 🔥本文给大家介绍使用STFFM(时空特征融合模块) 改进YOLOv11网络模型,可在特征提取阶段实现空间外观信息与时间序列信息的早期融合,使模型由单纯的空间建模扩展为时空联合建模。STFFM 通过注意力机制引导网络在关键空间位置和有效特征通道上自适应地融合空间…

作者头像 李华
网站建设 2026/4/23 12:58:18

车联网隐私保护认证区块链实验复现方案

车联网隐私保护认证区块链实验复现方案 一、项目概述与目标 1.1 研究背景 车联网(IoV)作为智能交通系统的核心组成部分,面临着严峻的隐私保护和认证安全挑战。传统的中心化认证机制存在单点故障、隐私泄露等问题。区块链技术以其去中心化、不可篡改的特性,为车联网提供了…

作者头像 李华
网站建设 2026/4/23 12:56:54

19、将 Snort 规则转换为 iptables 规则

将 Snort 规则转换为 iptables 规则 在网络安全领域,我们常常需要使用入侵检测和预防系统来保障网络的安全。Snort 是一款知名的入侵检测系统(IDS),而 iptables 则是 Linux 系统中常用的防火墙工具。将 Snort 规则转换为 iptables 规则,能够结合两者的优势,增强网络的安全…

作者头像 李华