How do I vendorize gems for Rails3/Bundler

2019-01-12 18:43发布

问题:

In Rails 2.X, I could simply copy gems into vendor/gems/gem_name, or use the rake command rake gems:unpack. Since Rails3 uses bundler, it doesn't appear to work anymore. I have found the command bundle package, but it doesn't work the same way.

Edit:

So, just to elaborate a bit on this:

The way that rails 2 worked, I could easily grep to find stuff in vendor/gems. If they are bundled up in .gem files, that isn't possible. Also, when developing a gem/plugin, it's very helpful to have it placed within a rails application to test it out in context. How would I do such things with bundler/rails3? Is my workflow inherently broken somehow?

回答1:

Answering the second part of your question, developing a plugin/gem and shipping it with the rails app without making the gem publicly available, you may do this

Gemfile

gem 'my_private_gem', :path => "vendor/gems/my_private_gem-VERSION"

assuming you performed a gem unpack my_private_gem --target vendor/gems

note: bundle package unpacks all gems (as many as in Gemfile.lock). I wouldn't want those in git.



回答2:

The Bundler equivalent is bundle package. It packages all of the .gem files specified in the Gemfile into vendor/cache so that future installs get the gems from this cache rather than from http://rubygems.org/



回答3:

The correct Bundler equivalent is bundle install --deployment. This will install the gems, in their unpacked state, in vendor/bundle.



回答4:

This is what worked for me:

gem unpack <GEM_NAME> [-v <VERSION>] --target vendor/gems
gem specification <GEM_NAME> [-v <VERSION>] --ruby > vendor/gems/<GEM_NAME>[-<VERSION>].gemspec

For example:

gem unpack sidekiq-pro -v 2.1.4 --target vendor/gems
gem specification sidekiq-pro -v 2.1.4 --ruby > vendor/gems/sidekiq-pro-2.1.4.gemspec

The first command unpacks the gem into the vendor/gems directory. However, that doesn't contain the gemspec. The second command creates the associated gemspec. It's noteworthy that another poster mentioned something similar. This solution correctly writes the gemspec in ruby format instead of in yaml.

You can then update your Gemfile to point to the vendored gem:

gem '<GEM_NAME>', '<VERSION>', :path => "vendor/gems/<GEM_NAME>-<VERSION>"

For example:

gem 'sidekiq-pro', '2.1.4', :path => "vendor/gems/sidekiq-pro-2.1.4"


回答5:

Consider using "hosted" development infrastructure delivered by the hosted_gem_development gem.

Developing gems is often tricky because they act like separate projects with regard to the applications you use them in.

"Hosted" development infrastructure makes gem development easier by including them into (making them "hosted by") your live application. Then you update your gem's code like you update regular application code.

Go to project page