You are or have been a Pythonista? You are or were in love with virtualenv, virtualenwrapper or Buildout? Now you do some Ruby you are looking for the same wonderful tools? You should take a look at RVM or Ruby Version Manager.
Oh, well. You are or have been a Rubyist? You are or were in love with RVM? Now you do some Python you are looking for the same wonderful tool? You should take a look at virtualenv (with virtualenvwrapper).
Installation
I am a Pythonista
First, make sure pip is installed on your system.
Then, in your terminal:
sudo pip install virtualenvwrapper
Create the directory which will contain your virtual environments. For example,
$HOME/.virtualenvs
:
mkdir ~/.virtualenvs
Edit your $HOME/bash_profile
file and add these lines:
export WORKON_HOME=$HOME/.virtualenvs
export PIP_VIRTUALENV_BASE=$WORKON_HOME
export PIP_RESPECT_VIRTUALENV=true
Source it:
source ~/.bash_profile
Troubleshooting? Check the documentation.
I am a Rubyist
First, make sure Git is installed on your system.
Then, in your terminal:
bash < <( curl http://rvm.beginrescueend.com/releases/rvm-install-head )
Edit your $HOME/.bash_profile
file and add this line at the very end:
[[ -s "$HOME/.rvm/scripts/rvm" ]] && . "$HOME/.rvm/scripts/rvm"
Source it:
source ~/.rvm/scripts/rvm
Troubleshooting? Check the documentation.
Managing multiple interpreters
I am a Pythonista
You have to install the different Python versions on your system (via your
package manager). When you will create a virtual environment with
virtualenv, you will pass the interpreter path of the desired Python
version as -p
argument of mkvirtualenv
command.
Example:
mkvirtualenv -p /opt/local/bin/python3 myproject
I am a Rubyist
RVM compiles and installs the desired Ruby interpreter and Ruby version in the current user directory. It supports MRI/YARV, Rubinius, JRuby, Ruby Enterprise Edition, MagLev, IronRuby, MacRuby and GoRuby. This can be achieved in a single one command.
To list the available interpreters and versions to which it may install:
rvm list known
Let’s install the original implementation in version 1.8.7 and 1.9.2 (make sure Subversion is installed):
rvm install 1.8.7
rvm install 1.9.2
This takes some compilation time and you’ve done.
To list the installed Ruby versions:
rvm list rubies
To switch between interpreters:
rvm use RUBY_VERSION
For example, switching to 1.8.2:
rvm use 1.8.2
Or switching to 1.9.2:
rvm use 1.9.2
To set up the default interpreter:
rvm --default use RUBY_VERSION
For example, if you want to use Ruby 1.9.2 as default interpreter:
rvm --default use 1.9.2
To switch back to your default system interpreter:
rvm use system
This is very powerful. Check the documentation to know more about available commands and options.
Managing multiple environments
I am a Pythonista
Generally, with virtualenv, you create one environment per project and/or
project stage (development, testing, staging, production, etc). This can be
accomplished with the mkvirtualenv
command:
mkvirtualenv --no-site-packages PROJECT_NAME
For example, if my project name is “superdjango”:
mkvirtualenv --no-site-packages superdjango
The --no-site-packages
option removes the standard site-packages
directory
from the environment sys.path
. I recommend to use this option if you want
more isolation. It avoids dealing with system packages conflicts.
As seen above, you can specify the Python version with the -p
option:
mkvirtualenv --no-site-packages -p /opt/local/bin/python3 PROJECT_NAME
If you added export PIP_RESPECT_VIRTUALENV=true
in your $HOME/.bash_profile
file, when your environment is active, pip
auto-installs packages in this
environment. You do not have to prefix it with any sudo
command or have to
pass it any option. Just this:
pip install PACKAGE
Example:
pip install Django
Otherwise, you need to use the -E
option:
pip install -E ENVIRONMENT_NAME PACKAGE
Example:
pip install -E superdjango Django
To list all available environments, use the workon
command:
workon
To activate an environment:
workon ENVIRONMENT_NAME
Example:
workon superdjango
The first time you create a virtual environment with the mkvirtualenv
command, you will auto-switch to this environment instantly (the environment
name prefixes your session prompt).
To deactivate the current environment, use the deactivate
command:
deactivate
To delete a virtual environment:
rmvirtualenv ENVIRONMENT_NAME
Example:
rmvirtualenv superdjango
I am a Rubyist
Where virtualenv has “environments”, RVM has “gemsets”. Interpreters and packages are all separated and self-contained from system and from each other. Creating a virtual environment with virtualenv is creating a gemset with RVM. Generally, you create one gemset per project and/or project stage (development, testing, staging, production, etc). This can be done with this command:
rvm use RUBY_VERSION@GEMSET_NAME --create
Example:
rvm use 1.9.2@myproject --create
This is equivalent to:
rvm use 1.9.2
rvm gemset create myproject
rvm gemset use myproject
When your gemset is active, using gem install
command will install packages
directly in your gemset. So you can use:
gem install PACKAGE
This will install the given package in your current active gemset directory.
To know the path of this directory, you can use the gemdir
RVM command:
rvm gemdir
Deleting a gemset is simple as:
rvm gemset delete GEMSET_NAME
Example:
rvm gemset delete myproject
To empty a gemset (removing all installed gems):
rvm gemset empty GEMSET_NAME
Example:
rvm gemset empty myproject
Managing project dependencies
I am a Pythonista
Managing project dependencies with Pip and virtualenv is crazy simple. You
just have to create a text file containing package names (and optionally
package versions) and give this file to Pip via the -r
option. Everything
is clearly well explained in the documentation.
To give you an example, for my “superdjango” project, I create a
requirements.txt
file to start my project with Django
1.2.x and South support. This requirements.txt
file looks like this:
Django >= 1.2
South == 0.7.2
If I don’t already created my environment, I create it right now:
mkvirtualenv --no-site-packages superdjango
And I install project dependencies:
pip install -r /path/to/my/requirements.txt
This will install the latest Django 1.2 version and South 0.7.2 into my virtual environment.
I am a Rubyist
Managing project dependencies with RVM, RubyGem and Bundler is crazy simple too.
Where Pip has “requirements” files, Bundler has “Gemfile” files.
First, you need to create a dedicated gemset for the project:
rvm use RUBY_VERSION@GEMSET_NAME --create
Example:
rvm use 1.9.2@myproject --create
This is the same of these commands:
rvm use 1.9.2
rvm gemset create myproject
rvm gemset use myproject
I install Bundler into my gemset:
gem install bundler
I create a directory for my project:
cd /path/to/my/workspace
mkdir myproject
I go in the directory and create an empty Gemfile
file:
cd myproject
bundle init
Then I edit the Gemfile
file and add my dependencies:
source "http://rubygems.org"
gem "sinatra", "~> 0.9.0"
gem "rack-cache"
gem "rack-bug"
Now, I install dependencies in the current gemset:
bundle install
That’s all. Everything is clearly well explained in the documentation.
Conclusion
RVM and virtualenv (coupled with virtualenvwrapper) are both powerful tools which considerably improve your productivity and reduce headache fighting with dependencies. Today, I can’t even imagine living without. I didn’t cover Buildout, the Python alternative to virtualenv, because it works a different way but it’s a wonderful tool you should give it a try. These articles, written by Jacob Kaplan-Moss, are must-read: