厨师安装系列预包装宝石



我正在尝试安装我的食谱所需的一系列 gem,但我宁愿不在我的生产机器上安装开发工具(即 gcc、gcc-c++、ruby-devel.有关更多上下文,请参阅此内容),因此将相关的 gem 文件作为资源包含在我的食谱中。

我正在使用此代码

node["chef_gems"].each do |pkg, attrs|
  gem_file = "#{pkg}-#{attrs["version"]}.gem"
  dest_gem_file = "#{Chef::Config['file_cache_path']}/#{gem_file}"
  cookbook_file "#{dest_gem_file}" do
      source "gems/#{gem_file}"
  end
  if File.exist?("#{dest_gem_file}")
    chef_gem pkg do
      source "#{dest_gem_file}"
      action :install
    end
  end
end

我遇到的问题

  1. 目前,由于 File.exist? 检查,这需要两次 chef 运行,但如果没有它,它将无法编译,因为该文件在编译阶段不存在。有没有更简单的方法来实现这一点?
  2. 其中一些宝石具有依赖关系,因此排序问题似乎默认为按字母顺序排列。我即将走上通过排序键(丑陋)执行顺序的道路,想知道是否有更好的方法。
  3. 退一步说,这似乎过于复杂了。是否有更简单的策略来实现安装 gem 及其依赖项的目标,而无需在生产服务器上安装开发工具。

这是没有File.exist的原始错误?

检查
Starting Chef Client, version 11.4.0
resolving cookbooks for run list: ["cis-rhel", "ec2-hostname-rhel", "chef-client", "cassandra"]
Synchronizing Cookbooks:
<REDACTED>
Compiling Cookbooks...
[2013-10-16T18:45:01-04:00] WARN: Cloning resource attributes for user[<REDACTED>] from prior resource (CHEF-3694)
<REDACTED>
[2013-10-16T18:45:01-04:00] WARN: Current  user[cassandra]: /var/chef/cache/cookbooks/cassandra/recipes/user.rb:23:in `from_file'
Recipe: cassandra::packages
  * chef_gem[cassandra-cql] action install
================================================================================
Error executing action `install` on resource 'chef_gem[cassandra-cql]'
================================================================================

Gem::Exception
--------------
Cannot load gem at [/var/chef/cache/cassandra-cql-1.1.4.gem] in /

Cookbook Trace:
---------------
/var/chef/cache/cookbooks/cassandra/recipes/packages.rb:36:in `block in from_file'
/var/chef/cache/cookbooks/cassandra/recipes/packages.rb:29:in `each'
/var/chef/cache/cookbooks/cassandra/recipes/packages.rb:29:in `from_file'
/var/chef/cache/cookbooks/cassandra/recipes/default.rb:23:in `from_file'

Resource Declaration:
---------------------
# In /var/chef/cache/cookbooks/cassandra/recipes/packages.rb
 36:     chef_gem pkg do
 37:       source "#{dest_gem_file}"
 38:       action :install
 39:     end
 40: #  end

Compiled Resource:
------------------
# Declared in /var/chef/cache/cookbooks/cassandra/recipes/packages.rb:36:in `block in from_file'
chef_gem("cassandra-cql") do
  provider Chef::Provider::Package::Rubygems
  action [:install]
  retries 0
  retry_delay 2
  package_name "cassandra-cql"
  source "/var/chef/cache/cassandra-cql-1.1.4.gem"
  cookbook_name "cassandra"
  recipe_name "packages"
end


================================================================================
Recipe Compile Error in /var/chef/cache/cookbooks/cassandra/recipes/default.rb
================================================================================

Gem::Exception
--------------
chef_gem[cassandra-cql] (cassandra::packages line 36) had an error: Gem::Exception: Cannot load gem at [/var/chef/cache/cassandra-cql-1.1.4.gem] in /

Cookbook Trace:
---------------
  /var/chef/cache/cookbooks/cassandra/recipes/packages.rb:36:in `block in from_file'
  /var/chef/cache/cookbooks/cassandra/recipes/packages.rb:29:in `each'
  /var/chef/cache/cookbooks/cassandra/recipes/packages.rb:29:in `from_file'
  /var/chef/cache/cookbooks/cassandra/recipes/default.rb:23:in `from_file'

Relevant File Content:
----------------------
/var/chef/cache/cookbooks/cassandra/recipes/packages.rb:
 29:  node["cassandra"]["chef_gems"].each do |pkg, attrs|
 30:    gem_file = "#{pkg}-#{attrs["version"]}.gem"
 31:    dest_gem_file = "#{Chef::Config['file_cache_path']}/#{gem_file}"
 32:    cookbook_file "#{dest_gem_file}" do
 33:        source "gems/#{gem_file}"
 34:    end
 35:  #  if File.exist?("#{dest_gem_file}")
 36>>     chef_gem pkg do
 37:        source "#{dest_gem_file}"
 38:        action :install
 39:      end
 40:  #  end
 41:  end
 42:  
 43:  # Some distributed packages of Cassandra start the service in their
 44:  # postinstall; keep them all equal and a restart can be done after the configs
 45:  # are written on the first run. Added difficulty: they also come with init

[2013-10-16T18:45:01-04:00] ERROR: Running exception handlers
[2013-10-16T18:45:02-04:00] FATAL: Saving node information to /var/chef/cache/failed-run-data.json
[2013-10-16T18:45:02-04:00] ERROR: Exception handlers complete
Chef Client failed. 0 resources updated
[2013-10-16T18:45:02-04:00] FATAL: Stacktrace dumped to /var/chef/cache/chef-stacktrace.out
[2013-10-16T18:45:02-04:00] FATAL: Gem::Exception: chef_gem[cassandra-cql] (cassandra::packages line 36) had an error: Gem::Exception: Cannot load gem at [/var/chef/cache/cassandra-cql-1.1.4.gem] in /
  1. 您可以并且应该跳过if File.exist?("#{dest_gem_file}")段,因为上一个资源将始终创建文件或引发异常。
  2. 如果你能做到这一点,使用可以处理依赖项的包管理器安装它们可能是一个更好的选择。
  3. 如果由于需要编译包的本机扩展而无法使用rubygems包管理器执行此操作,则可以考虑打包已编译的版本并使用系统包管理器来安装它们。

最新更新