(2004.03.27新規作成。2004.12.31更新。)
Rubyは、バージョン1.6から1.8にバージョンアップしたときに、CGIライブラリが変更され、非互換な部分が生じています。Ruby 1.6用に書かれたCGIスクリプトを両方で動かすことができません。
この話は、拙著『基礎から学ぶWebデータベースプログラミング』でも解説しています(p.192-193)。
Ruby CGI Adjusterは、次のことを行うための、小さなスクリプトです。
Ruby's ライセンスとします。LICENSE
Ruby 1.6用のCGIスクリプトで、次のようになっているところ;
require "cgi"または
require "cgi/session"を、次のように修正します。
$COMPAT_VERSION = "1.6" require "cgisup.rb"
Ruby 1.8用のスクリプトでは、$COMPAT_VERSION に代入せずに、次のようにしてください。
require "cgisup.rb"
Ruby 1.6モード($COMPAT_VERSION == "1.6")では、@params[key] と同じ。
Ruby 1.8モードでは、次のように動作する。
次のようにして使う。
require "cgisup.rb" cgi = CGI.new text = cgi.get("text") file = cgi.file_control("file") size = file.size body = file.read
通常、CGIクラスの[]メソッドでフォームのコントロール値を取り出します。CGI#[]の戻り値は、Rubyのバージョン、formタグのenctype属性値によって、それぞれ次のようになります。
enctype属性値 | Ruby 1.6の場合 | Ruby 1.8の場合 |
---|---|---|
application/x-www-form-urlencoded (省略値) | コントロール値(文字列)の配列、またはnil | コントロール値を格納したCGI::QueryExtension::Valueインスタンス、または"" |
multipart/form-data | コントロール値を読むためのTempfileインスタンスの配列、またはnil | コントロール値を読むためのStringIOまたはTempfileインスタンス |
問題は、次の2点。
どうしてこういう惚(とぼ)けた失敗をやらかすのか理解できません。ライブラリでは通常、既存のプログラムが動かなくなるような事態を避けるために、すでにあるメソッドの動作は変えず、新しいメソッドを作るものです。基礎的なものであるほど変更は慎重に行わなければなりません。
それはともかく、この問題を解決するために、次の方針で臨むことにします。
Rubyはすでにあるクラスの定義を書き換えられるのが助かります。Ruby 1.6用のスクリプトの場合は、1.6と同じ動作になるようにCGI#[]を定義しなおします。Ruby 1.8.1でもRuby 1.8.0と非互換な変更が入っている(ふざけているの?)ので、それも潰しておきます。