@maihaさんを中心として、私やMerb勉強会の参加者によって作り続けていたMerbのRuby-1.9.1対応のパッチ群が、Merb本体に取り込まれました。

http://github.com/wycats/merb/commits/
Merb勉強会での活動が実を結んだわけです。
めでたいです。ありがとうございます。
Merb-1.1では、Ruby-1.9.1に対応したMerbがリリースされそうです。
@maihaさんを中心として、私やMerb勉強会の参加者によって作り続けていたMerbのRuby-1.9.1対応のパッチ群が、Merb本体に取り込まれました。

http://github.com/wycats/merb/commits/
Merb勉強会での活動が実を結んだわけです。
めでたいです。ありがとうございます。
Merb-1.1では、Ruby-1.9.1に対応したMerbがリリースされそうです。
EC2のサーバ上でruby-1.8.x系で動作しているpassenger(aka mod_rails)
と平行して、ruby-1.9.1を動かす環境を用意するために色々と試行錯誤を繰り返していたのですが、ひとまず良さそうな構成に落ち着いたのでメモしておきます。
構成
入り口から順に並べるとこんな感じです。
apache2はpassengerを使っているので外せないとして、
ruby-1.9.1で動かすサービスはmod_proxy_balancerを使う事にしました。
最初はバックエンドに直接merb clusterを当てていたのですが、
現状のmerb clusterにはgraceful reloadする機能が無いようだったので、
間になにか挟む事にしました。
そこで、以前から目を付けていた
Swiftiply
を試す事にしました。
Swiftiplyはとても面白い設計のウェブサーバで、そのへんは
rakutoさんの記事
「[Rails] Swiftiplyのアーキテクチャとベンチマーク」
を読むのがわかりやすいでしょう。
merbはbuilt-inでSwiftiply用のアダプター(SwiftipliedMongrel adapter)を備えているので、Swiftiplyを起動する設定をおこなえば、使うのはわりと簡単です。
しかし、例によってswiftiplyが依存しているeventmachineがruby-1.9.1
でインストール出来なかったので、原因を調査。
単純にテストの実行だけがうまく動いてないようだったので、テスト無しでインストールしました。
あとは、swiftiplyの起動スクリプトを用意。
/etc/init.d/swiftiply
ruby>>
#!/usr/bin/env ruby
PID = "/var/run/swiftiply.pid"
case ARGV[0]
when 'start'
if File.exist?(PID)
puts "swiftiply is already started."
exit 1
end
print "Starting swiftiply: "
pid = fork do
Process.setsid
Process.exec "swiftiply", "-c", "/etc/swiftiply.yml"
end
begin
open(PID, "w"){|file| file.write pid}
puts "done"
rescue Exception => e
puts e.message
Process.kill 9, pid
end
when 'stop'
print "Stopping swiftiply: "
begin
pid = open(PID).read.to_i
File.unlink PID
Process.kill 9, pid
puts "done"
rescue Exception => e
puts e.message
end
when 'restart'
system $0, 'stop'
system $0, 'start'
else
puts "usage: {start|stop|restart}"
end
<<--
アプリケーションの起動、停止は以下のようにおこないます。
pre>>
cd #{current_path}; #{merb} -K all
cd #{current_path}; #{merb} -e production -a swift -c 1 -p 30000
<<--
これで動きますが、プロセスが死んだりすると不安なので、
monitを使って死活管理をおこなうようにします。
/etc/monit/monitrc
pre>>
check process swiftiply
with pidfile /var/run/swiftiply.pid
group root
start program = "/etc/init.d/swiftiply start"
stop program = "/etc/init.d/swiftiply stop"
if failed port 4000 then restart
if 5 restarts within 5 cycles then timeout
check process merbist
with pidfile /mnt/app/merbist/current/log/merb.30000.pid
group root
start program = "/mnt/app/merbist/shared/script/start"
as uid app and gid app
stop program = "/mnt/app/merbist/shared/script/stop"
as uid app and gid app
if failed port 30000 then restart
if 5 restarts within 5 cycles then timeout
depends on swiftiply
<<--
以上で完了。
現在、http://merbi.st/ は上記の設定で動いています。
See Aslo
追記
しばらく運用してみたのですが、プロセスが数時間に一回ぐらいのペースで落ちる問題があったので、Swiftiplyの代わりにPoundを使う構成に変えました。
Swiftiplyは次のバージョン0.7.0から、クラスタリングのサポートが強化されるようなので、それまで待ってみた方が良いかもしれないですね。
Ruby-1.9.1を使うと、
以下のようにして簡単にRubyVMのInstaractionSequenceを見る事が出来ます。
ruby>>
puts RubyVM::InstructionSequence.new("puts 'Hello, world!'").disasm #=> nil
== disasm: <RubyVM::InstructionSequence:@ >==========
0000 trace 1 ( 1)
0002 putnil
0003 putstring "Hello, world!"
0005 send :puts, 1, nil, 8,
0011 leave
<<--
生成したInstractionSequence(aka iseq)は、evalメソッドを呼び出して実行する事もできます。
ruby>>
RubyVM::InstructionSequence.new("puts 'Hello, world!'").eval #=> nil
Hello, world!
<<--
さらに、to_aメソッドで個々のインストラクションに分解する事も出来ます。
ruby>>
RubyVM::InstructionSequence.new("puts 'Hello, world!'").to_a
["YARVInstructionSequence/SimpleDataFormat", 1, 1, 1, {:arg_size=>0, :local_size=>1, :stack_max=>2}, "", " ", :top, [], 0, [], [1, [:trace, 1], [:putnil], [:putstring, "Hello, world!"], [:send, :puts, 1, nil, 8, nil], [:leave]]]
<<--
今月もRails勉強会
に行ってきました。
Merbのセッションをやる予定でしたが、1.9.1対応の話とネタが被ったのでマージしました。
ということで、会場ででてきた修正案
ruby>>
static int
file_load_ok(const char *path)
{
return eaccess(path, R_OK) == 0 && rb_file_file_p(Qnil, rb_str_new2(path));
}
<<--
eaccessでチェックしてるだけだったので、環境によっては
ディレクトリをloadしようとしてエラーが発生してしまうようです。
この問題が発生する典型的な例としては、
pre>>
lib/foo/
bin/foo
<<--
というようなディレクトリ階層にある場合に、load "foo"を行う場合が挙げられます。
結構深刻な問題だと思うので、早いうちに修正版のruby-1.9.1がリリースされると良いです。
懇親会ではCOBOLの話をしてました。
メタコボラーの時代がくる!?
Ruby-1.9.1がリリースされて以来、
@maiha
さんと一緒にMerbのRuby-1.9.1対応のための作業を続けてきましたが、
ようやくMerbアプリケーションをRuby-1.9.1で動かす事ができました。
決定的に重要だったのは、@ko1_twitterさんが作ってくれた
methoparaです。
これによって、merbが抱えていたmerb-action-argsに関する問題を解決するための道が開かれ、Ruby-1.9.1対応を行うためのモチベーションが高まりました。
今回のRuby-1.9.1対応のために作ったパッチや、修正版のGemなどの多くは
github上に残っています
(http://github.com/maiha, http://github.com/genki)
残りは、http://merbi.st/pluginsで公開されています。
Good luck!
The ruby-1.9.1 had come to the world, and
several days went by...
@maiha
and I have worked for making the merb to be correspond to the ruby-1.9.1.
And now we are very happy, because we can announce there is the first child of Merb and ruby-1.9.1.
http://merbi.st is the site which is running on merb with ruby-1.9.1.

Our efforts are remaining at several places.
Most of them are in github
(see http://github.com/maiha,
http://github.com/genki).
Others are published on here http://merbi.st/plugins
Good luck!
irb_rocketがRuby-1.9.1で動かないよ、というコメントを頂いたので、
ruby-terminfoをRuby-1.9.1対応にしてみました。
これでirb_rocketをRuby-1.9.1で使う事が出来ます。
pre>>
% sudo gem install irb_rocket --source http://merbi.st
<<--
@maiha
さんがRuby-1.9.1でMongrelをインストールできるようにしてくれました。
修正したバージョンは、以下のコマンドでインストール出来ます。
pre>>
% sudo gem install mongrel --source http://merbi.st
<<--
不要になったと思われるfastthread関係のgemへの依存を切っています。
それにしても、Mongrelってメンテナンスされてるのかな。
結構メンテナンスされてるのかどうなのかわからないGemがあって悩みどころですね。
methopara
is a gem that enables us to use Method#parameters with Ruby-1.9.1.
It was originally made by @ko1_twitter, the creater of YARV, at the previous meet-up of asakusa.rb.
And this time, I added an interface to use it for UnboundMethod.
Now you can use UnboundMethod#parameters with new methopara, like this.
ruby>>
require 'rubygems'
require 'methopara'
class Foo
def foo(a,b) end
end
Foo.instance_method(:foo).parameters
#=> [[:req, :a], [:req, :b]]
<<--
Enjoy!
Yesterday (Feb 10, 2009),
asakusa.rb
took place at Akihabara, Tokyo.
asakusa.rb is a rubyist community that is based on Asakusa.
In the monthly meet-up of that community,
@ko1_twitter wrote a code snippet.
This snippet is a kind of backport of Method#parameters for Ruby-1.9.1.
His quick job led a way for merbists to change merb to be corresponding to Ruby-1.9.1.
He named his work "methopara". It stands for METHOd PARAmeters.
And I made it as a gem
for ease of use.
Now we can use it by the command below.
pre>>
% sudo gem install methopara --source http://merbi.st
<<--
Usage is as follows.
ruby>>
require "rubygems"
require "methopara"
def foo(a,b=nil,&c) end
method(:foo).parameters
=> [[:req, :a], [:opt, :b], [:block, :c]]
<<--
This gem is only for Ruby-1.9.1.
Because Ruby18x have merb-action-args, and Ruby-1.9.2 and its successors will have built-in Method#parameters.
Enjoy!
See Also
Ruby-1.9.1では、以下のように配列リテラルの中でHashを定義する事が出来るようになったのですね。
ruby>>
[:foo, :bar => :baz]
#=> [:foo, {:bar=>:baz}]
<<--
いままでも、
ruby>>
[:foo => :bar]
<<--
のような形式であればOKだったのですが、配列リテラルの中に
Hash以外の要素を含む場合には構文エラーが発生していました。
We are excited about Ruby 1.9.1. Of course, with all the performance improvements, who wouldn’t be? Unfortunately a large number of Ruby libraries and extensions still don’t work on 1.9.1, so Ruby 1.9 cannot be considered production-ready yet.
しばらくは大きなプロジェクトのRuby-1.9.1対応がにぎやかになりそうですね。
安定板のリリースは重要だな。
Merbはまだaction-argsの問題があるけど、
1.9.1でMethod#parametersが出なかったので、
ParseTreeあたりが1.9.1に対応する感じで進化して対応される気がする。
せめてProc#to_sourceがあればripperを使ってなんとか出来たと思うんだけどなー。
merbで採用されているジェネレータフレームワークの本命、
templater
に、ruby-1.9.1対応のパッチを取り込んで頂きました。

レガシープロダクトをruby-1.9.1に対応させる方法のメモです。
#include "re" は #include "ruby/re"#include "st" は #include "ruby/st"merb本体全部対応するのはちょっと厳しかったので、
merb-genを起動する所までで必要なgemをruby-1.9.1対応にしてみました。
これに加えて、merb-gen自体のコードもruby-1.9.1対応させました。
これでmerb-genコマンドでappのひな形を生成する所までは動きます。