首页 > 解决方案 > 自制的 ansible 模块不适用于 bash 脚本?

问题描述

我需要使用 bash 编写一个 ansible 模块(因为我不知道 python)。这是我在我的剧本中使用的 shell 模块:

   - name: Finding out what web server it uses
     shell: "lsof -i :80 | grep LISTEN | cut -d ' ' -f 1"
     register: result
   - name: output the result of what web server it uses
     debug: msg="{{ result.stdout_lines|first }}"

这是wbsrv.sh位于所需位置的 bash 脚本ansible.cfg

 #!/bin/bash
lsof -i :80 | grep LISTEN | cut -d ' ' -f 1
if [ $? == 0 ]; then
  printf '{"changed": true, "rc": 0}'
else
  printf '{"failed": true, "msg": "Something went wrong", "rc": 1}'
fi

所以我把我的剧本改成了这个

 - name: Finding out what web server it uses
     wbsrv:
     register: result
 - name: output the result of what web server it uses
   debug: msg="{{ result.stdout_lines|first }}"

当我运行剧本时,错误发生在“TASK [输出它使用的 Web 服务器的结果]”:

fatal: [vm2]: FAILED! => {"msg": "The task includes an option with an undefined variable. The error was: 'dict object' has no attribute 'stdout_lines'\n\nThe error appears to have been in '/home/ansible/wbsrvtest.yml': line 19, column 6, but may\nbe elsewhere in the file depending on the exact syntax problem.\n\nThe offending line appears to be:\n\n     register: result\n   - name: output the result of what web server it uses\n     ^ here\n\nexception type: <class 'ansible.errors.AnsibleUndefinedVariable'>\nexception: 'dict object' has no attribute 'stdout_lines'"}

我尝试删除 bash 脚本中的条件。我试着把echo而不是printf. 我还尝试将RESULT变量设置为等于脚本中的 bash 代码行,然后在 if 语句中回显它,但所有这些都返回了类似的错误。

标签: bashshellmoduleansible

解决方案


所以看起来你在这里发生了一些事情。调用 bash 脚本不需要像创建一个新模块那么复杂。如果要制作这样的模块,通常必须用 python 代码编写。

https://docs.ansible.com/ansible/2.3/dev_guide/developing_modules_general.html

但这并不需要那么难,您可以使用 ansibles 预先编写的模块来为您运行 bash 脚本。创建您的 bash 脚本,如果您不是仅针对 localhost 运行它,请使用复制模块将其放置在远程主机上,然后使用 shell 模块调用它,这将为您提供您正在寻找的输出为了。另外,我不知道这是否只是一个粘贴错误,但是您在示例中的缩进看起来不正确。Ansible 对缩进非常挑剔,因此模块名称的缩进不会超过“名称”指示符。所以你可以尝试这样的事情:

- name: Place shell script
  copy:
    src: < source file path >/wbsrv.sh 
    dest: < desired file location >/wbsrv.sh
    owner: < desired owner >
    group: < desired group >
    mode: < desired permissions >

- name: Finding out what web server it uses
  shell: < desired file location >/wbsrv.sh
  register: result

- name: output the result of what web server it uses
  debug: msg="{{ result.stdout }}"

如果您不想留下工件,只需运行另一个 shell 命令模块,删除您放置的 shell 脚本。此外,如果您打算让您的 shell 脚本仅输出一行,则无需执行 stdout_lines 并将其删减。如果你运行带有详细标志的剧本,你实际上可以在输出中看到 shell 命令的输出,从而不需要调试语句和寄存器(但它不会那么漂亮)。


推荐阅读