Why should I use application-specific RVM gemsets in addition to Bundler? - ruby

I'm using RVM to manage my local Ruby installations, and Bundler for application dependency management.
Some people recommend using a separate RVM gemset for each application, while some seem to think that's not necessary.
So what are the advantages of using a separate RVM gemset for each application, when I'm using Bundler anyway? What are the risks of not doing so?

i use gemsets in addition to bundler because of the following:
easy to just drop everything once a while (i like messing around with my installed gems)
no need to call bundle exec (this is obsolete with binstubs)
faster loading, because less gem-specs need to be parsed
easy to distribute (copy it to your mates)
there are probably more reasons to use them, but i generally like the idea of sandboxes!

I've found that it's useful to have rvm if you're using rails 2. RVM is great if you need to work on an app that has old code. Rails 2 doesn't use a Gemfile, so bundle exec doesn't work. RVM makes it easy to keep the gem versions correct for that project, and they you can switch back to newer versions of rails and use the Gemfile to specify versions. If you have multiple apps that use different gem versions, but the same version of ruby, it's convenient to share most of the gems, and specify them in the Gemfile where they differ.
I think it's kind of case dependent. If you find that there are tons of version issues between two apps, and constantly modifying Gemfiles to keep them straight is annoying, then use separate gemsets. If there is enough in common, it might make sense to just use the same gemset

RVM gemsets allow you to separate gems without loading bundler - which is faster, it will be simpler to load the gems.
You should be using gemsets to just separate projects from your helper gems (like gist).
But if you decide that gemsets are of no help for you you can tell RVM to ignore gemsets totally:
echo "export rvm_ignore_gemsets_flag=1" >> ~/.rvmrc

Might I also refer you to the 'globalcache' documentation in the form of an rvm-test located at fast/globalcache_comment_test.sh in conjunction with your projects' Gemfile.
This will also cut down on the network traffic to rubygems.org. Initial loadout of global, not withstanding.

Related

Managing multiple versions of a Ruby Gem

I'm a newbie, but I have a question regarding managing different versions of a gem, in my case, zurb-foundation. A new version just came out and I did a gem update and it made my older versions of the framework no longer compile.
My project contains a config.rb file that starts with
require 'zurb-foundation'
How does Ruby know to use the latest version of this? Is there a symlink somewhere pointing to the latest version? If so, I was thinking I could just re-write this symlink depending on which project I'm currently working in.
If you have multiple projects that use different versions of a gem you probably want to have a look at Bundler.
http://gembundler.com/
Bundler makes managing Ruby gems a breeze. This is highly recommended!
You should use RVM to manage multiple versions of ruby and gems.
Visit followings links to have an idea of rvm and to install.
https://rvm.io/
https://rvm.io/rvm/install/

Updated ruby, then gemsets via rvm upgrade, but .rvmrc files?

I'm not sure if my workflow is off, or if I'm using rvm gemsets entirely wrong, but here's how I upgraded to the latest patch level in Ruby today [327].
Updated ruby via rvm install.
Ran rvm upgrade and upgraded everything
Selected yes, when asked during rvm upgrade to delete old ruby.
So, then I noticed that my .rvmrc files in my apps were trying to load the old gemset that now doesn't exist. I manually updated each .rvmrc file with the new gemset from the rvm upgrade.
All is well, but my questions:
Should I have kept my prior version of ruby installed just in case?
Is manually updating each .rvmrc the right thing to do?
Should I be creating gemsets for each app, or should I really just use gemsets to manage ruby versions for different required environments?
1- Patches don't really change much thing that can accidentally break your code. Keep just major versions. (1.8.7, 1.9.2, 1.9.3, etc)
2- This way is the fastest and simplest way. It works flawless and really don't have any problem.
3- Gemsets are good for organization purposes. I really like to have on for each project, but i guess i and kind of a control freak, so i believe it is personal taste.

Why does RVM install duplicate gems for different gemsets?

So, I've created a separate rvm gemset for each of my rails projects. They both use the same version of ruby 1.9.3.
This causes bundle install to completely install a fresh set of gems for both projects. It doesn't matter if the other project has the exact same version of the gem installed in the other gemset. I'm guessing this is the expected behavior to me but it seems like an inefficient use of hard drive space and bandwidth.
I know that I could manually move some of those gems to a global gemset, but that seems tedious to me and also prone to breaking if my dependencies change for a particular project.
Is there a better way to organize things, or have rvm auto detect when a gem version is already installed and just use that copy?
Or is there a better alternative to RVM that I should be using.
This is by design. Gemsets allow you to completely isolate the libraries used so you don't have any accidental interaction between projects. If you don't need the isolate you can just use an interpreter without a gemset:
rvm use 1.9.3
If there are a few gems you use across all projects, just switch to the global gemset for the interpreter:
rvm use 1.9.3#global
gem install the common gems and then they won't be re-installed per-project anymore when you are in a gemset.
While gemsets definitely aren't efficient in terms of bandwidth or HD space, they are extremely handy because you can easily blow away all dependencies for a project and re-bundle from scratch any time you want to. They also completely eliminate accidentally changing versions of your dependencies. If you don't like gemsets, correctly specifying versions in your Gemfile can get you pretty far on this without them.
As far as alternatives, rbenv is the main one I'd check out.

