2008-08-06

Aptana Jaxer でファイルをアップロードすると、特定の条件で mod_jaxer がエラーになる

次のようなフォームを使って、Aptana Jaxer に対してファイルをアップロードを試みました。

ファイルのアップロードは期待どおり動作するのですが、ファイルを指定せずにアップロードしようとすると、mod_jaxer がエラーになり、Apache が 500 Internal Server Error になってしまいます。

<form method="post" action="/picture.html" enctype="multipart/form-data">
<input id="form_picture" type="file" name="picture" value="" />
<input type="submit" value="写真をアップロードする ≫" />
</form>

Apache のエラーログには、次のように出力されます。

[Wed Aug 06 06:46:20 2008] [warn] (OS 10054)既存の接続はリモート ホストに強制的に切断されました。 : mod_jaxer: receive data over socket error: total len=3 read=0
[Wed Aug 06 06:46:20 2008] [warn] (-1)Unknown error: mod_jaxer: read data from socket error

いろいろ確認してみたところ、Safari 3 と Opera 9 (ともに Windows XP) でのみ再現することがわかりました。どうやら、ファイルを指定しないときの multipart/form-data の扱いが、ブラウザによって違いがあり、その違いが mod_jaxer の期待と異なることがあると推測できます。

次のように、送信ボタンに name="submit" と名前を指定したところ、この不都合は発生しなくなりました。つまり、multipart/form-data でファイルをアップロードするときは、type="file" 以外のフィールドも合わせて送信するのが無難そうです。

<form method="post" action="/picture.html" enctype="multipart/form-data">
<input id="form_picture" type="file" name="picture" value="" />
<input type="submit" name="submit" value="写真をアップロードする ≫" />
</form>

ということで、実用上は不都合はないという結論です。

Aptana Jaxer のバグ報告を検索してみましたが、それらしきバグは報告されていないようです。ここで扱った Aptana Jaxer のバージョンは 0.9.7.2472 (Windows XP) です。ですので、先日公開された 1.0.0 RC B では改善されているかもしれません。もしも、改善されていないようでしたら、Aptana に報告したいと思います。

2008-08-02

Aptana Jaxer で foo.html? といった ? で終わる ページは callback に失敗する

Aptana Jaxer で http://127.0.0.1:8081/foo.html? といった ? で終わる URL でページを表示し、JavaScript から Jaxer にコールバックしようとすると、次のような例外が発生します。



http://127.0.0.1:8081/foo.html のように ? がないときや http://127.0.0.1:8081/foo.html?bar のように ? 以降があるときは、このエラーは発生せず、期待どおり動作します。

注意さえすれば実用上は不都合ないと思いますが、気になったので原因を調べてみたところ、Jaxer が HTML ページをレンダリングするとき、自動的に追加する JavaScript コードに誤りがありました。

本来なら Jaxer.Callback.pageName の値には、このページの識別子が指定されるはずなのですが、? で終わるときのみ空欄になってしまいます。これはバグですね。

Jaxer.Callback.pageSignature = 610035010;
Jaxer.Callback.pageName = '';
Jaxer.CALLBACK_URI = '/jaxer-server/callback';
Jaxer.ALERT_CALLBACK_ERRORS = true;

具体的な事象が分かったので、Aptana に報告せねばと調べたところ、URL with question mark at the end fails Jaxer という Issue があり、解決済みとなっていました。貢献できると思ったのにちょっと残念。

ここで扱った Aptana Jaxer のバージョンは 0.9.7.2472 です。ですので、先日公開された 1.0.0 RC B では改善されているということですね(未確認です)。

Permission denied to get property Object.constructor

Firefox 3.0にFirebugアドオン(1.2.0b7)を入れたところ、JavaScriptを使ったページで次のエラーが表示されました。FirebugがFirebugを無効にすると直ります。
Permission denied to get property Object.constructor

Firebugは独自にプロパティのアクセス制御をしているのですね。便利ですが使う際に注意が必要そう。

2008-08-01

実践! Ajax フレームワーク jQuery

実践! Ajax フレームワーク jQuery という本が書店に並んでいました。パラパラっと流し読みした感じですと... (立ち読みしちゃった)

実践!Ajaxフレームワーク jQuery

jQuery API のメソッドを1つ1つ取り上げて、サンプルコードとその実行結果を見せながら解説するというスタイルになっています。jQuery 公式サイトの API リファレンスにもサンプル(demo)がありますが、少し読みにくく分かりにくい印象があるので、それを補うための本としての活用があると感じました。ですので、jQuery を使って WEB サイトをどう構成して開発していくかといった視点は弱いですね。

IE6/7 が Aptana Jaxer のレスポンスを誤認して文字エンコーディングの検出に失敗することがある?

Aptana Jaxer で、ある特定の条件で HTML ページをレンダリングすると、Internet Explorer で、誤った文字セットを使用して HTML ページがレンダリングされる という振る舞いが引き金となって、IE6 と IE7 で文字エンコーディングの検出を誤認することがあります。

HTML ページのなるべく先頭に、次のような meta 要素を指定しているにも関わらず、IE6 と IE7 は文字エンコーディングを UTF-8 でなく Shift_JIS として認識してしまいます。

<meta http-equiv="content-type" content="text/html; charset=UTF-8">

この文字エンコーディングの誤認は、Aptana Jaxer が HTML ページをレンダリングするときに自動的に挿入する、次のような script 要素の文字列長と関係しています(と推測しています)。

<html xml:lang="ja" xmlns="http://www.w3.org/1999/xhtml" lang="ja"><head>
<script src="/jaxer/framework/clientFramework_compressed.js?version=0.9.7.2472"></script>
<script>Jaxer.Callback.pageSignature = ...</script>
<meta http-equiv="content-type" content="text/html; charset=UTF-8">

Aptana Jaxer は、html 要素のすぐ後に Jaxer Client Framework の JavaScript ファイルと、サーバとクライアント間の引き渡すデータを JavaScript コードを追加します。この追加する JavaScript の文字列長は、クライアントからサーバにコールバックするかどうか、サーバからクライアントにデータを引き渡す かどうかの条件によって変わってきます。

Aptana Jaxer が追加する script 要素の位置を変更する方法は見つかっていないため、次のとおり、HTTP ヘッダを使って文字エンコーディングが UTF-8 であることを明示すれば、この問題は解決できます。

Aptana Jaxer の中で HTTP ヘッダを上書きできます。次のとおり、Jaxer.Response.addHeader メソッドを使って、Content-Type ヘッダを上書き(引数 true)します。このとき charset=utf-8 を明示します。

Jaxer.response.addHeader('Content-Type', 'text/html; charset=utf-8', true);
もしくは Apache 2.2 の MIME タイプの設定を、次のように変更します。このとき charset=utf-8 を明示します。

AddType "text/html; charset=utf-8" html
なお、このエントリで扱った Aptana Jaxer のバージョンは 0.9.7.2472 のものです。ですので、先日公開された 1.0.0 RC B では改善されているかもしれません(未確認です)。