Say I have a Rails app with gems installed with bundler
. Should I use bundle exec rails
or bin/rails
? Should I use bundle exec rake
or bin/rake
? Is there any difference? Is any of those better then the other one?
tl;dr no particular difference, but if I were to choose, I'd use bin/rails
There's little to no difference. Let us see.
DISABLE_SPRING=1 bin/rails --version
:
bin/rails
: require_relative '../config/boot'
config/boot
: require 'bundler/setup'
bundler/setup
: Bundler.setup
Bundler.setup
: definition.validate_runtime!
Bundler.definition
: Definition.build
Bundler::Definition.build
: Dsl.evaluate
Bundler::Dsl.evaluate
: builder.eval_gemfile
Bundler::Dsl#eval_gemfile
: instance_eval
After require 'bundler/setup'
, trying to gem 'rails', 'x.y.z'
results in:
*** Gem::LoadError Exception: can't activate rails (= x.y.z), already activated rails-5.1.3. Make sure all dependencies are added to Gemfile.
With bundle exec rails --version
, we end up running bin/rails
anyway:
~/.gem/ruby/x.y.z/bin/rails
: load Gem.activate_bin_path('railties', 'rails', version)
exe/rails
: require 'rails/cli'
rails/cli
: Rails::AppLoader.exec_app
Rails::AppLoader.exec_app
: `exec RUBY, 'bin/rails', *ARGV
Also, do note the message one can found in the last file:
Beginning in Rails 4, Rails ships with a
rails
binstub at ./bin/rails that should be used instead of the Bundler-generatedrails
binstub.
So, at the end of the day there's no difference. But considering the fact that Rails goes through the trouble of shipping its own binstubs, I'd favor bin/rails
alternative. Also, it autocompletes better.
And,
App executables now live in the
bin/
directory:bin/bundle
,bin/rails
,bin/rake
. Runrake rails:update:bin
to add these executables to your own app.script/rails
is gone from new apps.Running executables within your app ensures they use your app's Ruby version and its bundled gems, and it ensures your production deployment tools only need to execute a single script. No more having to carefully
cd
to the app dir and runbundle exec ...
.Rather than treating
bin/
as a junk drawer for generated "binstubs", bundler 1.3 adds support for generating stubs for just the executables you actually use:bundle binstubs unicorn
generatesbin/unicorn
. Add that executable to git and version it just like any other app code.
https://github.com/rails/rails/blob/4-0-stable/railties/CHANGELOG.md