5

我正在开发一本食谱来部署一个简单的基于 jekyll 的博客。我使用“应用程序”食谱作为基础。除了厨师简单地忽略我定义的回调之外,一切都很顺利。

Chef 日志包含有关我的回调的条目,但我没有看到回调执行的错误或结果。

这是 recipes/default.rb 文件:

include_recipe "git"

application "example_com" do
  path "/var/www/example.com"
  repository "git@example.org:xxx/xxx.git"
  revision "master"

  deploy_key <<EOF
-----BEGIN RSA PRIVATE KEY-----
..skip...
-----END RSA PRIVATE KEY-----
EOF

  # before_symlink "script/bootstrap"

  before_deploy do
    # raise
    # Chef::Log.info("INSANE!")
    execute "bundle exec rake generate" do
      cwd release_path
    end
  end
end

这是 chef-client 说它执行 before_deploy 回调的日志:

[2012-10-06T10:06:20-04:00] INFO: Processing ruby_block[example_com before_deploy] action create (/var/cache/chef/cookbooks/application/providers/default.rb line 107)
[2012-10-06T10:06:20-04:00] DEBUG: Got callback before_deploy: #<Proc:0x00007f0509788088@/var/cache/chef/cookbooks/example_com/recipes/default.rb:24>
[2012-10-06T10:06:20-04:00] INFO: application[example_com] running callback before_deploy
[2012-10-06T10:06:20-04:00] INFO: ruby_block[example_com before_deploy] called
[2012-10-06T10:06:20-04:00] INFO: Processing deploy_revision[example_com] action deploy (/var/cache/chef/cookbooks/application/providers/default.rb line 122)

我也尝试使用字符串定义回调,但结果是一样的。当没有带有回调定义的文件时,Chef 会显示错误,如果文件在正确的位置,则简单地忽略该文件。

更新 1

在深入挖掘 Chef 资源后,我意识到回调是在单独的 chef runner 中执行的,这不会立即发生。当应用程序说明书中的代码调用 _recipe_eval_ 来评估回调主体时,Chef 创建单独的运行器并且代码不会执行,直到调用收敛方法。

所以,我稍微修改了应用程序说明书。我在 _recipe_eval_ 之后添加了调用收敛,一切都开始工作了。

我认为这是一个错误,我将在官方 Opscode 跟踪器中创建一个问题。但是,非常欢迎任何评论!

这是应用程序/库/default.rb 的修改版本:

class Chef
  class Provider
    module ApplicationBase

    # ...skip...

      def callback(what, callback_code=nil)
        Chef::Log.debug("Got callback #{what}: #{callback_code.inspect}")
        @collection = Chef::ResourceCollection.new
        case callback_code
        when Proc
          Chef::Log.info "#{@new_resource} running callback #{what}"
          # recipe_eval(&callback_code)
          recipe_eval(&callback_code)
          converge # <--- Remove this line and no callbacks will work.
        when String
          callback_file = "#{release_path}/#{callback_code}"
          unless ::File.exist?(callback_file)
            raise RuntimeError, "Can't find your callback file #{callback_file}"
          end
          run_callback_from_file(callback_file)
        when nil
          nil
        else
          raise RuntimeError, "You gave me a callback I don't know what to do with: #{callback_code.inspect}"
        end
      end
    end
  end
end
4

1 回答 1

1

Opscode 刚刚确认这是 Chef 中的错误。如果有人需要更多详细信息和修复状态,请使用以下链接:

于 2012-11-01T06:29:43.133 回答