CGI.pmを継承して漢字コードの変換をする必要性に疑問
はてなブックマークでちらりと見かけたid:hidedenさんのこのエントリー。すでにプログラムな視点からはSawaさんが議論されていますが、斜めからの意見としてはCGI.pmを継承してまで漢字コードの変換をする必要性を考える事が必要かなと思う。
一般的なブラウザならば、ページのエンコーディングとPOST/GETのリクエスト文字列のエンコーディングは同じ(ハズ)です。Perlでプログラムを作るのであれば、EUC-JPまたは最近であればUTF-8でコーディングしていると思います。プログラムからの出力も同じエンコーディングで行えばまったく問題ありません。わざわざJcodeを挟み込んだりすると漢字コードの判断ミスがおきて逆に文字化けしてしまうこともあるでしょう。
しかし、一般的なブラウザではない携帯電話の場合、ページのエンコーディングはShift_JIS、サーバサイドの文字コードはEUCなどとするのが通常の流れだと思います。その時は仕方がないので「現在のエンコーディングを指定」しつつ変換するのが良いでしょう。フレームワークを使うのも手です。
例によってCGI::Applicationならば、
package MyApp; use strict; use base qw(CGI::Application); use Jcode; sub cgiapp_init{ my $self = shift; $self->header_props(-charset=>'Shift_JIS'); } sub cgiapp_prerun{ my $self = shift; #Sledge::Charset::Shift_JISを参考 for my $p ($self->query->param) { my @v = map { Jcode->new($_, 'sjis')->h2z->euc } $self->query->param($p); $self->query->param($p,@v); } } sub cgiapp_postrun{ my $self = shift; my $bodyref = shift; $$bodyref = Jcode->new($$bodyref,'euc')->sjis; } 1;
動作確認はしていませんが、こんな感じでしょうか。
携帯電話ならJcodeよりUnicode::Japaneseの方が魅力的なメソッドが並んでおります。
コメント
はじめまして!
あくまであれはネタと受け取ってくださいませ。確かに主要ブラウザでは文字コードはページのエンコードにあわせてくれますし、通常なら問題はほとんどありません。
ただし、ページエンコーディングを故意に文字化けするように手動で選択した場合などではページエンコーディングと違う文字コードでPOSTする等の事も可能ですし、極まれではありますが、そういう意地悪な事をするユーザーも存在します。
実際に半角カナなどを多用する可能性がある場合などには誤判定防止用にtype="hidden"である文字列を渡し、バイナリレベルでそれをコード判定用に使用し、変換が不要だった場合には変換処理をしない等の負荷的な面での機構も組み込んでいます。
また、実際のところは文字コード変換よりは携帯絵文字の相互変換やエスケープなどをする為だったりします。その他強制的に数字を半角にして読み込むとか、あったら楽だな系を集めた感じになってます。笑
また、DBへはUTF8で格納するけど、表示はSJIS等の変な仕様の時に、
my %data = $q->Vars;
$q->set_code('utf8');
ClassDBI::table->create(\%data);
$q->set_code('sjis');
$tt->process('hoge.tt', \%data, \$out);
のように切り替えて使ったりもします。まぁVarsとか言うマイナー?な物にこだわってた理由もここにあったりします。
結局は手抜きしやすいように作っただけなので、軽くネタだと思って受け流してくださいませ!blogにソースだらだら長いの載っけても誰も読まないよなーって事でちょっとわかりづらい例しか示せず申し訳ないです。
投稿者: hideden | 2005年11月14日 22:36