mage Ansible学习1 常用模块
一、Ansible特点
二、Ansible架构
1、core modules实现常用模块
2、Custom modules实现自定义模块
3、Connection Plugins 连接插件,可通过SSH或其它连接方式
4、Host Inventory 主机清单,我们只有列在清单中的主机才是那些通过连接插件连接过去管理的主机。
5、Playbooks:剧本,演戏时的剧本。某一个被管控的目标主机可能要实现的任务不只一个,比如我们要安装不只一个程序包,安装完后还要给其提供配置文件,然后还要创建出某个特定的用户,然后还要启动服务。每一步都要按照次序执行。所以我们ansible的核心操作就是要为每一个主机编辑其playbooks。把playbooks组织在角色中,然后定义好每一个主机扮演什么角色,而后把这样一个剧本扔给这个角色让角色执行就结束了,剧本是yaml格式的。
三、使用Ansible
1、使用阿里云yum源查看ansible版本
[root@localhost ~]# yum info ansible
2、我们现在有三台主机,node1,node2,node3 。node1和node2是被管控节点,node3是管控节点,也就是说我们只需要在node3上安装ansible即可。让其能基于ssh无秘钥连接被管控节点
a、首先在node3安装ansible
[root@node3 ~]# yum install -y ansible
b、查看ansible包信息
[root@node3 ~]# rpm -ql ansible |less /etc/ansible #配置文件目录 /etc/ansible/ansible.cfg #主配置文件 /etc/ansible/hosts #主机清单 /etc/ansible/roles #角色目录 /usr/bin/ansible #主程序 /usr/bin/ansible-2 /usr/bin/ansible-2.7 /usr/bin/ansible-config /usr/bin/ansible-connection ...
c、查看我们ansible配置文件信息,配置项选择默认即可
[root@node3 /]# cat /etc/ansible/ansible.cfg |grep -Ev "^#|^$" [defaults] roles_path = /etc/ansible/roles:/usr/share/ansible/roles #角色路径 [inventory] [privilege_escalation] [paramiko_connection] [ssh_connection] [persistent_connection] [accelerate] [selinux] [colors] [diff]
d、查看我们的主机清单文件
3、Ansible简单使用方式
a、相应参数
[root@node3 /]# ansible --help Usage: ansible <host-pattern>(要操作哪些主机) [options] Define and run a single task 'playbook' against a set of hosts Options: #通用选项 -a MODULE_ARGS, --args=MODULE_ARGS #传输给定模块的参数 module arguments --ask-vault-pass ask for vault password -B SECONDS, --background=SECONDS run asynchronously, failing after X seconds (default=N/A) -C, --check don't make any changes; instead, try to predict some of the changes that may occur #dry-run 干跑检查是否能执行。 -D, --diff when changing (small) files and templates, show the differences in those files; works great with --check -e EXTRA_VARS, --extra-vars=EXTRA_VARS set additional variables as key=value or YAML/JSON, if filename prepend with @ -f FORKS, --forks=FORKS #一批一批的执行,默认一批执行5个任务。 specify number of parallel processes to use (default=5) -h, --help show this help message and exit -i INVENTORY, --inventory=INVENTORY, --inventory-file=INVENTORY #指明主机清单文件是谁,如果不指名那就是默认的/etc/ansible/hosts specify inventory host path or comma separated host list. --inventory-file is deprecated -l SUBSET, --limit=SUBSET further limit selected hosts to an additional pattern --list-hosts outputs a list of matching hosts; does not execute anything else #列出匹配的目标主机 -m MODULE_NAME, --module-name=MODULE_NAME #指明要调用哪些模块 module name to execute (default=command) -M MODULE_PATH, --module-path=MODULE_PATH prepend colon-separated path(s) to module library (default=[u'/root/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']) --new-vault-id=NEW_VAULT_ID the new vault identity to use for rekey --new-vault-password-file=NEW_VAULT_PASSWORD_FILES new vault password file for rekey -o, --one-line condense output -P POLL_INTERVAL, --poll=POLL_INTERVAL set the poll interval if using -B (default=15) --syntax-check perform a syntax check on the playbook, but do not execute it #检查playbook的语法是否正确 -t TREE, --tree=TREE log output to this directory --vault-id=VAULT_IDS the vault identity to use --vault-password-file=VAULT_PASSWORD_FILES vault password file -v, --verbose verbose mode (-vvv for more, -vvvv to enable connection debugging) --version show program's version number and exit Connection Options: #连接相关的选项 control as whom and how to connect to hosts -k, --ask-pass ask for connection password --private-key=PRIVATE_KEY_FILE, --key-file=PRIVATE_KEY_FILE use this file to authenticate the connection -u REMOTE_USER, --user=REMOTE_USER connect as this user (default=None) -c CONNECTION, --connection=CONNECTION connection type to use (default=smart) -T TIMEOUT, --timeout=TIMEOUT override the connection timeout in seconds (default=10) --ssh-common-args=SSH_COMMON_ARGS specify common arguments to pass to sftp/scp/ssh (e.g. ProxyCommand) --sftp-extra-args=SFTP_EXTRA_ARGS specify extra arguments to pass to sftp only (e.g. -f, -l) --scp-extra-args=SCP_EXTRA_ARGS specify extra arguments to pass to scp only (e.g. -l) --ssh-extra-args=SSH_EXTRA_ARGS specify extra arguments to pass to ssh only (e.g. -R) Privilege Escalation Options: #权限升级方式 control how and which user you become as on target hosts -s, --sudo run operations with sudo (nopasswd) (deprecated, use become) -U SUDO_USER, --sudo-user=SUDO_USER desired sudo user (default=root) (deprecated, use become) -S, --su run operations with su (deprecated, use become) -R SU_USER, --su-user=SU_USER run operations with su as this user (default=None) (deprecated, use become) -b, --become run operations with become (does not imply password prompting) --become-method=BECOME_METHOD privilege escalation method to use (default=sudo), valid choices: [ sudo | su | pbrun | pfexec | doas | dzdo | ksu | runas | pmrun ] --become-user=BECOME_USER run operations as this user (default=root) --ask-sudo-pass ask for sudo password (deprecated, use become) --ask-su-pass ask for su password (deprecated, use become) -K, --ask-become-pass ask for privilege escalation password Some modules do not make sense in Ad-Hoc (include, meta, etc)
b、Ansible的简单使用格式
[root@node3 /]# ansible HOST-PATTERN(主机组) -m MOD_NAME(指明模块) -a MOD_ARGS(向模块传递参数) -f FORKS(一次操作多少台主机) -C(干跑模式) -u USERNAME(指明用户名) -c CONNECTION(指明连接方式,智能选择合适的链接方式)
4、配置秘钥认证
a、首先在node3上创建私钥文件
[root@node3 /]# ssh-keygen -t rsa -P "" Generating public/private rsa key pair. Enter file in which to save the key (/root/.ssh/id_rsa): Your identification has been saved in /root/.ssh/id_rsa. Your public key has been saved in /root/.ssh/id_rsa.pub. The key fingerprint is: SHA256:8YCeFqcL5th0aujydQuE4PqJnKHpKPwMOYArDQ1b5lo root@node3 The key's randomart image is: +---[RSA 2048]----+ | | | . | |o o o + | |oO . . = + | |=.E = * S . | |o*.O = . | |*=+ B o | |B**+ o . | |B**o . | +----[SHA256]-----+
b、设定管理员连接另外一台主机的方式,两台都是相同的方式
[root@node3 /]# ssh-copy-id -i ~/.ssh/id_rsa.pub root@192.168.10.13 /usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "/root/.ssh/id_rsa.pub "/usr/bin/ssh-copy-id: INFO: attempting to log in with the new key(s), to filter out any that are already installed/usr/bin/ssh-copy-id: INFO: 1 key(s) remain to be installed -- if you are prompted n ow it is to install the new keysroot@192.168.10.13's password: Number of key(s) added: 1 Now try logging into the machine, with: "ssh 'root@192.168.10.13'" and check to make sure that only the key(s) you wanted were added.
5、主机清单配置,任何主机想要被管理需要被定义在主机清单中。
a、直接将主机写进/etc/ansible/hosts
[root@node3 ~]# cat /etc/ansible/hosts |grep -Ev "^$|^#" 192.168.10.13 192.168.10.14 192.168.10.15
b、也可以用中括号分组
[root@node3 ~]# cat /etc/ansible/hosts |grep -Ev "^$|^#" [websrvs] 192.168.10.13 192.168.10.14 [dbsrvs] 192.168.10.15 192.168.10.14 #IP可以复用
6、使用ansible,相应模块介绍
a、ping:测试ping
[root@node3 ~]# ansible all -m ping 192.168.10.13 | SUCCESS => { "changed": false, "ping": "pong" } 192.168.10.14 | SUCCESS => { "changed": false, "ping": "pong" } 192.168.10.15 | SUCCESS => { "changed": false, "ping": "pong" }
查看有多少模块
[root@node3 ~]# ansible-doc --help
[root@node3 ~]# ansible-doc --help Usage: ansible-doc [-l|-s] [options] [-t <plugin type] [plugin] plugin documentation tool Options: -a, --all **For internal testing only** Show documentation for all plugins. -h, --help show this help message and exit -l, --list List available plugins -M MODULE_PATH, --module-path=MODULE_PATH prepend colon-separated path(s) to module library (default=[u'/root/.ansible/plugins/modules', u'/usr/share/ansible/plugins/modules']) -s, --snippet Show playbook snippet for specified plugin(s) :显示指定插件的剧本片段 -t TYPE, --type=TYPE Choose which plugin type (defaults to "module") -v, --verbose verbose mode (-vvv for more, -vvvv to enable connection debugging) --version show program's version number and exit See man pages for Ansible CLI options or website for tutorials https://docs.ansible.com
playbook首先是定义所期望的目标状态,然后操作必须是幂等的。
[root@node3 ~]# ansible-doc -s group - name: Add or remove groups group: gid: # Optional `GID' to set for the group. name: # (required) Name of the group to manage. state: # Whether the group should be present or not on the remote host. #存在或不存在 system: # If `yes', indicates that the group created is a system group. #这个组是不是系统组
b、group:创建用户组 mygrp
[root@node3 ~]# ansible all -m group -a "gid=3000 name=mygrp state=present system=no" #gid为3000,如果不指定就默认在现有gid后增加;名称为mygrp;状态为默认的present,即创建,若为absent则表示删除;是否为系统组选项为no。 192.168.10.15 | SUCCESS => { "changed": true, "gid": 3000, "name": "mygrp", "state": "present", "system": false } 192.168.10.13 | SUCCESS => { "changed": true, "gid": 3000, "name": "mygrp", "state": "present", "system": false } 192.168.10.14 | SUCCESS => { "changed": true, "gid": 3000, "name": "mygrp", "state": "present", "system": false }
看看用户组是否创建成功
[root@node3 ~]# ansible all -m shell -a "tail -1 /etc/group" 192.168.10.13 | SUCCESS | rc=0 >> mygrp:x:3000: 192.168.10.14 | SUCCESS | rc=0 >> mygrp:x:3000: 192.168.10.15 | SUCCESS | rc=0 >> mygrp:x:3000:
也可在/var/log/message中查看相应记录
[root@node2 ~]# tail /var/log/messages Oct 15 20:50:41 node2 python: ansible-group Invoked with state=absent gid=3000 system=False name=mygrp Oct 15 20:51:37 node2 kernel: hrtimer: interrupt took 13531131 ns Oct 15 20:51:41 node2 systemd-logind: Removed session 24. Oct 15 20:52:28 node2 systemd: Started Session 25 of user root. Oct 15 20:52:28 node2 systemd-logind: New session 25 of user root. Oct 15 20:52:28 node2 systemd: Starting Session 25 of user root. Oct 15 20:52:29 node2 python: ansible-group Invoked with state=present gid=3000 system=False name=mygrp Oct 15 20:52:47 node2 python: ansible-command Invoked with warn=True executable=None _uses_shell=True _raw_params=cat /etc/group removes=None creates=None chdir=None stdin=None Oct 15 20:52:57 node2 python: ansible-command Invoked with warn=True executable=None _uses_shell=True _raw_params=tail -1 /etc/group removes=None creates=None chdir=None stdin=None Oct 15 20:53:57 node2 systemd-logind: Removed session 25.
c、user:创建用户
[root@node3 ~]# ansible all -m user -a "uid=5000 name=testuser state=present groups=mygrp shell=/bin/tcsh" 192.168.10.15 | SUCCESS => { "changed": true, "comment": "", "createhome": true, "group": 5000, "groups": "mygrp", "home": "/home/testuser", "name": "testuser", "shell": "/bin/tcsh", "state": "present", "system": false, "uid": 5000 } 192.168.10.14 | SUCCESS => { "changed": true, "comment": "", "createhome": true, "group": 5000, "groups": "mygrp", "home": "/home/testuser", "name": "testuser", "shell": "/bin/tcsh", "state": "present", "system": false, "uid": 5000 } 192.168.10.13 | SUCCESS => { "changed": true, "comment": "", "createhome": true, "group": 5000, "groups": "mygrp", "home": "/home/testuser", "name": "testuser", "shell": "/bin/tcsh", "state": "present", "system": false, "uid": 5000 }
查看创建的用户
[root@node3 ~]# ansible all -m shell -a "id testuser && tail -1 /etc/passwd" 192.168.10.15 | SUCCESS | rc=0 >> uid=5000(testuser) gid=5000(testuser) groups=5000(testuser),3000(mygrp) testuser:x:5000:5000::/home/testuser:/bin/tcsh 192.168.10.14 | SUCCESS | rc=0 >> uid=5000(testuser) gid=5000(testuser) groups=5000(testuser),3000(mygrp) testuser:x:5000:5000::/home/testuser:/bin/tcsh 192.168.10.13 | SUCCESS | rc=0 >> uid=5000(testuser) gid=5000(testuser) groups=5000(testuser),3000(mygrp) testuser:x:5000:5000::/home/testuser:/bin/tcsh
d、copy:复制文件
[root@node3 ~]# ansible-doc -s copy - name: Copies files to remote locations copy: attributes: # Attributes the file or directory should have. To get supported flags look at the man page for `chattr' on the target system. This string should contain the attributes in the same order as the one displayed by `lsattr'. backup: # Create a backup file including the timestamp information so you can get the original file back if you somehow clobbered it incorrectly. content: # When used instead of `src', sets the contents of a file directly to the specified value. For anything advanced or with formatting also look at the template module. decrypt: # This option controls the autodecryption of source files using vault. dest: # (required) Remote absolute path where the file should be copied to. :文件要复制到哪儿去,如果源是一个目录的话那么目标必须就是一个目录 If `src' is a directory, this must be a directory too. If `dest' is a nonexistent path and if either `dest' ends with "/" or `src' is a directory, `dest' is created. If `src' and `dest' are files, the parent directory of `dest' isn't created: the task fails if it doesn't already exist. directory_mode: # When doing a recursive copy set the mode for the directories. If this is not set we will use the system defaults. The mode is only set on directories which are newly created, and will not affect those that already existed. follow: # This flag indicates that filesystem links in the destination, if they exist, should be followed. force: # the default is `yes', which will replace the remote file when contents are different than the source. If `no', the file will only be transferred if the destination does not exist. group: # Name of the group that should own the file/directory, as would be fed to `chown'. local_follow: # This flag indicates that filesystem links in the source tree, if they exist, should be followed. mode: # Mode the file or directory should be. For those used to `/usr/bin/chmod' remember that modes are actually octal numbers (like 0644). Leaving off the leading zero will likely have unexpected results. As of version 1.8, the mode may be specified as a symbolic mode (for example, `u+rwx' or `u=rw,g=r,o=r'). owner: # Name of the user that should own the file/directory, as would be fed to `chown'. remote_src: # If `no', it will search for `src' at originating/master machine. If `yes' it will go to the remote/target machine for the `src'. Default is `no'. Currently `remote_src' does not support recursive copying. selevel: # Level part of the SELinux file context. This is the MLS/MCS attribute, sometimes known as the `range'. `_default' feature works as for `seuser'. serole: # Role part of SELinux file context, `_default' feature works as for `seuser'. setype: # Type part of SELinux file context, `_default' feature works as for `seuser'. seuser: # User part of SELinux file context. Will default to system policy, if applicable. If set to `_default', it will use the `user' portion of the policy if available. src: # Local path to a file to copy to the remote server; can be absolute or relative.#本地目录,可以是相对也可以是绝对的,如果源文件不以斜线结尾的那么就把目录本身复制过去了,如果以斜线结尾那么就只复制目录下内容而不复制目录。 If path is a directory, it is copied recursively. In this case, if path ends with "/", only inside contents of that directory are copied to destination. Otherwise, if it does not end with "/", the directory itself with all contents is copied. This behavior is similar to Rsync. unsafe_writes: # Normally this module uses atomic operations to prevent data corruption or inconsistent reads from the target files, sometimes systems are configured or just broken in ways that prevent this. One example are docker mounted files, they cannot be updated atomically and can only be done in an unsafe manner. This boolean option allows ansible to fall back to unsafe methods of updating files for those cases in which you do not have any other choice. Be aware that this is subject to race conditions and can lead to data corruption. validate: # The validation command to run before copying into place. The path to the file to validate is passed in via '%s' which must be present as in the example below. The command is passed securely so shell features like expansion and pipes won't work.
[root@node3 ~]# ansible all -m copy -a "src=/etc/fstab dest=/tmp/fstab.ansible mode=600" 192.168.10.13 | SUCCESS => { "changed": true, "checksum": "89d0808ef2385b3f238e2c3db44b9c7670dd6d88", "dest": "/tmp/fstab.ansible", "gid": 0, "group": "root", "md5sum": "bc5dda5c7a4563573fb79ac3cc08d4ed", "mode": "0600", "owner": "root", "size": 465, "src": "/root/.ansible/tmp/ansible-tmp-1571146933.77-113790359734924/source", "state": "file", "uid": 0 } 192.168.10.15 | SUCCESS => { "changed": true, "checksum": "89d0808ef2385b3f238e2c3db44b9c7670dd6d88", "dest": "/tmp/fstab.ansible", "gid": 0, "group": "root", "md5sum": "bc5dda5c7a4563573fb79ac3cc08d4ed", "mode": "0600", "owner": "root", "size": 465, "src": "/root/.ansible/tmp/ansible-tmp-1571146933.72-201959469900611/source", "state": "file", "uid": 0 } 192.168.10.14 | SUCCESS => { "changed": true, "checksum": "89d0808ef2385b3f238e2c3db44b9c7670dd6d88", "dest": "/tmp/fstab.ansible", "gid": 0, "group": "root", "md5sum": "bc5dda5c7a4563573fb79ac3cc08d4ed", "mode": "0600", "owner": "root", "size": 465, "src": "/root/.ansible/tmp/ansible-tmp-1571146933.73-208452429531583/source", "state": "file", "uid": 0 }
查看copy结果
[root@node3 ~]# ansible all -m shell -a "ls -lh /tmp|grep fstab" 192.168.10.13 | SUCCESS | rc=0 >> -rw------- 1 root root 465 Oct 15 21:42 fstab.ansible 192.168.10.15 | SUCCESS | rc=0 >> -rw------- 1 root root 465 Oct 15 21:42 fstab.ansible 192.168.10.14 | SUCCESS | rc=0 >> -rw------- 1 root root 465 Oct 15 21:42 fstab.ansible
将/etc/pam.d 目录下的文件复制到所有节点的/tmp目录下
[root@node3 ~]# ansible all -m copy -a "src=/etc/pam.d/ dest=/tmp/" 192.168.10.13 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d/" } 192.168.10.15 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d/" } 192.168.10.14 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d/" }
将/etc/pam.d 目录复制到所有节点的/tmp目录下
[root@node3 ~]# ansible all -m copy -a "src=/etc/pam.d dest=/tmp/" 192.168.10.13 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d" } 192.168.10.15 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d" } 192.168.10.14 | SUCCESS => { "changed": true, "dest": "/tmp/", "src": "/etc/pam.d" } [root@node3 ~]# ls /tmp/ |grep pam pam.d
还可以直接生成文件的内容
[root@node3 ~]# ansible all -m copy -a "content='hi there \n' dest=/tmp/hi.txt" 192.168.10.13 | SUCCESS => { "changed": true, "checksum": "92a6180c01ee28d168da763431e37cb28de094a0", "dest": "/tmp/hi.txt", "gid": 0, "group": "root", "md5sum": "1c4c81e5c5e4b740bb33561c2f6d6722", "mode": "0644", "owner": "root", "size": 10, "src": "/root/.ansible/tmp/ansible-tmp-1571188267.99-61855119955295/source", "state": "file", "uid": 0 } 192.168.10.14 | SUCCESS => { "changed": true, "checksum": "92a6180c01ee28d168da763431e37cb28de094a0", "dest": "/tmp/hi.txt", "gid": 0, "group": "root", "md5sum": "1c4c81e5c5e4b740bb33561c2f6d6722", "mode": "0644", "owner": "root", "size": 10, "src": "/root/.ansible/tmp/ansible-tmp-1571188268.01-32198329634800/source", "state": "file", "uid": 0 } 192.168.10.15 | SUCCESS => { "changed": true, "checksum": "92a6180c01ee28d168da763431e37cb28de094a0", "dest": "/tmp/hi.txt", "gid": 0, "group": "root", "md5sum": "1c4c81e5c5e4b740bb33561c2f6d6722", "mode": "0644", "owner": "root", "size": 10, "src": "/root/.ansible/tmp/ansible-tmp-1571188267.96-73713190719989/source", "state": "file", "uid": 0 } [root@node3 ~]# ansible all -m shell -a "cat /tmp/hi.txt" 192.168.10.15 | SUCCESS | rc=0 >> hi there 192.168.10.13 | SUCCESS | rc=0 >> hi there 192.168.10.14 | SUCCESS | rc=0 >> hi there
e、fetch:从远程主机复制文件到本机
f、command:在远程主机上执行命令,不过其没法解析像shell中的管道符等特殊字符
[root@node3 ~]# ansible all -m command -a "ifconfig"
g、shell:执行命令
修改testuser密码
[root@node3 ~]# ansible all -m shell -a "echo wohaoshuai |passwd --stdin testuser " 192.168.10.15 | SUCCESS | rc=0 >> Changing password for user testuser. passwd: all authentication tokens updated successfully. 192.168.10.13 | SUCCESS | rc=0 >> Changing password for user testuser. passwd: all authentication tokens updated successfully. 192.168.10.14 | SUCCESS | rc=0 >> Changing password for user testuser. passwd: all authentication tokens updated successfully.
h、file:创建文件
创建目录
[root@node3 ~]# ansible all -m file -a "path=/var/tmp/hello.dir state=directory" 192.168.10.15 | SUCCESS => { "changed": true, "gid": 0, "group": "root", "mode": "0755", "owner": "root", "path": "/var/tmp/hello.dir", "size": 6, "state": "directory", "uid": 0 } 192.168.10.13 | SUCCESS => { "changed": true, "gid": 0, "group": "root", "mode": "0755", "owner": "root", "path": "/var/tmp/hello.dir", "size": 6, "state": "directory", "uid": 0 } 192.168.10.14 | SUCCESS => { "changed": true, "gid": 0, "group": "root", "mode": "0755", "owner": "root", "path": "/var/tmp/hello.dir", "size": 6, "state": "directory", "uid": 0 }
i、cron :计划任务。
每隔三分钟从192.168.10.15同步时间
[root@node3 ~]# ansible all -m cron -a "minute=*/3 job='/usr/sbin/update 192.168.10.15 &> /dev/null'" 192.168.10.15 | SUCCESS => { "changed": true, "envs": [], "jobs": [ "None" ] } 192.168.10.14 | SUCCESS => { "changed": true, "envs": [], "jobs": [ "None" ] } 192.168.10.13 | SUCCESS => { "changed": true, "envs": [], "jobs": [ "None" ] } [root@node3 ~]# ansible all -m shell -a "crontab -l" 192.168.10.15 | SUCCESS | rc=0 >> #Ansible: None */3 * * * * /usr/sbin/update 192.168.10.15 &> /dev/null 192.168.10.14 | SUCCESS | rc=0 >> #Ansible: None */3 * * * * /usr/sbin/update 192.168.10.15 &> /dev/null 192.168.10.13 | SUCCESS | rc=0 >> #Ansible: None */3 * * * * /usr/sbin/update 192.168.10.15 &> /dev/null
删除计划任务
[root@node3 ~]# ansible all -m cron -a "minute=*/3 job='/usr/sbin/update 192.168.10.15 &> /dev/null' name=None state=absent" 192.168.10.14 | SUCCESS => { "changed": true, "envs": [], "jobs": [] } 192.168.10.13 | SUCCESS => { "changed": true, "envs": [], "jobs": [] } 192.168.10.15 | SUCCESS => { "changed": true, "envs": [], "jobs": [] }
j、yum:安装程序包
所有主机安装一个nginx
[root@node3 ~]# ansible all -m yum -a "name=nginx state=installed"
k、service:管理服务
启动nginx服务
[root@node3 ~]# ansible all -m service -a "name=nginx state=started"
停止服务
[root@node3 ~]# ansible all -m service -a "name=nginx state=stopped"
l、script:执行脚本,会自动将本地的脚本copy到远程执行
[root@node3 ~]# ansible all -m script -a "/tmp/test.sh" 192.168.10.15 | SUCCESS => { "changed": true, "rc": 0, "stderr": "Shared connection to 192.168.10.15 closed.\r\n", "stdout": "", "stdout_lines": [] } 192.168.10.14 | SUCCESS => { "changed": true, "rc": 0, "stderr": "Shared connection to 192.168.10.14 closed.\r\n", "stdout": "", "stdout_lines": [] } 192.168.10.13 | SUCCESS => { "changed": true, "rc": 0, "stderr": "Shared connection to 192.168.10.13 closed.\r\n", "stdout": "", "stdout_lines": [] }