Vagrant:多机环境下 Shell Provisioner 操作

Vagrant:多机环境下 Shell Provisioner 操作

我正在构建一个多机器环境,并且对 Vagrantfile 处理过程中看到的行为感到困惑。

我的目标:创建 n 个具有 3 个不同角色的虚拟机。所有 n 个虚拟机将使用一个通用的“bootstrap.sh”脚本,然后每个角色将根据主机名/角色运行另一个脚本。

Vagrantfile 在这里: Vagrant文​​件

所有单独的部分/部分都正常工作,脚本运行,并在正确的 VM 中创建了正确的数量的额外磁盘。我想了解的是为什么“内联”配置程序的行为不同,如何确保特定于角色的脚本在正确的时间运行。

第一个问题——为什么这段代码只执行一次?

      config.vm.provision "Setup shell environment", type: "shell" do |s|
    s.inline = <<-SHELL
      # Install some tools
      #yum install -y net-tools traceroute git ansible gcc make python > /dev/null 2>&1 
      # Add the public key
      mkdir /root/.ssh
      chmod 700 /root/.ssh
      touch /root/.ssh/authorized_keys
      echo "Appending user@Laptop keys to root and vagrant authorized_keys"
      echo #{ssh_pub_key} >> /home/vagrant/.ssh/authorized_keys
      echo #{ssh_pub_key} >> /root/.ssh/authorized_keys
      echo "Appending AdminVM keys to root and vagrant authorized_keys"
      echo #{adminvm_karlvkey} >> /home/vagrant/.ssh/authorized_keys
      echo #{adminvm_karlvkey} >> /root/.ssh/authorized_keys
      echo #{adminvm_rootkey} >> /home/vagrant/.ssh/authorized_keys
      echo #{adminvm_rootkey} >> /root/.ssh/authorized_keys

      # Copy /etc/hosts
      #if [ -e /vagrant/files/hosts ]
      #  then sudo cat /vagrant/files/hosts >> /etc/hosts
      #elif [ -e /home/vagrant/sync/files/hosts ]
      #  then sudo cat /home/vagrant/sync/files/hosts >> /etc/hosts
      #fi     
    SHELL
  end # inline shell provisioner config.provision

但是,这会对已解析的哈希中的每个元素执行一次?因此,对于哈希中的第一个 VM,“admin”,一切正常。但是在后续迭代中,它会对前面的每个元素运行一次?因此,到第六个 VM 时,它会运行六次。

 config.vm.provision :shell, :path => "../../scripts/bash/config/bootstrap.sh"

这些也一样:

  # - OSD Node
  if ("#{servers["name"]}").include? "osd"
    puts "I'm an OSD"
    puts servers["name"]
    config.vm.provision :shell, :path => "../../scripts/bash/ceph/osd.sh"
  end

我怀疑我没能理解这里的一些基本原理。我搜索了整个互联网,甚至搜索到了互联网的边缘,但找不到一个很好的解释。

答案1

这将阻止 bootscrap.sh 脚本多次运行:

  config.vm.provision "bootstrap", type: "shell" do |script|
     script.path = "../../scripts/bash/config/bootstrap.sh"
  end

我仍然不知道如何让这些停止执行。我想我明白为什么它们每次都会被执行,只是不确定如何停止它。它们只需要在配置的 VM 上和引导脚本之后运行。我不可能是唯一一个想要这样做的人,我只是找不到任何地方的记录。

  if ("#{servers["name"]}").include? "osd"
    config.vm.provision "Configure OSD Node", type: "shell" do |script|
       script.path = "../../scripts/bash/ceph/osd.sh"
    end
  end

  # - Monitor Node
  if ("#{servers["name"]}").include? "mon"
    config.vm.provision "Configure Monitor Node", type: "shell" do |script|
       script.path = "../../scripts/bash/ceph/monitor.sh"
    end
  end

  # - Admin Node
  if ("#{servers["name"]}").include? "admin"
    config.vm.provision "Configure Admin Node", type: "shell" do |script|
       script.path = "../../scripts/bash/ceph/admin.sh"
    end
  end

答案2

最终解决方案:

  ### External shell scripts for configuration
  # - Run on every node
  config.vm.provision "bootstrap", type: "shell" do |script|
     script.path = "../../scripts/bash/config/bootstrap.sh"
  end

  # Role based setup is in the servers.yml file - pull it out as a key:value
  config.vm.provision "Role", type: "shell" do |script|
     script.path = "../../scripts/bash/ceph/#{servers["script"]}"
  end

我有一个“servers.yml”文件,我向其中添加了 VM 的另一个属性“script”。然后我只需在 script.path 中明确调用它即可。

现在一切都运行正常并且我的 Vagrantfile 已更新。

相关内容