linux - Chef/Bash 配方中的 String.Format 等价物

标签 linux chef-infra

在 Chef Recipe 中寻找类似于 .Net 字符串格式的内容,即。

string phone = String.format("phone: {0}",_phone);

我有一个 Chef Recipe ,我需要用其中的 30 个参数构建一个命令字符串,所以希望有一种整洁的方式来构建字符串,原则上我这样做
a=node['some_var'].to_s
ruby_block "run command" do
  block do
    cmd = shell_out!("node mycommand.js #{a}; exit 2;")           
  end
end

当我尝试这个时,我得到了错误

path.join 的参数必须是字符串 任何提示表示赞赏

最佳答案

Chef 分两个阶段运行:

编译并执行(见 https://www.chef.io/blog/2013/09/04/demystifying-common-idioms-in-chef-recipes/ 了解更多细节)。

您对 a 的变量赋值发生在编译时,例如当 Chef 加载所有 Recipe 时。 ruby block 将在收敛时以执行模式执行,无法访问变量 a .

所以最简单的解决方案可能是将属性放入 ruby​​ block 中:

   ruby_block "run command with argument #{node['some_var']}" do
     block do
       shell_out!("node mycommand.js #{node['some_var']}")
     end
   end

但是:
  • 如果您不需要执行 Ruby 代码,请考虑使用 executebash而是资源。
  • 请记住,如果要围绕它构建某种循环,则必须具有唯一的资源名称。一个简单的方法是在名称 ruby_block "something unique per loop iteration" do ... end 中加入一些独特的东西。
  • 我真正不明白的是你的退出代码2。这是一个错误代码。它会使 Chef 每次都抛出异常。 (shell_out! 如果退出代码 != 0 则抛出异常,参见 https://github.com/chef/chef/blob/master/lib/chef/mixin/shell_out.rb#L24-L28 )
  • 该资源将在每次 Chef 运行时执行。这可能不符合您的利益。考虑添加一个守卫(测试),以防止不必要的执行,见 https://docs.chef.io/resource_common.html#guards
  • 关于linux - Chef/Bash 配方中的 String.Format 等价物,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30617359/

    相关文章:

    linux - 通过 Jenkins SSH 插件连接和普通 ssh 之间的区别

    c++ - Linux中的UDP sendto是否会返回ENOBUFS?

    linux - 在没有 crontab 的情况下添加 cron 作业

    ruby - Chef 库其他 Recipe 库依赖

    solr - solr 查询中哪些特殊字符需要转义?

    ruby - 使用 Chef 角色插入属性

    php - 使用 UCLIBC 交叉编译 PHP

    linux - 如何在 linux 中递归重命名目录和子目录?

    Ruby 代码块和 Chef

    ruby - 在 Chef 中更改 ruby​​_block 中的权限时如何执行 "unless"条件?