minimize

事業拡大のため、新しい仲間を募集しています。
→詳しくはこちら

WebWork(2.2.4以降)についての各種Tipsです。
新しく書いたものが上になるように並べてあります。

リソースの Encoding について

Velocityを使う場合に、リソースの Encoding を指定する方法を紹介します。

入力、出力の文字エンコーディングが全て同じ場合、
webwork.properties に

webwork.i18n.encoding = 文字エンコーディング名

と指定すればOKです。

しかし、リソース毎に異なるエンコーディングにしたい場合は少し厄介です。

Velocityの出力をつかさどっているのは com.opensymphony.webwork.dispatcher.VelocityResult なのですが
このクラスの getEncoding() を見てみると以下のようになっています。

protected String getEncoding(String templateLocation) {
    String encoding = (String) Configuration.get(WebWorkConstants.WEBWORK_I18N_ENCODING);
    if (encoding == null) {
        encoding = System.getProperty("file.encoding");
    }
    if (encoding == null) {
        encoding = "UTF-8";
    }
    return encoding;
}

要するに、全リソース固定の文字エンコーディングしか利用できないのです。
なので、ここを変えるには VelocityResult を拡張しなければなりません。

public class ExtVelocityResult extends VelocityResult {
    @Override
    protected String getEncoding(String templateLocation) {
        ...
    }
}

こんな感じで拡張クラスを作成し、getEncodingメソッドをオーバーライドします。
templateLocation にリソースのパスが渡ってくるので
この情報を元に文字エンコーディングを変更させることができます。
ただし、このエンコーディングは入力と出力の両方を兼ねているので
両者を異なる値にすることはできません。ここではその方法までは追求しないことにします。

とりあえずこの拡張Resultを使うには、xwork.xml に以下の記述をします。

<result-types>
  <result-type name="velocity" class="パッケージ名.ExtVelocityResult" />
</result-types>

name属性を"velocity"にすれば、既存の VelocityResult が上書きされます。
上書きしたくない場合は別の名前にしましょう。

ちなみに、ページ毎に入力エンコーディングを変えるのは不可能のようです。
僕は「PCならUTF-8」「携帯ならWindows-31J」という感じにしたかったのですが
ソース見る限り無理っぽいのでWindows-31Jに統一しました。
早く携帯サイトでUTF-8が完全保障される日が来ないかなぁ…