How can I install a gem as if it was specified in a Gemfile?

I want to install a gem via gem install, but I need it to resolve with dependencies of the current project.
Basically I want the functionality that bundler gives me when I specify gem 'xyz' in a Gemfile, but I don't want to add that specific gem into the Gemfile.
I tried doing bundle exec gem install ... but it doesn't seem to work.
edit: The reason why I don't want to add it to the Gemfile is that it might be something like metric_fu, metrical, saikuro, rails_best_practices, etc. Simply gems that are kind of utility use and might only cluttler the project.
I might only want to use them temporarily, or install them, try out, if it doesn't work out the way I want do rvm gemset empty and bundle install again to clean up.
The point of Bundler is, in part, to prevent you from doing things like that (to prevent you from injecting gems from outside when your project doesn't declare them).
Looking for a way of doing that is looking for a bug in Bundler. If you did manage to find some way of skirting Bundler's enforcement mechanisms, you should probably not use it; instead, you may consider filing it as a bug with Bundler's issue tracker.
Now we come to the real questions: what can you do? and what should you do?
You should use either RVM gemsets or Bundler to isolate your application and its gem dependencies. You don't need both. I would recommend Bundler for this purpose over RVM gemsets.
You should add to your Gemfile any gems that you want to use and that integrate with your application (i.e., that either load your application or that are loaded as part of your application). This is not a requirement for any gems that refrain from integrating with your application.
You should refrain from committing a changed Gemfile or Gemfile.lock to version control until you are satisfied that your application continues to operate acceptably (tests pass, new gem does something useful, etc.).
Or you should stop using Bundler, because you want to do things it is explicitly designed to prevent you from doing (not recommended).
At the risk of sounding dumb, why not add it to the gemfile? You can always add it to its own group if you don't want to have to install it everywhere.
A slightly different approach is, if you're using version control, such as Git, to create a new branch and install the gems. If it doesn't work out, uninstall the gem (I'm not sure this will be done by bundle update on the old branch) and trash the branch. If it does, work, merge your stuff into the old the branch.
Though I do believe the other answers and comments have some very good points.

Benefits of RVM

Why should I/should I not use RVM?
I'm new to the ruby language and servers as a whole. I've had some trouble installing using RVM...so I'm inclined to not use it right now, but it seems like it may make installations down the road easier?
I'm interested to hear about your experience with RVM and your thoughts as it pertains to maintaining a server.
RVM is useful even if you don't want to install multiple versions at the same time. I'm a ruby hobbyist (PHP during the day :(), and I have no reason to want to use old versions, but I still use RVM.
Installing ruby is a pain. Getting it from the package manager (at least in ubuntu) gives you an outdated version that changes installation directories from the defaults. I've had nothing but problems with it.
So you think, "I'll just build it from source". Building from source requires getting a load of dependencies and configuring options. Often times I've built ruby only to find out I forgot to enable SSL support or readline support.
RVM takes care of all of this. In 3 or so commands, you have a perfectly built version of ruby.
And I didn't even cover how RVM manages multiple ruby installations for you, which is its killer feature. If you have that need, there is really no other sane solution.
RVM is great as this allows your to install different versions without touching your system's default Ruby install. It is rather similar to virtualenv's in Python.
Another great advantage to having RVM are the gemsets - you can create as many gemsets that are unique to the version, and patch level, of ruby.
I've extolled some of its virtues here and you should also see this blog post.
In terms of maintaining a server - let's take a Passenger install for example; do remember that Passenger is installed as a gem, so with rvm the benefit here is that you can have multiple installs of passenger, tied to a different version of ruby. Of course, typically, you'll have Passenger running on one version at a time, although there are ways to have Passenger, in particular, running on different ruby versions.
I use different Ruby versions for different projects (that's where .rvmrc is really handy). Some deployment environments are happy with 1.9, while there are a couple of legacy servers using 1.8 for some reasons. Also, occasionally I want to launch a specific version of ruby to compare how they work. RVM does all that for me.
When you are first getting used to Ruby, it may not entirely be necessary. That said, what it does is set you up for success in the future. Because once you get hooked, you may end up playing with projects that need to move from, say, MRI 1.8.x to 1.9.x. Or from 1.9.x, to JRuby 1.6.x. My experience is that this happens irregularly, but when it does, there's no substitute for RVM.
Outside of that, the other biggest feature that I use regularly, is the ability to segment one particular release. So I can have an environment for 'stable' gems, and an environment for 'unstable' gems. For instance, while Rails 3.1 has been in release candidate mode, I've had one main workspace for 1.9.2 and a separate space for Rails 3.1.rc? gems on 1.9.2. That makes it possible for me to keep developing my main Rails 3.0 stuff (with one command at the CLI), without having to specify full file paths to the appropriate rails bin files in order to use the older files.
If you're using a Debian based platform where the packagers/policy leads to a really bad default installation you'll have a way better experience using rvm.

Resources