首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何在Ansible的shell配置中防止条件命令求值?

问如何在Ansible的shell配置中防止条件命令求值?
EN

Stack Overflow用户
提问于 2019-10-09 18:04:50
回答 2查看 58关注 0票数 1

我有以下多机Vagrant设置:

代码语言:javascript
复制
Vagrant.configure(2) do |config|

  config.vm.define "xfcevm" do |xfcevm|
    xfcevm.vm.box = "generic/ubuntu1904"
    xfcevm.vm.hostname = "xfcevm"
    config.vm.provider "virtualbox" do |vb|
      vb.name = "ubuntu-xfce"
    end
  end

  config.vm.define "kdevm" do |kdevm|
    kdevm.vm.box = "generic/arch"
    kdevm.vm.hostname = "kdevm"
    config.vm.provider "virtualbox" do |vb|
      vb.name = "arch-kde"
    end
  end

  ## only Arch doesn't ship with Python installed
  config.vm.provision "shell", inline: "which python || sudo pacman --noconfirm -S python"

  config.vm.provider "virtualbox" do |vb|
    vb.gui = true
    vb.memory = "2048"
    vb.cpus = 1
    vb.customize ["modifyvm", :id, "--vram", "32"]
  end

  config.vm.provision "ansible" do |ansible|
    ansible.verbose = "v"
    ansible.compatibility_mode = "2.0"
    ansible.playbook = "setup.yml"
    ansible.inventory_path = "hosts"
  end

end

由于Arch vagrant box不包含Python,因此我创建了一个内联外壳配置命令,该命令应该测试Python的存在(由which python执行),如果结果为false,则应随后进行Python的pacman安装。对于回显输出,不应该计算第二部分,这是通过在终端中运行命令来实现的。

但是,不管||是否存在,shell provisioner都会在Python后对该部分进行评估。在Ubuntu的情况下,它引发了一个明显的错误,因为pacman没有被安装:

代码语言:javascript
复制
$ vagrant up --provision
Bringing machine 'xfcevm' up with 'virtualbox' provider...
Bringing machine 'kdevm' up with 'virtualbox' provider...
==> xfcevm: Checking if box 'generic/ubuntu1904' version '1.9.34' is up to date...
==> xfcevm: Running provisioner: shell...
    xfcevm: Running: inline script
    xfcevm: sudo
    xfcevm: : 
    xfcevm: pacman: command not found
The SSH command responded with a non-zero exit status. Vagrant
assumes that this means the command failed. The output for this command
should be in the log above. Please read the output to determine what
went wrong.

同样的道理也适用于简单的if语句,而不是||

代码语言:javascript
复制
config.vm.provision "shell", inline: "if [ ! `which python` ]; then sudo pacman --noconfirm -S python; fi"
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2019-10-10 00:04:57

实际的问题是两件事的结合:在Arch中使用python作为Python3的别名(与Ubuntu相反,在Ubuntu中python是Python2的别名),以及Ubuntu不随Python2一起提供的事实(我们不需要它用于任何目的,我们使用Python3)。

因此,解决方案是同时检查python和python3

代码语言:javascript
复制
config.vm.provision "shell", inline: "if [ ! `which python`] && [ ! `which python3` ]; then sudo pacman --noconfirm -S python; fi"
票数 1
EN

Stack Overflow用户

发布于 2019-10-10 00:08:14

在我的机器上使用以下Vagranfile进行测试后:

代码语言:javascript
复制
 Vagrant.configure(2) do |config|
     config.vm.box = "generic/ubuntu1904"
     config.vm.hostname = "test"
     config.vm.network "private_network", type: "dhcp"
     config.vm.synced_folder ".", "/vagrant", disabled: true
     config.vm.provider "virtualbox" do |v|
         v.memory = 2048
         v.cpus = 2
     end
     config.vm.provision "default", type: "shell", inline: "which python", run: "always"
 end

这是vagrant up的结果(仅最后一行)

代码语言:javascript
复制
==> default: Running provisioner: default (shell)...
    default: Running: inline script
The SSH command responded with a non-zero exit status. Vagrant
assumes that this means the command failed. The output for this command
should be in the log above. Please read the output to determine what
went wrong.

交互检查:

代码语言:javascript
复制
$ vagrant ssh
Last login: Wed Oct  9 15:33:22 2019 from 10.0.2.2
vagrant@test:~$ which python
vagrant@test:~$ echo $?
1
vagrant@test:~$ which python3
/usr/bin/python3
vagrant@test:~$ echo $?
0
vagrant@test:~$

结论:你得到的是完全连贯的。python不存在于您的ubuntu镜像中,因此您的命令的其余部分将被运行。你的方案有一个缺陷,你需要找到另一种方法。

在您的上下文中,我会尝试在ansible中运行所有内容。这里有一个我没有测试的例子,它肯定可以得到很大的改进

代码语言:javascript
复制
- name: Make sure machine can run ansible
  hosts: all
  gather_facts: false

  tasks:
    - block:
        - name: Try to ansible-ping the host. Consider python is not installed otherwise
          ping:

      rescue:
        - name: No python available, install with low-level and dirty command
          become: true
          become_method: sudo
          raw: pacman --noconfirm -S python
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/58301725

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档