見よう見まねで、ssbをRackに対応させてみた

とりあえず、mobile.hatena.ne.jpが(ぱっと見)表示できるところまでは確認した。

まじめにやるなら、WEBrick前提なところを全部Rack前提にいじる必要がある様な気がしますが、まだRack対応についてよく理解できていないので、今回はcallメソッドを追加してごまかしてみました。

以下の様な、libs/ssb/rack.rbという拡張用のライブラリファイルを追加。

rackupで動かすために、config.ruを追加。

後は、rackupでサーバを起動。動かすウェブサーバの指定については、何も考えていないので、結局、WEBrickで動いてましたが、一応、Rack越しにアプリケーションが動かせる事が確認できました。

問題は、call(env)として動かすために、run(cgi_request, cgi_response)で受け取る引数のごまかしが適当すぎる事でしょうか。cgi_requestは、Rack::Requestを使ってごまかしていますが、cookiesのところが個人的に鬼門なので、本当に適当です。挙動の検証すらしていません。動けばよしでやっつけました。cgi_responseは、さらに適当です。使っているインターフェースに適合させただけです。

この状態でmod_passengerを使って動かせるかは未確認ですが、ひとまずRackを使えた事に満足しました。


mod_passenger(2.0.3)でも動く事が確認できました。最初のコードに少々手を加えています。

  • Lintでenv['CONTENT_LENGTH']を文字列で入れろと出るのでLintを省略
  • staticなファイルはmod_passenger側でファイル読み込みになるので省略
  • mod_passengerを使っているかどうかの判断はENV['RACK_ENV']で
  • 一部WEBrickを使用する部分でrequireと名前の絶対表記が必要だったので修正

CONTENT_LENGTHの件は、よく分かりません。WEBrickで動かしたときには問題がなかったので、mod_passengerで動かした場合にLintが妙な動きをするんでしょうかね。


Rack::Lintのcheck_envは、アプリケーションのcallが実行される前に実行される様子。つまりは、レスポンスのCONTENT_LENGTHではなくて、リクエストのCONTENT_LENGTHもしくは、環境変数の初期状態についてチェックしているという事になる。

問題となっているのは、CGIキーが文字列(String)であるかどうか、というところ。rack/lint.rbの140行目あたり。ハッシュのenvをeachでまわしているので、CONTENT_LENGTHというキーは存在している事になる。

mod_passengerから渡るenvは、リクエストヘッダをパースしたもの。ただ、CONTENT_LENGTHは必ず代入されるため、キーは必ず存在する事になる。このときヘッダのHTTP_CONTENT_LENGTHというキーに該当する値が使われる(passenger/abstract_request_handler.rbの293行目あたり)。

Content-Lengthヘッダは、必ず存在するヘッダフィールドではないので、mod_passengerの問題となるのでしょうか。それとも、自分が見たコードは、転送コーディングが施されていない場合にのみとおる部分だったりするんでしょうか。

Rack::Lintが必須キー以外についても、Stringの型判定をしているのが悪いのでしょうか。個人的には、必須でないとされているものについては、nilを許容してもいい気がしています。が、Lintだから厳しい限りは問題ないというか、そうすべきな気もしています。

結局、この件については、放置です。

プロフィール

このブログ記事について

このページは、koshigoeが2008年9月 6日 23:46に書いたブログ記事です。

ひとつ前のブログ記事は「Rackに興味を持ってみたり」です。

次のブログ記事は「ひとまず、ssb導入後記など」です。

最近のコンテンツはインデックスページで見られます。過去に書かれたものはアーカイブのページで見られます。