rbenv といえば 複数バージョンの Ruby を切り替えて使うための環境を提供してくれる便利なツールとして欠かすことのできないものですが、機会があってそれがどうやって動いているか調べたので、ここに書いておきます。また ruby-build は ruby をインストールするためによく使われている(というか使ってない人いないのでは)rbenv のプラグインです。rbenv install
というコマンドは ruby-build が提供しています。これについても一緒に書きます。
はじめに断っておきますが、間違ったことを書いているかもしれないのでその辺はご了承ください。また、将来 rbenv の変更によって変わってしまう部分もあるかもしれません。
また rbenv のドキュメントはとても充実しているので、それを読めばここに書いてあることはだいたいわかると思います。
もくじ
- rbenv のインストール方法による違い
- RBENV_ROOT とはなにか?
- rbenv init はなにを行うのか
- rbenv は ruby-build をどのように使うか?
- 新しい ruby を入れたい。それぞれのインストール方法でどうやるか?
- 情報源
1. rbenv のインストール方法による違い
Mac で rbenv を使う場合、2通りの方法があります。
- Github から checkout してくる
- homebrew を使う
この2つ、何が違うのでしょうか?
1つ目の違いはインストール場所です。
Github から checkout
以下の場所にインストール(git clone)します。
- rbenv は
$HOME/.rbenv
- ruby-build は
$HOME/.rbenv/plugins/ruby-build
homebrew
以下の場所にインストールされます。
- rbenv は
/usr/local/Cellar/rbenv/バージョン番号
- ruby-build は
/usr/local/Cellar/ruby-build/バージョン番号(年月日)
また、homebrew の仕組みにしたがって、適切なバージョンの実行可能ファイルに /usr/local/bin
からのシンボリックリンクが作成されます。
こんな感じ。
$ ll /usr/local/bin/{rbenv,ruby-build} lrwxr-xr-x 1 takatoshi admin 31 6 19 2013 /usr/local/bin/rbenv@ -> ../Cellar/rbenv/0.4.0/bin/rbenv lrwxr-xr-x 1 takatoshi admin 44 1 8 22:33 /usr/local/bin/ruby-build@ -> ../Cellar/ruby-build/20141225/bin/ruby-build
2つめの違いはインストールされるファイルです。
Github から checkout する場合は(当たり前ですが)リポジトリの内容そのままになります。
homebrew の場合はリリースパッケージに含まれるファイルがインストールされます。具体的には homebrew の Formula
- homebrew/rbenv.rb at master · Homebrew/homebrew · GitHub
- homebrew/ruby-build.rb at master · Homebrew/homebrew · GitHub
を見ればわかりますが、Releases · sstephenson/rbenv · GitHub にある Source code (tar.gz) を解凍したものになっています。
2. RBENV_ROOT とはなにか?
RBENV_ROOT というのは rbenv の shims (後述) と versions (Ruby のインストール先) がある場所(パス)を指し示すための環境変数です。
rbenv コマンドを叩いた時に未設定なら $HOME/.rbenv
になります(ここで設定している)。
RBENV_ROOT の値を見るには rbenv root
コマンドを使います。RBENV_ROOT 環境変数が空っぽの時に $HOME/.rbenv
になっているのがわかります。
$ echo $RBENV_ROOT $ rbenv root /Users/takatoshi/.rbenv
ちなみに RBENV_ROOT は特に理由がなければデフォルトのままにしておくのがオススメらしいです。 そして mislav (Mislav Marohnić) · GitHub さんによると変更する理由は思いつかないとのこと。
参考URL
そして RBENV_ROOT を変更する場合は rbenv init
する前にやる必要があります。
理由はデフォルトが$HOME/.rbenv
になるということと rbenv init
が何を行うかを知ればわかります。
3. rbenv init はなにを行うのか
rbenv のインストール手順を見ると .bash_profile
の中で eval "$(rbenv init -)"
を実行するように書いてあります。
3. Add rbenv init to your shell to enable shims and autocompletion. $ echo 'eval "$(rbenv init -)"' >> ~/.bash_profile
これは何を行うのでしょうか? 答えは書いてあるとおり、shims と autocompletion を有効化します。 ・・・って、それなに?
sstephenson/rbenv · GitHub を見るともっと詳細に書いてあります。
これを見ると shims を有効化するというのは $RBENV_ROOT/shims
を PATH に入れることだというのがわかります。
実際に shims を見てみると以下のファイルが入っていました。
$ ls `rbenv root`/shims bundle bundler erb gem irb rake rdoc ri ruby testrb
rbenv init
コマンドの実体は rbenv/rbenv-init at master · sstephenson/rbenv · GitHub です。これを見ると shims の有効化をする前に $RBENV_ROOT
の下に shims と versions というディレクトリを作っているのがわかります。またその後で rbenv rehash
しています。
rbenv rehash
が何をするか?それはここに書いてあります。
これは Ruby の実行可能ファイルの shims を作成する(し直す)コマンドです。shims とは実行可能ファイル(ruby, rake など)のラッパースクリプトで、その中では rbenv exec
コマンドを使って ruby や rake などを実行しています。だから、新しいバージョンの Ruby を入れたときや、実行ファイルを提供する gem を入れたあとに実行するとよいのです。
rbenv/rbenv-rehash at master · sstephenson/rbenv · GitHub
4. rbenv は ruby-build をどのように使うか?
ruby-build を入れると rbenv install
コマンドが使えるようになります。
rbenv init
もそうですが rbenv のコマンドはすべてこのようなプラグイン方式になっています。
では、まず init や install というコマンドはどのように実行されるのでしょうか?
それを知るためには rbenv/rbenv at master · sstephenson/rbenv · GitHub を見ればよいです。
がその前に、ドキュメントにも書いてあるので先にそっちを見てみましょう。
https://github.com/sstephenson/rbenv/wiki/Plugins
A plugin can be installed by dropping it in as a sub-directory of $RBENV_ROOT/plugins, or it can be located elsewhere on the system as long as rbenv-* executables are placed in the $PATH and hooks are installed accordingly somewhere in $RBENV_HOOK_PATH.
- プラグインは
$RBENV_ROOT/plugins
に配置する - または
rbenv-*
(*
は init とか install とか)という実行可能ファイルが PATH のどこかにあればよい
前者は git clone でプラグインを入れた場合、後者は homebrew で入れた場合に対応すると考えられます。
また、プラグインの作り方というドキュメントもあります。
https://github.com/sstephenson/rbenv/wiki/Authoring-plugins
rbenv がコマンドを実行する前にやっていることは、ほとんどこのドキュメントに書かれている気がします。
簡単に言うと、
- コマンドを実行するための環境を準備
- コマンドを実行
これだけ。環境を準備というのは、RBENV_ROOT、PATH、RBENV_HOOK_PATH などの環境変数を設定したりすることです。
5. 新しい ruby を入れたい。それぞれのインストール方法でどうやるか?
ここまでくれば、これも容易にわかるでしょう。 Github checkout と homebrew の違いはインストール場所です。
つまり rbenv install バージョン番号
したときの挙動はこうなります。
Github checkout のとき
$RBENV_ROOT/plugins/ruby-build/bin/ruby-build
が実行される- したがって、ここにある ruby-build を 最新にしておけばよい(通常は
git pull
すればいいだろう)
homebrew のとき
- PATH のどこかにある ruby-build が実行される
- それを最新にするのは homebrew の役割だ(通常は brew update && brew upgrade ruby-build すればいいだろう)
6. 情報源
この2つを見ましょう。