厨师:为什么我没有读入我刚刚设置的属性值?

Chef: Why am I not reading in the attribute value I just set?

我的工作让我的脚趾被厨师弄湿了,我的任务是安装制作配方,在我们的机器上使用自定义配置安装 telegraf。我也没有 ruby 经验作为序言。

在下载或安装 telegraf 之前,我想验证 if telegraf 是否存在,以便仅在版本不匹配时才执行以下所有工作。

所以我试图在配方运行时设置一个其他资源将检查的属性。

ruby_block 'get telegraf version' do
  block do
      #tricky way to load this Chef::Mixin::ShellOut utilities
      Chef::Resource::RubyBlock.send(:include, Chef::Mixin::ShellOut)
      command = 'C:\Program Files\telegraf\telegraf.exe --version'
      command_out = shell_out(command)
      node.default['windows']['telegraf']['installed_version'] = 'good'
  end
  notifies :write, 'log[log_version]', :delayed
  action :run
  only_if { ::File.exists?('C:\Program Files\telegraf\telegraf.exe')}
end

log 'log_version' do
    message node['windows']['telegraf']['installed_version']
    level :error
end

当我查看输出时,虽然我看到

     * ruby_block[get telegraf version] action run[2018-07-23T14:48:11-07:00] INFO: Processing ruby_block[get telegraf version] action run (win-telegraf::telegraf line 26)
   [2018-07-23T14:48:11-07:00] INFO: ruby_block[get telegraf version] called

       - execute the ruby block get telegraf version
     * log[log_version] action write[2018-07-23T14:48:11-07:00] INFO: Processing log[log_version] action write (win-telegraf::telegraf line 39)
   [2018-07-23T14:48:11-07:00] ERROR:

那么,为什么当我阅读 node['windows']['telegraf']['installed_version'] 时,日志什么也不打印,而不是 'good'?

Chef 使用二次加载系统,查看 https://coderanger.net/two-pass/ 了解更多详情。但是这种情况的 tl;dr 是 block do ... end 中的内容在第二阶段运行,而 log 资源的 Ruby 代码在第一阶段进行评估。通常,您可以使用 lazy{} 帮助器来解决此问题,但在这种情况下,您可能需要的是自定义资源或 Ohai 插件。对于 "normal" Windows 应用程序,这全部由 MSI 子系统和 windows_package 资源处理,但由于 Telegraf 不提供 MSI 包,你有点不走运。也就是说,有可用于 Chocolatey 的软件包(Windows 包装系统,如 Mac 的 Homebrew),因此您可能想研究使用它而不是自己编写。