使用lineinfile和blockinfile编辑文件或只使用模板复制整个文件?

时间:2016-02-04 13:11:24

标签: ansible configuration-management

我开始使用Ansible来编写一个将为我们的应用程序部署暂存环境的剧本。 我试图了解应用文件更改的最佳做法是在控制计算机上本地更改它们,然后将它们传播到远程服务器,或者是否应该在剧本中操作这些文件。

在可读性和文档方面,通过playbook操作文件似乎更好,并且将整个配置过程保持为整个配置过程的一个工具。 另一方面,更改本地服务器上的文件更容易,更快。

解决这些问题的最佳方法是什么?

谢谢, 亚龙。

4 个答案:

答案 0 :(得分:2)

欢迎来到Ansible!

我认为你应该看看模板。切勿在本地更改文件并部署它们。您的部署不应在本地更改任何文件!

如果您有配置文件,请为此文件编写模板并在其中呈现一些变量以更改已部署应用程序的配置。模板模块将直接将文件呈现给您的服务器。

答案 1 :(得分:1)

使用lineinfileblockinfile (ansible > 2.0)。它更清洁,便携,可以从任何控制机器运行。但是当块很大时会有异常。

答案 2 :(得分:0)

模板应该是您的首选。它们使用起来更简单,并且您知道在播放剧本后主机将具有准确的配置。

当我有一个遗留系统,我需要保留许多主机上的文件有很多更改时,我发现自己只能使用lineinfileblockinfile作为后备。

尽可能将模板渲染到linux上的配置目录。例如。不要在lineinfile上使用/etc/sudoers添加管理员帐户,将帐户的模板呈现给/etc/sudoers.d/administrators

答案 3 :(得分:0)

正如其他答案已经告诉你的那样,copytemplate模块是使用Ansible操作配置文件的首选方式。

它们允许您预先准备整个文件,然后将其移动到您的服务器(它们之间的区别是template模块允许您使用变量,而copy模块将文件复制为是)。

由于您可以完全控制文件,因此没有任何意外。

但是,(通常情况下)有些情况禁止使用这些模块:

  • 操纵同一文件的不同角色
  • 处理遗留系统
  • 为不同的服务器(在某种程度上)需要不同版本的文件

在这种情况下,我喜欢以防弹方式使用lineinfile模块:

  • 首先删除除要添加的指令
  • 之外的所有指令
  • 然后在特定位置添加该行

举个例子,拿一个sshd_config文件。您可能希望确保服务器仅侦听IP地址1.2.3.4

- name: Remove lines with unwanted occurrences of ListenAddress
  lineinfile: dest=/etc/ssh/sshd_config
              regexp="^ListenAddress (?!1\.2\.3\.4)"
              state=absent

- name: Listen on 1.2.3.4
  lineinfile: dest=/etc/ssh/sshd_config
              line="ListenAddress 1.2.3.4"
              insertafter="^#?AddressFamily"

第一个任务删除了ListenAddress的每次出现,它没有指定我们想要的IP(使用名为negative lookahead的正则表达式结构)。

然后第二个任务直接在以ListenAddress 1.2.3.4开头的行之后插入正确的指令(AddressFamily)(评论与否)。

这样,您的任务保持幂等性,您可以确定您不知道的文件中没有ListenAddress指令。

如果您需要更多详细信息,我就此主题撰写了an article。如果您尝试部署的应用程序是用Rails编写的,您可能会对我撰写的关于此主题的书Efficient Rails DevOps感兴趣。