summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohn Keiser <john@johnkeiser.com>2016-04-14 14:24:46 -0700
committerJohn Keiser <john@johnkeiser.com>2016-04-14 22:53:37 -0700
commitd0bf64da60725181918a2fa0de949f4158da29a1 (patch)
tree4029aa13518c8dffef8bb900616ce4e04612567a
parent303a25c9cb42b4d8d5860daf82efd11c5776fe61 (diff)
downloadchef-jk/bundle-repro.tar.gz
Use released oc-chef-pedant with latest chef-zerojk/bundle-repro
-rw-r--r--.travis.yml1
-rw-r--r--Gemfile10
-rw-r--r--Gemfile.lock94
-rw-r--r--Gemfile.windows.lock100
-rw-r--r--appveyor.yml1
-rw-r--r--omnibus/Gemfile.lock2
-rw-r--r--omnibus/files/chef-gem/build-chef-gem/gem-install-software-def.rb43
-rw-r--r--omnibus/files/chef/build-chef.rb16
-rw-r--r--tasks/gemfile_util.rb185
9 files changed, 201 insertions, 251 deletions
diff --git a/.travis.yml b/.travis.yml
index ec268e1343..243349bb8d 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -62,7 +62,6 @@ matrix:
rvm: 2.2
- env:
- TEST_GEM: chef-zero
- - TEST_WITH_GEMS: oc-chef-pedant
script: tasks/bin/run_external_test $TEST_GEM "rake spec" "rake cheffs"
rvm: 2.2
- env:
diff --git a/Gemfile b/Gemfile
index a56f4aece4..6e742f659b 100644
--- a/Gemfile
+++ b/Gemfile
@@ -10,8 +10,7 @@ gem "chef-config", path: File.expand_path("../chef-config", __FILE__) if File.ex
# Ensure that we can always install rake, regardless of gem groups
gem "rake"
gem "bundler"
-# Remove "master" bit when cheffish tests succeed in Ruby 2.2
-gem "cheffish", github: "chef/cheffish"
+gem "cheffish"
group(:omnibus_package) do
gem "appbundler"
@@ -32,14 +31,13 @@ group(:integration) do
gem "chef-sugar"
gem "chefspec"
gem "halite"
- gem "poise", github: "poise/poise" # until released poise's tests succeed against chef master
+ gem "poise", git: "https://github.com/poise/poise" # until released poise's tests succeed against chef master
gem "knife-windows"
gem "foodcritic"
# Used by others:
- gem "fauxhai", github: "customink/fauxhai" # until AIX changes are released
- gem "poise-boiler", github: "poise/poise-boiler" # until new release is made with higher rake dep
- gem "oc-chef-pedant", github: "chef/chef-server" # until new chef-zero release
+ gem "fauxhai", git: "https://github.com/customink/fauxhai" # until AIX changes are released
+ gem "poise-boiler", git: "https://github.com/poise/poise-boiler" # until new release is made with higher rake dep
end
group(:docgen) do
diff --git a/Gemfile.lock b/Gemfile.lock
index 5790365375..21052fd7c3 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -1,36 +1,27 @@
GIT
- remote: git://github.com/chef/chef-server.git
- revision: 88a33630aaeae21a63b4a8111fd0a196438520c0
+ remote: https://github.com/chef/chefstyle.git
+ revision: cc37808b7849fdcf49f04011626143940f83fe92
+ branch: master
specs:
- oc-chef-pedant (2.2.0)
- activesupport (~> 3.2)
- erubis (~> 2.7)
- mixlib-authentication (~> 1.3)
- mixlib-config (~> 2.0)
- mixlib-shellout (>= 1.1)
- net-http-spy (~> 0.2)
- rest-client (>= 1.6)
- rspec (~> 3.2)
- rspec-rerun (~> 1.0)
- rspec_junit_formatter (~> 0.2)
+ chefstyle (0.3.1)
+ rubocop (= 0.39.0)
GIT
- remote: git://github.com/chef/cheffish.git
- revision: 614d15ddc31b759319696aeab0f4ef50a101ebc2
+ remote: https://github.com/customink/fauxhai
+ revision: 079c591fabd78ef13e284a84fe808fc48bf1930f
specs:
- cheffish (2.0.3)
- chef-zero (~> 4.3)
- compat_resource
+ fauxhai (3.3.0)
+ net-ssh
GIT
- remote: git://github.com/customink/fauxhai.git
- revision: a616c6aa9e2e7e6d9825a579a00b8d6e15484205
+ remote: https://github.com/poise/poise
+ revision: a76980685a92283c08f5b2e4526ae1f08f87de79
specs:
- fauxhai (3.2.0)
- net-ssh
+ poise (2.6.2.pre)
+ halite (~> 1.0)
GIT
- remote: git://github.com/poise/poise-boiler.git
+ remote: https://github.com/poise/poise-boiler
revision: 0714455eba947bde2a9d49b72db1bc3ad1034ee4
specs:
poise-boiler (1.7.2)
@@ -60,21 +51,6 @@ GIT
yard-classmethods (~> 1.0)
GIT
- remote: git://github.com/poise/poise.git
- revision: a76980685a92283c08f5b2e4526ae1f08f87de79
- specs:
- poise (2.6.2.pre)
- halite (~> 1.0)
-
-GIT
- remote: https://github.com/chef/chefstyle.git
- revision: cc37808b7849fdcf49f04011626143940f83fe92
- branch: master
- specs:
- chefstyle (0.3.1)
- rubocop (= 0.39.0)
-
-GIT
remote: https://github.com/rubysec/bundler-audit.git
revision: 4e32fca89d75f0e249671431ff38aadc02bfb28b
ref: 4e32fca
@@ -84,6 +60,14 @@ GIT
thor (~> 0.18)
PATH
+ remote: chef-config
+ specs:
+ chef-config (12.10.4)
+ fuzzyurl (~> 0.8.0)
+ mixlib-config (~> 2.0)
+ mixlib-shellout (~> 2.0)
+
+PATH
remote: .
specs:
chef (12.10.4)
@@ -113,14 +97,6 @@ PATH
syslog-logger (~> 1.6)
uuidtools (~> 2.1.5)
-PATH
- remote: chef-config
- specs:
- chef-config (12.10.4)
- fuzzyurl (~> 0.8.0)
- mixlib-config (~> 2.0)
- mixlib-shellout (~> 2.0)
-
GEM
remote: https://rubygems.org/
specs:
@@ -165,12 +141,15 @@ GEM
ubuntu_ami (~> 0.4, >= 0.4.1)
chef-rewind (0.0.9)
chef-sugar (3.3.0)
- chef-zero (4.5.0)
+ chef-zero (4.6.1)
ffi-yajl (~> 2.2)
hashie (>= 2.0, < 4.0)
mixlib-log (~> 1.3)
rack
uuidtools (~> 2.1)
+ cheffish (2.0.4)
+ chef-zero (~> 4.3)
+ compat_resource
chefspec (4.6.1)
chef (>= 11.14)
fauxhai (~> 3.2)
@@ -193,8 +172,6 @@ GEM
thread_safe (~> 0.3, >= 0.3.1)
diff-lcs (1.2.5)
docile (1.1.5)
- domain_name (0.5.20160310)
- unf (>= 0.0.5, < 1.0.0)
erubis (2.7.0)
ethon (0.8.1)
ffi (>= 1.3.0)
@@ -252,8 +229,6 @@ GEM
thor
hashie (3.4.3)
highline (1.7.8)
- http-cookie (1.0.2)
- domain_name (~> 0.5)
httpclient (2.7.1)
i18n (0.7.0)
inifile (3.0.0)
@@ -282,7 +257,9 @@ GEM
multi_json (~> 1.10)
logify (0.2.0)
method_source (0.8.2)
- mime-types (2.99.1)
+ mime-types (3.0)
+ mime-types-data (~> 3.2015)
+ mime-types-data (3.2016.0221)
mini_portile2 (2.0.0)
mixlib-authentication (1.4.0)
mixlib-log
@@ -303,7 +280,6 @@ GEM
multipart-post (2.0.0)
net-http-persistent (2.9.4)
net-http-pipeline (1.0.1)
- net-http-spy (0.2.1)
net-scp (1.2.1)
net-ssh (>= 2.6.5)
net-sftp (2.1.2)
@@ -370,10 +346,6 @@ GEM
rainbow (2.1.0)
rake (11.1.2)
rb-readline (0.5.3)
- rest-client (1.8.0)
- http-cookie (>= 1.0.2, < 2.0)
- mime-types (>= 1.16, < 3.0)
- netrc (~> 0.7)
retryable (2.0.3)
rspec (3.4.0)
rspec-core (~> 3.4.0)
@@ -390,8 +362,6 @@ GEM
rspec-mocks (3.4.1)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.4.0)
- rspec-rerun (1.1.0)
- rspec (~> 3.0)
rspec-support (3.4.1)
rspec_junit_formatter (0.2.3)
builder (< 4)
@@ -457,9 +427,6 @@ GEM
typhoeus (0.8.0)
ethon (>= 0.8.0)
ubuntu_ami (0.4.1)
- unf (0.1.4)
- unf_ext
- unf_ext (0.0.7.2)
unicode-display_width (1.0.3)
url (0.3.2)
uuidtools (2.1.5)
@@ -493,7 +460,7 @@ DEPENDENCIES
chef-provisioning-aws
chef-rewind
chef-sugar
- cheffish!
+ cheffish
chefspec
chefstyle!
fauxhai!
@@ -503,7 +470,6 @@ DEPENDENCIES
knife-windows
netrc
nokogiri
- oc-chef-pedant!
octokit
poise!
poise-boiler!
diff --git a/Gemfile.windows.lock b/Gemfile.windows.lock
index 6cff3e06a8..bd515be37b 100644
--- a/Gemfile.windows.lock
+++ b/Gemfile.windows.lock
@@ -1,39 +1,29 @@
GIT
- remote: git://github.com/chef/chef-server.git
- revision: 88a33630aaeae21a63b4a8111fd0a196438520c0
- ref: 88a33630aaeae21a63b4a8111fd0a196438520c0
+ remote: https://github.com/chef/chefstyle.git
+ revision: cc37808b7849fdcf49f04011626143940f83fe92
+ ref: cc37808b7849fdcf49f04011626143940f83fe92
specs:
- oc-chef-pedant (2.2.0)
- activesupport (~> 3.2)
- erubis (~> 2.7)
- mixlib-authentication (~> 1.3)
- mixlib-config (~> 2.0)
- mixlib-shellout (>= 1.1)
- net-http-spy (~> 0.2)
- rest-client (>= 1.6)
- rspec (~> 3.2)
- rspec-rerun (~> 1.0)
- rspec_junit_formatter (~> 0.2)
+ chefstyle (0.3.1)
+ rubocop (= 0.39.0)
GIT
- remote: git://github.com/chef/cheffish.git
- revision: 614d15ddc31b759319696aeab0f4ef50a101ebc2
- ref: 614d15ddc31b759319696aeab0f4ef50a101ebc2
+ remote: https://github.com/customink/fauxhai
+ revision: 079c591fabd78ef13e284a84fe808fc48bf1930f
+ ref: 079c591fabd78ef13e284a84fe808fc48bf1930f
specs:
- cheffish (2.0.3)
- chef-zero (~> 4.3)
- compat_resource
+ fauxhai (3.3.0)
+ net-ssh
GIT
- remote: git://github.com/customink/fauxhai.git
- revision: a616c6aa9e2e7e6d9825a579a00b8d6e15484205
- ref: a616c6aa9e2e7e6d9825a579a00b8d6e15484205
+ remote: https://github.com/poise/poise
+ revision: a76980685a92283c08f5b2e4526ae1f08f87de79
+ ref: a76980685a92283c08f5b2e4526ae1f08f87de79
specs:
- fauxhai (3.2.0)
- net-ssh
+ poise (2.6.2.pre)
+ halite (~> 1.0)
GIT
- remote: git://github.com/poise/poise-boiler.git
+ remote: https://github.com/poise/poise-boiler
revision: 0714455eba947bde2a9d49b72db1bc3ad1034ee4
ref: 0714455eba947bde2a9d49b72db1bc3ad1034ee4
specs:
@@ -64,22 +54,6 @@ GIT
yard-classmethods (~> 1.0)
GIT
- remote: git://github.com/poise/poise.git
- revision: a76980685a92283c08f5b2e4526ae1f08f87de79
- ref: a76980685a92283c08f5b2e4526ae1f08f87de79
- specs:
- poise (2.6.2.pre)
- halite (~> 1.0)
-
-GIT
- remote: https://github.com/chef/chefstyle.git
- revision: cc37808b7849fdcf49f04011626143940f83fe92
- ref: cc37808b7849fdcf49f04011626143940f83fe92
- specs:
- chefstyle (0.3.1)
- rubocop (= 0.39.0)
-
-GIT
remote: https://github.com/rubysec/bundler-audit.git
revision: 4e32fca89d75f0e249671431ff38aadc02bfb28b
ref: 4e32fca89d75f0e249671431ff38aadc02bfb28b
@@ -140,9 +114,6 @@ PATH
GEM
remote: https://rubygems.org/
specs:
- activesupport (3.2.22.2)
- i18n (~> 0.6, >= 0.6.4)
- multi_json (~> 1.0)
addressable (2.4.0)
appbundler (0.9.0)
mixlib-cli (~> 1.4)
@@ -181,12 +152,15 @@ GEM
ubuntu_ami (~> 0.4, >= 0.4.1)
chef-rewind (0.0.9)
chef-sugar (3.3.0)
- chef-zero (4.5.0)
+ chef-zero (4.6.1)
ffi-yajl (~> 2.2)
hashie (>= 2.0, < 4.0)
mixlib-log (~> 1.3)
rack
uuidtools (~> 2.1)
+ cheffish (2.0.4)
+ chef-zero (~> 4.3)
+ compat_resource
chefspec (4.6.1)
chef (>= 11.14)
fauxhai (~> 3.2)
@@ -209,8 +183,6 @@ GEM
thread_safe (~> 0.3, >= 0.3.1)
diff-lcs (1.2.5)
docile (1.1.5)
- domain_name (0.5.20160310)
- unf (>= 0.0.5, < 1.0.0)
erubis (2.7.0)
ethon (0.8.1)
ffi (>= 1.3.0)
@@ -268,8 +240,6 @@ GEM
thor
hashie (3.4.3)
highline (1.7.8)
- http-cookie (1.0.2)
- domain_name (~> 0.5)
httpclient (2.7.1)
i18n (0.7.0)
inifile (3.0.0)
@@ -298,7 +268,9 @@ GEM
multi_json (~> 1.10)
logify (0.2.0)
method_source (0.8.2)
- mime-types (2.99.1)
+ mime-types (3.0)
+ mime-types-data (~> 3.2015)
+ mime-types-data (3.2016.0221)
mini_portile2 (2.0.0)
mixlib-authentication (1.4.0)
mixlib-log
@@ -321,7 +293,6 @@ GEM
multipart-post (2.0.0)
net-http-persistent (2.9.4)
net-http-pipeline (1.0.1)
- net-http-spy (0.2.1)
net-scp (1.2.1)
net-ssh (>= 2.6.5)
net-sftp (2.1.2)
@@ -388,11 +359,6 @@ GEM
rainbow (2.1.0)
rake (11.1.2)
rb-readline (0.5.3)
- rest-client (1.8.0-x86-mingw32)
- ffi (~> 1.9)
- http-cookie (>= 1.0.2, < 2.0)
- mime-types (>= 1.16, < 3.0)
- netrc (~> 0.7)
retryable (2.0.3)
rspec (3.4.0)
rspec-core (~> 3.4.0)
@@ -409,8 +375,6 @@ GEM
rspec-mocks (3.4.1)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.4.0)
- rspec-rerun (1.1.0)
- rspec (~> 3.0)
rspec-support (3.4.1)
rspec_junit_formatter (0.2.3)
builder (< 4)
@@ -476,9 +440,6 @@ GEM
typhoeus (0.8.0)
ethon (>= 0.8.0)
ubuntu_ami (0.4.1)
- unf (0.1.4)
- unf_ext
- unf_ext (0.0.7.2-x86-mingw32)
unicode-display_width (1.0.3)
url (0.3.2)
uuidtools (2.1.5)
@@ -542,8 +503,8 @@ DEPENDENCIES
chef-provisioning-aws (= 1.9.0)!
chef-rewind (= 0.0.9)!
chef-sugar (= 3.3.0)!
- chef-zero (= 4.5.0)!
- cheffish!
+ chef-zero (= 4.6.1)!
+ cheffish (= 2.0.4)!
chefspec (= 4.6.1)!
chefstyle!
childprocess (= 0.5.9)!
@@ -557,7 +518,6 @@ DEPENDENCIES
descendants_tracker (= 0.0.4)!
diff-lcs (= 1.2.5)!
docile (= 1.1.5)!
- domain_name (= 0.5.20160310)!
erubis (= 2.7.0)!
ethon (= 0.8.1)!
faraday (= 0.9.2)!
@@ -578,7 +538,6 @@ DEPENDENCIES
halite (= 1.2.1)!
hashie (= 3.4.3)!
highline (= 1.7.8)!
- http-cookie (= 1.0.2)!
httpclient (= 2.7.1)!
i18n (= 0.7.0)!
inifile (= 3.0.0)!
@@ -598,7 +557,8 @@ DEPENDENCIES
logging (= 2.1.0)!
logify (= 0.2.0)!
method_source (= 0.8.2)!
- mime-types (= 2.99.1)!
+ mime-types (= 3.0)!
+ mime-types-data (= 3.2016.0221)!
mini_portile2 (= 2.0.0)!
mixlib-authentication (= 1.4.0)!
mixlib-cli (= 1.5.0)!
@@ -612,7 +572,6 @@ DEPENDENCIES
multipart-post (= 2.0.0)!
net-http-persistent (= 2.9.4)!
net-http-pipeline (= 1.0.1)!
- net-http-spy (= 0.2.1)!
net-scp (= 1.2.1)!
net-sftp (= 2.1.2)!
net-ssh (= 3.1.1)!
@@ -623,7 +582,6 @@ DEPENDENCIES
nokogiri (= 1.6.7.2)!
nori (= 2.6.0)!
oauth2 (= 1.1.0)!
- oc-chef-pedant!
octokit (= 4.3.0)!
ohai (= 8.14.0)!
overcommit (= 0.33.0)!
@@ -644,14 +602,12 @@ DEPENDENCIES
rainbow (= 2.1.0)!
rake (= 11.1.2)!
rb-readline (= 0.5.3)!
- rest-client (= 1.8.0)!
retryable (= 2.0.3)!
rspec (= 3.4.0)!
rspec-core (= 3.4.4)!
rspec-expectations (= 3.4.0)!
rspec-its (= 1.2.0)!
rspec-mocks (= 3.4.1)!
- rspec-rerun (= 1.1.0)!
rspec-support (= 3.4.1)!
rspec_junit_formatter (= 0.2.3)!
rubocop (= 0.39.0)!
@@ -679,8 +635,6 @@ DEPENDENCIES
treetop (= 1.6.5)!
typhoeus (= 0.8.0)!
ubuntu_ami (= 0.4.1)!
- unf (= 0.1.4)!
- unf_ext (= 0.0.7.2)!
unicode-display_width (= 1.0.3)!
url (= 0.3.2)!
uuidtools (= 2.1.5)!
diff --git a/appveyor.yml b/appveyor.yml
index 13437088bb..d76e43013e 100644
--- a/appveyor.yml
+++ b/appveyor.yml
@@ -16,6 +16,7 @@ skip_tags: true
branches:
only:
- master
+ - jk/bundle-repro
install:
- systeminfo
diff --git a/omnibus/Gemfile.lock b/omnibus/Gemfile.lock
index 715a2f3edc..7e92537e3c 100644
--- a/omnibus/Gemfile.lock
+++ b/omnibus/Gemfile.lock
@@ -1,6 +1,6 @@
GIT
remote: https://github.com/chef/omnibus-software.git
- revision: 8d611676c4458fa679cbc48e2111892ae7986cbf
+ revision: 6127be3af79941c32419228cbd9e63c4f061d76b
specs:
omnibus-software (4.0.0)
omnibus (>= 5.2.0)
diff --git a/omnibus/files/chef-gem/build-chef-gem/gem-install-software-def.rb b/omnibus/files/chef-gem/build-chef-gem/gem-install-software-def.rb
index 5992ae8057..ee096b8ed9 100644
--- a/omnibus/files/chef-gem/build-chef-gem/gem-install-software-def.rb
+++ b/omnibus/files/chef-gem/build-chef-gem/gem-install-software-def.rb
@@ -1,6 +1,7 @@
require "bundler"
require "omnibus"
require_relative "../build-chef-gem"
+require_relative "../../../../tasks/gemfile_util"
module BuildChefGem
class GemInstallSoftwareDef
@@ -34,16 +35,16 @@ module BuildChefGem
gem_name = self.gem_name
gem_version = self.gem_version
- gemspec = self.gemspec
+ gem_metadata = self.gem_metadata
lockfile_path = self.lockfile_path
software.build do
extend BuildChefGem
if gem_version == "<skip>"
- if gemspec
+ if gem_metadata
block do
- log.info(log_key) { "#{gem_name} has source #{gemspec.source.name} in #{lockfile_path}. We only cache rubygems.org installs in omnibus to keep things simple. The chef step will build #{gem_name} ..." }
+ log.info(log_key) { "#{gem_name} has source #{gem_metadata} in #{lockfile_path}. We only cache rubygems.org installs in omnibus to keep things simple. The chef step will build #{gem_name} ..." }
end
else
block do
@@ -95,34 +96,26 @@ module BuildChefGem
end
end
- def gemspec
- @gemspec ||= begin
- old_frozen = Bundler.settings[:frozen]
- Bundler.settings[:frozen] = true
- begin
- bundle = Bundler::Definition.build(gemfile_path, lockfile_path, nil)
- dependencies = bundle.dependencies.select { |d| (d.groups - without_groups).any? }
- # This is sacrilege: figure out a way we can grab the list of dependencies *without*
- # requiring everything to be installed or calling private methods ...
- gemspec = bundle.resolve.for(bundle.send(:expand_dependencies, dependencies)).find { |s| s.name == gem_name }
- if gemspec
- log.info(software.name) { "Using #{gem_name} version #{gemspec.version} from #{gemfile_path}" }
- elsif bundle.resolve.find { |s| s.name == gem_name }
- log.info(software.name) { "#{gem_name} not loaded from #{gemfile_path}, skipping" }
- else
- raise "#{gem_name} not found in #{gemfile_path} or #{lockfile_path}"
- end
- gemspec
- ensure
- Bundler.settings[:frozen] = old_frozen
+ def gem_metadata
+ @gem_metadata ||= begin
+ selected = GemfileUtil.select_gems(gemfile_path, without_groups: without_groups)
+ result = GemfileUtil.locked_gems(lockfile_path, selected)[gem_name]
+ if result
+ log.info(software.name) { "Using #{gem_name} version #{result[:version]} from #{gemfile_path}" }
+ result
+ elsif GemfileUtil.locked_gems(lockfile_path, GemfileUtil.select_gems(gemfile_path))[gem_name]
+ log.info(software.name) { "#{gem_name} not loaded from #{gemfile_path} because it was only in groups #{without_groups.join(", ")}, skipping" }
+ nil
+ else
+ raise "#{gem_name} not found in #{gemfile_path} or #{lockfile_path}"
end
end
end
def gem_version
@gem_version ||= begin
- if gemspec && gemspec.source.name == "rubygems repository https://rubygems.org/"
- gemspec.version.to_s
+ if gem_metadata && URI(gem_metadata[:source]) == URI("https://rubygems.org/")
+ gem_metadata[:version]
else
"<skip>"
end
diff --git a/omnibus/files/chef/build-chef.rb b/omnibus/files/chef/build-chef.rb
index d3e68d4e8a..8617312592 100644
--- a/omnibus/files/chef/build-chef.rb
+++ b/omnibus/files/chef/build-chef.rb
@@ -108,22 +108,24 @@ module BuildChef
name, version = $1, $2
# rubocop is an exception, since different projects disagree
next if GEMS_ALLOWED_TO_FLOAT.include?(name)
- gem_pins << "override_gem #{name.inspect}, #{version.inspect}\n"
+ gem_pins << "gem #{name.inspect}, #{version.inspect}, override: true\n"
end
end
+ # Find the installed chef gem by looking for lib/chef.rb
+ chef_gem = File.expand_path("../..", shellout!("#{gem_bin} which chef").stdout.chomp)
+ # Figure out the path to gemfile_util from there
+ gemfile_util = Pathname.new(File.join(chef_gem, "tasks", "gemfile_util"))
+ gemfile_util = gemfile_util.relative_path_from(Pathname.new(shared_gemfile).dirname)
+
create_file(shared_gemfile) { <<-EOM }
# Meant to be included in component Gemfiles at the end with:
#
# instance_eval(IO.read("#{install_dir}/Gemfile"), "#{install_dir}/Gemfile")
#
# Override any existing gems with our own.
- def override_gem(name, *args, &block)
- # If the Gemfile re-specifies something in our lockfile, ignore it.
- current = dependencies.find { |dep| dep.name == name }
- dependencies.delete(current) if current
- gem(name, *args, &block)
- end
+ require_relative "#{gemfile_util}"
+ extend GemfileUtil
#{gem_pins}
EOM
end
diff --git a/tasks/gemfile_util.rb b/tasks/gemfile_util.rb
index 293c755186..90c6762ccd 100644
--- a/tasks/gemfile_util.rb
+++ b/tasks/gemfile_util.rb
@@ -2,17 +2,8 @@ require "bundler"
require "set"
module GemfileUtil
- # gemspec and gem need to use absolute paths for things in order for our Gemfile
- # to be *included* in another. This works around some issues in bundler 1.11.2.
- def gemspec(options = {})
- options[:path] = File.expand_path(options[:path] || ".", Bundler.default_gemfile.dirname)
- super
- end
-
#
- # gemspec and gem need to use absolute paths for things in order for our Gemfile
- # to be *included* in another. This works around some issues in bundler 1.11.2.
- # Also adds `override: true`, which allows your statement to override any other
+ # Adds `override: true`, which allows your statement to override any other
# gem statement about the same gem in the Gemfile.
#
def gem(name, *args)
@@ -24,7 +15,7 @@ module GemfileUtil
if options[:path]
# path sourced gems are assumed to be overrides.
options[:override] = true
- options[:path] = File.expand_path(options[:path], Bundler.default_gemfile.dirname)
+ # options[:path] = File.expand_path(options[:path], Bundler.default_gemfile.dirname)
end
# Handle override
if options[:override]
@@ -72,88 +63,134 @@ module GemfileUtil
#
# Include all gems in the locked gemfile.
#
- # @param gemfile Path to the Gemfile to load
+ # @param gemfile Path to the Gemfile to load (relative to your Gemfile)
# @param groups A list of groups to include (whitelist). If not passed (or set
# to nil), all gems will be selected.
+ # @param without_groups A list of groups to ignore. Gems will be excluded from
+ # the results if all groups they belong to are ignored.
+ # This matches bundler's `without` behavior.
# @param gems A list of gems to include above and beyond the given groups.
# Gems in this list must be explicitly included in the Gemfile
# with a `gem "gem_name", ...` line or they will be silently
# ignored.
#
- def include_locked_gemfile(gemfile, groups: nil, gems: [])
- Bundler.ui.info "Loading locks from #{gemfile} ..."
+ def include_locked_gemfile(gemfile, groups: nil, without_groups: nil, gems: [])
gemfile = File.expand_path(gemfile, Bundler.default_gemfile.dirname)
+ gems = Set.new(gems) + GemfileUtil.select_gems(gemfile, groups: nil, without_groups: nil)
+ specs = GemfileUtil.locked_gems("#{gemfile}.lock", gems)
+ specs.each do |name, version: nil, **options|
+ options = options.merge(override: true)
+ Bundler.ui.debug("Adding gem #{name}, #{version}, #{options} from #{gemfile}")
+ gem name, version, options
+ end
+ rescue
+ puts "ERROR: #{$!}"
+ puts $!.backtrace
+ raise
+ end
- #
- # Read the gemfile and inject its locks as first-class dependencies
- #
- old_gemfile = ENV["BUNDLE_GEMFILE"]
- old_frozen = Bundler.settings[:frozen]
- begin
- # Set frozen to true so we don't try to install stuff.
- Bundler.settings[:frozen] = true
+ #
+ # Select the desired gems, sans dependencies, from the gemfile.
+ #
+ # @param gemfile Path to the Gemfile to load
+ # @param groups A list of groups to include (whitelist). If not passed (or set
+ # to nil), all gems will be selected.
+ # @param without_groups A list of groups to ignore. Gems will be excluded from
+ # the results if all groups they belong to are ignored.
+ # This matches bundler's `without` behavior.
+ #
+ # @return An array of strings with the names of the given gems.
+ #
+ def self.select_gems(gemfile, groups: nil, without_groups: nil)
+ Bundler.with_clean_env do
# Set BUNDLE_GEMFILE to the new gemfile temporarily so all bundler's things work
# This works around some issues in bundler 1.11.2.
ENV["BUNDLE_GEMFILE"] = gemfile
- bundle = Bundler::Definition.build(gemfile, "#{gemfile}.lock", nil)
- # Narrow it down to just the dependencies in the desired groups
- dependencies = bundle.dependencies.select do |dep|
- groups.nil? || (dep.groups & groups).any? || gems.include?(dep.name)
- end
- # Get the resolved specs descended from our dependencies, from the lockfile
- # This is sacrilege: figure out a way we can grab the list of dependencies *without*
- # requiring everything to be installed or calling private methods ...
- specs = bundle.resolve.for(bundle.send(:expand_dependencies, dependencies))
- # Go through and create the actual gemfile from the given locks and
- # groups.
- specs.sort_by { |spec| spec.name }.each do |spec|
- # bundler can't be installed by bundler so don't pin it.
- next if spec.name == "bundler"
+ parsed_gemfile = Bundler::Dsl.new
+ parsed_gemfile.eval_gemfile(gemfile)
+ deps = parsed_gemfile.dependencies.select do |dep|
+ dep_groups = dep.groups
+ dep_groups = dep_groups & groups if groups
+ dep_groups = dep_groups - without_groups if without_groups
+ dep_groups.any?
+ end
+ deps.map { |dep| dep.name }
+ end
+ end
- # Copy groups and platforms from included Gemfile
- gem_metadata = {}
- dep = bundle.dependencies.find { |d| d.name == spec.name }
- if dep
- gem_metadata[:groups] = dep.groups unless dep.groups == [:default]
- gem_metadata[:platforms] = dep.platforms unless dep.platforms.empty?
- end
- gem_metadata[:override] = true
+ #
+ # Get all gems in the locked gemfile that start from the given gem set.
+ #
+ # @param lockfile Path to the Gemfile to load
+ # @param groups A list of groups to include (whitelist). If not passed (or set
+ # to nil), all gems will be selected.
+ # @param without_groups A list of groups to ignore. Gems will be excluded from
+ # the results if all groups they belong to are ignored.
+ # This matches bundler's `without` behavior.
+ # @param gems A list of gems to include above and beyond the given groups.
+ # Gems in this list must be explicitly included in the Gemfile
+ # with a `gem "gem_name", ...` line or they will be silently
+ # ignored.
+ # @param include_development_deps Whether to include development dependencies
+ # or runtime only.
+ #
+ # @return Hash[String, Hash] A hash from gem_name -> { version: <version>, source: <source>, git: <git>, path: <path>, ref: <ref> }
+ #
+ def self.locked_gems(lockfile, gems, include_development_deps: false)
+ # Grab all the specs from the lockfile
+ parsed_lockfile = Bundler::LockfileParser.new(IO.read(lockfile))
+ specs = {}
+ parsed_lockfile.specs.each { |s| specs[s.name] = s }
- # Copy source information from included Gemfile
- use_version = false
- case spec.source
- when Bundler::Source::Rubygems
- gem_metadata[:source] = spec.source.remotes.first.to_s
- use_version = true
- when Bundler::Source::Git
- gem_metadata[:git] = spec.source.uri.to_s
- gem_metadata[:ref] = spec.source.revision
- when Bundler::Source::Path
- gem_metadata[:path] = spec.source.path.to_s
- else
- raise "Unknown source #{spec.source} for gem #{spec.name}"
+ # Select the desired gems, as well as their dependencies
+ to_process = Array(gems)
+ results = {}
+ while to_process.any?
+ gem_name = to_process.pop
+ next if gem_name == "bundler" # can't be bundled. Messes things up. Stop it.
+ # Only process each gem once
+ unless results.has_key?(gem_name)
+ spec = specs[gem_name]
+ unless spec
+ raise "Gem #{gem_name.inspect} was requested but was not in #{lockfile}! Gems in lockfile: #{specs.keys}"
end
-
- # Emit the dep
- if use_version
- Bundler.ui.debug("Adding #{spec.name}, #{spec.version}, #{gem_metadata} from #{gemfile}")
- gem spec.name, spec.version, gem_metadata
- else
- Bundler.ui.debug("Adding #{spec.name}, #{gem_metadata} from #{gemfile}")
- gem spec.name, gem_metadata
+ results[gem_name] = gem_metadata(spec, lockfile)
+ spec.dependencies.each do |dep|
+ if dep.type == :runtime || include_development_deps
+ to_process << dep.name
+ end
end
end
+ end
+
+ results
+ end
+
+ private
- Bundler.ui.info "Loaded #{bundle.resolve.count} locked gem versions #{groups ? "from groups #{groups.join(", ")}" : ""}#{gems.empty? ? "" : " (including #{gems.join(", ")})"} from #{gemfile}"
- rescue Exception
- # Bundler does a bad job of rescuing.
- Bundler.ui.info $!
- Bundler.ui.info $!.backtrace
- raise
- ensure
- Bundler.settings[:frozen] = old_frozen
- ENV["BUNDLE_GEMFILE"] = old_gemfile
+ #
+ # Get metadata for the given Bundler spec (coming from a lockfile).
+ #
+ # @return Hash { version: <version>, git: <git>, path: <path>, source: <source>, ref: <ref> }
+ #
+ def self.gem_metadata(spec, lockfile)
+ # Copy source information from included Gemfile
+ result = {}
+ case spec.source
+ when Bundler::Source::Rubygems
+ result[:source] = spec.source.remotes.first.to_s
+ result[:version] = spec.version.to_s
+ when Bundler::Source::Git
+ result[:git] = spec.source.uri.to_s
+ result[:ref] = spec.source.revision
+ when Bundler::Source::Path
+ # Path is relative to the lockfile (if it's relative at all)
+ result[:path] = File.expand_path(spec.source.path.to_s, File.dirname(lockfile))
+ else
+ raise "Unknown source #{spec.source} for gem #{spec.name}"
end
+ result
end
+
end