如何使用Ansible自动执行一次性任务?

时间:2015-04-28 06:44:23

标签: shell path ansible ansible-playbook

我正在使用Ansible为我们的一些构建环境自动化VM配置,例如设置PATH和代理环境变量,安装全局Node.js工具等。这很好用,并且很容易在多个主机上自动执行常见的设置任务。所有任务都通过Ansible roles分开,以分离职责和额外的可重用性。

现在我遇到了以下问题:安装了新软件包后,我需要更改PATH环境变量 - 它不再需要我之前作为Ansible安装程序的一部分添加的条目。

很自然地,我继续更新了我用来为新环境设置PATH变量的Ansible任务,并删除了自定义条目(我使用lineinfile任务来创建PATH条目。)

lineinfile:
    dest: ~/.profile
    regexp: "^export {{ item.regexp }}"
    line: "export {{ item.line }}"
    create: yes
  with_items:
    - { regexp: 'PATH', line: 'PATH=:~/bin:~/node_modules/.bin:$PATH' }

我从项目的上述line部分删除了一个条目。如您所见,lineinfile任务仅检查文件中是否存在条目export PATH,如果不存在,则会使用export PATH=:~/bin:~/node_modules/.bin:$PATH创建条目。

现在我的问题:由于lineinfile任务仅验证条目是否存在,但未检查完整值,我需要确保更新所有现有环境。我该怎么做?

是否有办法使lineinfile语句足够智能以验证行的内容,即确保存在我想要的确切行(同时避免重复PATH项)?或者这太复杂了?

我想到的另一件事(最终确实如此)是创建一个在所有环境中更新PATH变量的一次性剧本:

lineinfile:
    dest: ~/.profile
    backrefs: yes
    regexp: "^export PATH=(.*)/opt/foo/bar/baz/bin[\\:]*(.*)"
    line: "export PATH=\\1\\2"

这是一个常见的场景 - 为一次性任务创建剧本吗?好处是该剧本在所有主机上运行,​​避免了手动工作。除此之外的可重用性很小,因为我只希望这样做一次。

这是解决这个问题的正确方法,还是有更好,更聪明的方式来完成这样的任务?

2 个答案:

答案 0 :(得分:2)

您使用的是哪个版本的Ansible?由于您所描述的内容看起来像一个错误,因为lineinfile模块应检测到该行已更改并更新它。我只是复制粘贴你的第一个任务(只是改变了文件的路径),一切正常。

这是第一次运行:

➜  ~  % ansible-playbook test.yml

PLAY [all] ********************************************************************

TASK: [lineinfile ] ***********************************************************
changed: [localhost] => (item={'regexp': 'PATH', 'line': 'PATH=:~/bin:~/node_modules/.bin:$PATH'})

PLAY RECAP ********************************************************************
localhost                  : ok=1    changed=1    unreachable=0    failed=0

我从路径中删除~/bin并再次运行整个事情:

➜  ~  % ansible-playbook test.yml

PLAY [all] ********************************************************************

TASK: [lineinfile ] ***********************************************************
changed: [localhost] => (item={'regexp': 'PATH', 'line': 'PATH=:~/node_modules/.bin:$PATH'})

PLAY RECAP ********************************************************************
localhost                  : ok=1    changed=1    unreachable=0    failed=0

如您所见,模块检测到我更改了变量并更新了文件。所以一切正常。

答案 1 :(得分:0)

我不太确定我完全理解你的问题,但其中任何一个都会工作......

(1)在.profile中有一条专用行,用于添加删除的路径。因此,除PATH中的所有其他.profile内容外,您还有一行

export PATH=~/foo/removable:$PATH  # ANSIBLE MANAGED

您使用line_in_file模块添加和删除。

(2)使用/etc/profile.d目录,然后添加(通过copytemplate) and remove a file / etc / profile.d / temporary-path.sh that contains your temporary出口`声明。

相关问题