前のエントリでちょっと触れたS2Wicketの方向性。現在,考えていることが実際に実現可能かどうかを検証している段階である。で,とりあえず次期S2Wicketを使うと,これがこーなります,というコードを掲載しよう。
例えば,
というコードが,
というようになる予定。LabelModelは,helloプロパティのみを持つシンプルなJavaBeansクラスで,HelloServiceはS2Container管理下のビジネスロジックオブジェクト。
将来的には,命名規約を適用して,アノテーションすら書かなくてもいいようにするつもりだ。コンポーネントの登録,モデルとコンポーネントの関連付けはS2Wicketに任せて,開発者はイベントハンドラのみを書くだけで済む,という感じだ。
ページが持つモデルと,ビジネスロジックが扱うモデルの橋渡しをS2Dxoを使ってS2Wicket内でやってあげれば,@WicketComponentアノテーションに呼び出すビジネスロジックを指定するようにするだけで,イベントハンドラのメソッドすら書かなくてもいいようにできるかもしれない。マスタメンテ系の画面であれば,ページが持つモデルとビジネスロジックが扱うモデルは非常に近いものだろうし,呼び出すビジネスロジックも単純なものだろう。フィールド定義のみでマスタメンテ系のページは作れるようになる,かも。
ま,単純なところから手を付けているので,とりあえずは上記のような感じってことで。「○○ってどーすんのよ!?」というような突っ込み大歓迎。
- Posted:
- 03.22.2007
- Category:
- Wicket

Wicketは,WebアプリケーションをSwingなどに代表されるGUIアプリケーションと同じように開発することができるようにと考え出されたフレームワークである。機構自体は非常に複雑だが,その複雑さは表には一切出てこない。
コンポーネントベースという点ではJSFと同じだが,JSFは拡張性やVisualな開発ツールを意識するあまり,APIセットがプログラマに全くもって親しくない。そして,結局JSPをデフォルトとして採用しているため,相変わらず開発メンバーのロールをはっきりとすることができなくなっている。
WicketはPOHPを最初から見据えることができ,さらにSwingレベルのコーディングを由としたため,非常にプログラマに優しいAPIセットとなった。それは,Java言語の特性を存分に活用してプログラミングができることを意味する。UIコンポーネントの組み立ては継承を使ってもいいし,委譲を使っても良い。さらにイベントハンドラのコードは,抽象UIコンポーネントクラスを継承してイベントハンドラメソッドを実装する,というスタイルだ。ここでは,匿名クラスや内部クラスを多用することになるだろう。Wicketは,プログラマが楽しいフレームワークであることは,言うまでもないだろう。
Wicketの特徴は,矢野さんによって非常に分かりやすくまとめられている。
「Wicketはライトウェイトなフレームワークじゃない。でも気持ちがいい。」- 矢野勉のはてな日記
静的型付けオブジェクト指向言語Javaらしいやり方で、この言語を使いこなせるプログラマたちに本来あるべきオブジェクト指向環境を提供している。だからWicketはJavaプログラマにとって快適で、軽量なんです。
しかし,僕にはそんなWicketが,JSFが極端なように,非常に偏った出来に見える。APIの良い悪いを判断する尺度として,「IDEが作りやすいかどうか」という視点があると思っている。Wicketは,言うなればAWTやSwing,いや,SWTのためのVisualなGUI構築ツール(EclipseのVisualEditorが代表的)と同じくらいの難易度だと思う(ほんのちょっとそれより簡単かもしれないが)。
MicrosoftのVisualBasic(僕が知ってるのはVer.6)は,GUIの構築結果についてformファイルに「宣言的な記述」で作成される。つまりBasicコードではない。宣言的な記述は,Visualな開発ツールを作りやすい。文法的に簡単であり,条件分岐などが含まれず,さらにプログラマが手を入れる領域が限られる,という理由から言えることだ。しかし,AWTやSwing,SWTに対するVisualなGUI構築ツールは,その結果をJavaコードという動的な記述で出力しなければならない。これは,開発ツールが作りやすいとする理由のどれをとっても,正反対である。
開発ツールが作りやすいということは,結果が機械的であるということだ。Visual Basicは「機械的」な部分と「動的」な部分を分けることによって,プログラマに絶妙なバランスを提供した。しかし,AWTやSwing,SWTは「動的」な部分が大部分であり,プログラマが頑張らなければならない領域ばかり,という言い方ができる。そして,Wicketも残念ながら「動的」な部分ばかりなのだ。
常にプログラミングが「楽しい」わけがない。動きのある部分を作ることが楽しいと感じても,やはりGUIの構築をコードで書くのは非常にしんどい。少なくとも僕は,WebPageクラスの中でシコシコとUIコンポーネントを組み立てていくコードを書くのは苦手だ。
Wicketは,「動的だからこそ嬉しい部分」と「動的だからこそウザい部分」が共存している。そして,ウザい部分に何とか宣言的な要素を持ち込むことが出来れば,Wicketはより楽しいフレームワークになると思う。
S2Wicketは,「S2Containerとの統合」という意味で,最低限の機能は既に完成されたといって良いだろう。次に目指すべきことは,Wicketを使ってアプリケーションを作るときに「ウザい」と感じる部分への解決策を提供したいと思っている。
まずは,WebPageクラスやFormクラスの中で,各種UIコンポーネント(wicket.Componentのサブクラス)のインスタンス生成&親コンテナへの登録処理を宣言的に書けるようにしてみたい。そこには,アノテーションを適用し,さらに命名規約による暗黙的な動作も持ち込む。UIコンポーネントの役割が入出力される情報のモデルへのマッピングであれば,そのマッピングについても宣言的に書けるようにしてみたい。さらに,FormやAjaxコンポーネントの役割がビジネスロジックの駆動なのであれば,ビジネスロジックの呼び出しさえも宣言的に書けるようにしてみたい。
極限的には,WebPageクラスの中身が,UIコンポーネントとモデルの各種フィールド定義と,各フィールドに付与されたアノテーションのみ,なんて感じになるかな,と。
これには賛否両論あるだろうが,作ってみないと僕自身もその効果はわからない。やってみようと思う(こんな大それたもんじゃないけど・・・)。
- Posted:
- 03.19.2007
- Category:
- Wicket

WicketとSeasar2を統合するS2Wicketだが,先ほどVersion 1.2.0をリリースした。
今回のリリースでは,パッケージ名とクラス名,そしてフィールド名について,正規表現でパターンを与え,それに一致するフィールドをインジェクション対象とするFieldNamePatternFieldFilterフィールドフィルタ実装クラスを新たに提供している。これを利用することによって,@SeasarComponentアノテーションすら書かなくても,規約に従ってインジェクションが施されるようになる。まさに「Convention over Configuration」の考え方を取り入れてみた。ま,S2ContainerのFileSystemComponentAutoRegisterクラスのパクりと言われればそれまでだけど。。。
ソフトウェア的な変更はフィールドフィルタの追加だけだが,今回のリリースではJavadocコメントとサイトコンテンツの追記の他に,「バージョン番号の採番ルール」というサイトページを追加した。seasar.orgのページを見回したのだが,バージョン番号の採番に関するルールが見当たらなく,プロダクトごとにバラバラなルールとなっているように感じた。「説明しなくてもどんなルールかわかるだろ」という気もするが,採番ルールがちゃんと文書化されていた方がバージョン番号を見ただけで明確に修正のレベルがわかるようになるので,一応S2Wicketでの採番ルールを明確にしてみた,というわけである。
seasar.orgのmavenリポジトリ(http://maven.seasar.org/maven2/)にもアップしてあるので,ぜひ利用してみていただきたい。
- Posted:
- 02.21.2007
- Category:
- Wicket

Wicketの特徴として「Javaで何でも書くことにより,Javaプログラマが生き返る」ということがある。これは確かにそのとおり。特にJDK1.1の頃からJavaに携わっている開発者にとって,Wicketでアプリケーションをコーディングした結果は,あの頃のGUIアプリケーションに非常に近い。近年の多くのWebアプリケーションに比べて,自分の時代が戻ってきた!という感覚を開発者は持つだろう(Webアプリしか知らない人には体感できないかも)。
ただしこれは「アプリケーションの記述言語としてJavaを使う割合とそれについて得られるメリット」がポイントなんであって,Wicketを採用する人々が「コーディングが苦にならない」「コーディング大好き!」っていうことには直結しない。
現に,僕はコーディング量は減れば減るほど嬉しい。
Javaの登場以来,オブジェクト指向言語を利用することは当たり前となった。そして,デザインパターンなど多くの設計指針が一般に広まった。Webアプリケーションが登場する前,多くの開発者はGoFのデザインパターンなどの恩恵を受けていたことと思う。そして,MVCなどのパターンも無理なく自然に採用していただろうし,ロジックのコンポーネント化もカプセル化をうまく使って行えていたはずだ。その中で,継承や委譲を使って,コーディング量の削減や戦略の外出しを実現していたことと思う。
Webアプリケーションは,HTTPの特徴と処理の特性に依存して,関数型の開発手法となってしまった。つまり,サーバ上で状態を持つオブジェクトを利用することが難しくなってしまった。MVCについても,そのまま適用することはできず,MVC1やMVC2といったカスタマイズを施すことになってしまった。さらに,世間のEoDが「Javaでのコーディング量の削減=XMLによる設定ファイルの記述」という方向に流れてしまったため,JSPの普及も合わさって,複雑さが増してしまった。
オブジェクト指向言語は,GUIのソフトウェアの構築を見据えて発展してきた歴史がある。GoFのデザインパターンについても同様だ。つまり,カプセル化,継承,委譲,多態性など,オブジェクト指向言語を最大限生かすことができるターゲットは,GUIアプリケーションであると言える。XMLやJSP,スクリプト言語などを持ち込むことなく,オブジェクト指向をうまく使うことに主眼を置くことが,GUIアプリケーション構築には最適解だと思う。
Wicketは,Webアプリケーションについても,オブジェクト指向言語を使うことによるメリットを最大限受けられるように良く考えられている。つまり,GUIアプリケーションを構築するときと同じようなAPIセットを使ってWebアプリケーションをコーディングできるようにしてあるのだ。オブジェクト指向というJavaの原点を生かせるフレームワークこそが,Wicketである。
そのためWicketは,オブジェクト指向への深い理解と高い設計理論が求められる。しかも,GUIアプリケーションを構築するときと同じレベルの「面倒な」コーディングが求められる。GUIアプリケーションは,特にUIに関するコーディングについて,ボタンやテキストフィールドなどをコンポジットパターンで組み合わせていくコーディングがどうしても開発者の負担として付きまとう。従来では,IDEによるビジュアルなデザイナを使ってUIを構築したり,基本となるUIコンポーネントのクラスを拡張して,よりドメイン依存なコンポーネントを作ってそれを組み合わせることで,プログラマの負担を軽減するアプローチを取ってきた。
それと同じ工夫が,広く普及したWebアプリケーションフレームワークに比べて,多く求められるのがWicketだ。
こういう風に書くと,デメリットなように感じるかも知れない。しかし,GoFなどを見ればわかるとおり,GUIアプリケーションの構築を代表的な対象とする,オブジェクト指向言語を利用する際のクラス設計論について,既に我々は数多くのベストプラクティスを持っている。それらを(MVC2のように変にカスタマイズすることなく)素直に適用することができるのが,Wicketなのである。そして,Wicketを採用する人々は,Java登場以来ずっと蓄積されてきたオブジェクト指向的設計論を素直に使えることについて魅力を感じているからこそ,積極的に採用しているのだと思う。
Wicketを使えば,XMLファイルやその他設定ファイルを強制されることなく,Viewのための非常に複雑な機構を強制されることなく,Javaコードのみで業務を満たす最小のコードセットを作れる(もちろん,これの実現のために,Wicket自身は非常に複雑なコードとなっていて,しかもオブジェクト指向を生かすために積極的にHttpSessionを利用するため,サーバリソースを多く使用する)。そして,Javaのみでほぼ完結するため,コードを削減するための努力について,さまざまなアプローチを取ることができる。
リッチな共通部品を作ってもいいし。
ユーティリティクラスを作ってもいいだろうし。
アノテーションを提供して親クラスでそれを解釈するようにしてもいいだろうし。
そこにテンプレートパターンを適用してもいいし。
Panelによるコンポジットパターンで汎用化を進めてもいいだろうし。。。
そこにはJavaの開拓者が生み出してきたどのような知恵も持ち込むことが可能なのだ。
Wicketは,Javaプログラマにとって,自己主張が少なく,わがままでもなく,とても素直なフレームワークと言えるのではないだろうか。XML地獄に陥ることなく,コード量の削減をJava言語の特性を生かして素直に実践することができそうだね,というようにWicketを見て欲しいと僕は思う。
- Posted:
- 02.18.2007
- Category:
- Wicket

WicketからSeasar2を利用するためのS2Wicketのバージョン1.1.0を本日リリースした。
1.0.0では,@SeasarComponentアノテーションをフィールドに付与することによって,インジェクション対象としていた。1.1.0ではそれを進化させ,どのフィールドをインジェクション対象にするかを判断するロジック(フィールドフィルタ)を,アプリケーション開発者が自作して登録することができるようにした。つまり,インジェクション対象のフィールドをどれにするかという規約を定義することが可能となった。
アノテーションや設定ファイルを書かずに規約を重視するという,Convention over Configurationの考え方に基づいた開発が可能となる。本家のwicket-springでは@SpringBeanアノテーションが必要となるため,S2Wicketはより柔軟な拡張ライブラリとなったと言えるだろう。
本バージョンから,seasar.orgが提供するmaven2リポジトリに,S2Wicketも登録している。maven2を利用して開発をしている場合には,より手軽にS2Wicketを利用して頂けるだろう。
- Posted:
- 02.11.2007
- Category:
- Wicket

seasar.orgにて,S2Wicket 1.0.0をリリースした。
これは,wicket-seasarとして先日公開したライブラリを,Seasarブランドに仕立て直して再公開したものである。主な変更点は,プロダクト名の変更,パッケージ名の変更,それに伴うサイトの文面の変更があげられる。ソースコードに関しては,パッケージ名以外は変更していない。
とりあえずこれでwicket-springと表面的には肩を並べたわけだが,S2の冠を受けたからには,更なる機能追加をしていかなければならない。具体的には,以下のようなことを考えている。
(1) キャッシュによる処理性能の向上
内部的な話として,例えば同じ型に関する動的プロキシを複数個生成することは資源の無駄でもあり,動的プロキシ生成にかかる処理コストは非常にもったいない。現状では毎度毎度生成しているので,キャッシュ機構を追加することで全体的な処理性能を向上させる。
(2) 規約によるインジェクション
現状では,@SeasarComponentアノテーションが付与されたフィールドに対して,インジェクションを行っている。しかし,いちいちアノテーションを付与していくのも,手間といえば手間である。そこで,「指定した型のフィールドは全てインジェクション対象」や「指定したパターンにマッチするフィールド名のフィールドは全てインジェクション対象」など,iRuleによる暗黙的インジェクション設定を可能にする。
(3) Wicketコンポーネント登録の自動化
Wicketでは動的生成されるマークアップなものは,全てwicket.Componentクラス(のサブクラス)のインスタンスを生成し,親のコンテナに登録する処理を記述しなければならない。更に,それらのインスタンス毎に,バリデータやコンバータを登録する処理のコーディングも必要となる。そこで,インジェクション対象のフィールドがwicket.Componentクラスのサブクラスで,しかも特定の命名規則に一致する場合は,「インスタンス生成&インジェクション&バリデータやコンバータの登録&親のコンテナへの登録」までをも暗黙的に処理するようにする。
とりあえず以上の3点については,近々機能追加に着手したいと思っている。
Wicketは,これから事例が多くなると思われるフレームワークだ。ぜひS2Wicketを使って,Seasar2 Containerやその他のサブプロジェクトの成果物をWicketと共に利用し,自分なりのベストプラクティスを見つけて欲しい。もちろん,自らも模索を続けていこうと思っている。
疑問,質問,要望,批判,不具合などあれば,どしどしコメントをして欲しい。
- Posted:
- 02.03.2007
- Category:
- Wicket

「早!,もうかよ」と思うだろうが,先日公開したWicketとSeasar2の統合ライブラリは,S2Wicketとして公開し直すことにした。seasar.orgからの承認も得て,近日中にhttp://www.seasar.org/の中にサイトも移行する予定。wicket-seasarは,Seasarブランドの仲間入りをすることになる。移行後は,http://s2wicket.sandbox.seasar.org/ がS2WicketプロジェクトのサイトURLとなる。
それに伴う作業を現在行っているが,著作権表示の箇所やパッケージ名の変更など,いくつか修正をしなければならないことがあるため,もう少しかかってしまう予定。今週末までには何とかファイル一式をアップしたいところだが,引っ越しと入籍があるので,微妙。
ロクにSeasar2 Containerも使ったことがないのにseasar.orgの仲間入りを僕自身するのもどうかと悩んだが,ま,いっかと。S2Wicketを徐々に育てていきたいと思っているので,読者の方々には今後もお付き合い頂きたい。
ちなみに,S2Wicketが立ち上がり次第,wicket-seasarのサイトは閉鎖する予定である。
- Posted:
- 01.31.2007
- Category:
- Wicket

Wicketは,POHPソリューションの代表として今後広く普及するであろうフレームワークである。そして,WicketでDIコンテナの恩恵を受けるために,Spring Frameworkとの統合を行う拡張ライブラリ(wicket-spring)も提供されている。
最近,僕の回りではSpring Frameworkよりも,Seasar2をDIコンテナとして採用する事例がとても多い。さらに,以下のようなエントリを見つけてしまった。
「Webアプリ作成前に考えたこと」 – めそらぼ – mesolabs.com
プレゼン層でJSFに決まっていれば、EJB 3.0かSeasar 2.4の一騎打ちだったのですが、WicketになったのでWicketとの親和性を考えてSpring 2.0に決めました。
選択肢が狭いということは,とても悲しいことだ。オープンソースプロダクトの利点は,数多いソフトウェアを自分なりに組み合わせられる,ということなはずだ。
というわけで,WicketとSeasar2を統合するためのwicket-seasar拡張ライブラリを開発した。以下のURLがプロジェクトのページである。
S2Wicket – Wicket Seasar Integration
http://www.eisbahn.jp/wicket-seasar/
http://s2wicket.sandbox.seasar.org/
もしWicketとSeasar2との親和性を求めている方には,ぜひ利用してみていただきたい。ファーストバージョンということで最低限の機能しか実装していないが,今後機能追加や性能向上を行っていくつもりである。
WIcketは,先日下記のエントリによって,開発者にWicketの良さが広まった。
「Wicketはライトウェイトなフレームワークじゃない。でも気持ちがいい。」 – 矢野勉のはてな日記
Wicketはオブジェクト指向での開発をプログラマに与えるため、非常にJavaっぽい重厚なオブジェクト階層を作り上げ(その重厚さはほとんどSwing級です)つつも、部品の再利用を実現するためコンポーネントをベースとし、オブジェクト指向フレームワークらしく開発者が拡張できる拡張ポイントを大量に用意しています。コードが汚くなればリファクタリングにより改善できます。あらゆるシーンであなたの知ってるデザインパターンを適用できます。
ただし,
とはいえ、Wicketが提供するのはビューとコントローラまでですね。モデルはどうしましょうか。
と言及されているように,Wicketはあくまでフロントエンドのフレームワークである。ビジネスロジックについては,オブジェクト指向原理主義を適用するよりは,情報と振る舞いをクラスレベルで分離して開発する方が都合が良いだろう。更にRDBMSとのやり取りに関しても,Wicketにモデルを供給する観点ではO/Rマッピングツールが非常に重要になってくる。そうなると,何らかのDIコンテナの適用がやはり自然な解決策となる。そして,S2Daoなどの魅力的なプロダクトを使うためにも,wicket-seasarが切り口となると思っている。
個人的にSeasar2の使用経験はほとんどない(というかSpringに慣れている)のだが,Wicketが持つサクサク感とSeasar2が持つサクサク感が合わさることによる絶妙なハーモニーを,あなたのWebアプリケーションにも取り入れて欲しいと願っている。
追記: 2007/02/02
wicket-seasarは,S2Wicketとして下記サイトで再公開としたため,wicket-seasarのサイトは閉鎖した。
- Posted:
- 01.27.2007
- Category:
- Wicket

2007年1月14日時点での,Wicket1.2からWicket2.0への変更点について,以下のURLのページで発表されている。
Migrate-2.0 – Wicket wiki
要約すると,以下のような感じである。英語は苦手なので間違っている箇所があると思うが,構わずに掲載してしまおう。
- JavaSE5以上が必須になる。
- onAttach()の親実装を先に,onDetach()の親実装を最後に呼び出すように推奨される。
- Generics/パラメータ化された型への対応
コンポーネントが扱うモデルの型をGenericsにより規定することができるようになる。これにより,ドメイン依存のモデルをコンポーネントが強制できるようになり,より強固にアプリケーションを開発することができるようになる。
- コンポーネントのコンストラクタの変更
コンポーネントをインスタンス化する際に,親となるコンポーネントをコンストラクタの引数に指定することが強制される(Component#add()は廃止される!)。これにより,コンストラクション時に全てのコンポーネントの階層が確定されるようになり,リッチなコンポーネントにとって便利になるだけでなく,タグの属性をダイレクトに編集ことができるようになり,更にコンポーネントの階層がマークアップファイルに一致しなかった場合に,その検出をより早く行うことができるようになる。
- コンポーネントの入れ替え方式の変更
コンポーネントのコンストラクタの変更により,コンポーネントを入れ替えるための処理が変更となる。Component#replace()は廃止となる。その代わりに,代替メソッドであるreAttach()を使用するか,同一のIDを持つ入れ替えたいコンポーネントを対象の親コンポーネントを指定してインスタンス化することで実現する。
- JavaSE5の列挙型の使用
従来EnumeratedTypeクラスで実現していた列挙型を,JavaSE5のenumを使用するように変更された。これにより,import文による記述の省略化を行うことができるようになる。
- JavaSE5の戻り値型の柔軟化によるfinalの廃止
メソッドのオーバーライド時の戻り値の型に対する柔軟化(元の型のサブクラスであれば許可される)を使用するために,Component#getSession()やComponent#getApplication()などでfinalが削除された。これにより,ドメインに特化した型のインスタンスを返すgetSession()を作成することができるようになる。
- サーブレットの代わりにフィルタが推奨される
WicketServletは使用されなくなり,代わりにWicketFilterサーブレットフィルタの使用が推奨される。これにより,リソースを返すことや,ルートコンテキストにアプリケーションをマッピングすることが簡単になる。
- @SpringBeanの属性変更
name属性は非推奨になり,代わりにidを使用する。
- バリデーションの変更
FormComponentクラスからバリデーションの処理が分離され,新たにwicket.validationパッケージによるAPIと,wicket.validatorパッケージによる実装にバリデーションが委譲されるようになる。
- XMLリソースバンドルの対応
JavaSE5から提供されるXMLフォーマットでのリソースバンドルが使用可能となる。これにより,直接アスキーではないコードでメッセージリソースを記述することができるようになる。
- ISessionStoreクラスの変更
- その他いくつかのAPI変更
しかし,これらのどれよりも大きな進歩がある。
Java EE annotations support in Wicket – TRAVELLING, AND NOT ARRIVING
@Resource,@EJBそして@PersistenceUnitといったJavaEEのアノテーションをWebPageクラス内で使用可能になる。すでにGlassfish上で動作実績があるため,Wicket 2.0では確実に搭載されるだろう。
これは,wicket-javaeeモジュールとして作者(Filippo Diotalevi氏)により提供され,JIRAに登録されている。
WICKET-174 Java EE 5 support for Wicket – Wicket JIRA
さらに,これらの使い方を,Google Codeで見ることができる。
WicketJavaEEIntegration – Google Code
昨年の2006年8月24日付けで,WicketはApache incubatorに登録されており,Wicket 2.0の開発とApacheへの正式参加に対する作業が日々進んでいる。かなり大きな変化の結果,Wicket 2.0は,JavaEE分野でのPOHPソリューションの代名詞となるだろう。そして,Wicketを採用した事例が日本国内でも増えていって欲しいと願っている。
WicketのSVNから最新コードを取得し,さらに上記のWICKET-174からモジュールを得て組み合わせれば,JavaEEアノテーションを試すことが可能である。
Wicketの今後は,目を離すことができない。
- Posted:
- 01.18.2007
- Category:
- Wicket

WicketはPOHPのソリューションとして非常に素晴らしいが,やはりUIに対するライブラリであり,ビジネスロジックに関してはDIコンテナを採用してAOPなどの恩恵を受けることが今日の開発スタイルにマッチすると考えられる。
Wicketでは,DIコンテナであるSpringFrameworkと連携するための2つの方法を提供している。
- ApplicationオブジェクトにDIコンテナ管理下のオブジェクトをセッターインジェクションして,各WebPageオブジェクトからgetして利用する。
- 各WebPageオブジェクトにDIコンテナ管理下のオブジェクトをフィールドインジェクションして利用する。
1つ目の方法は,ApplicationクラスにDIコンテナ管理下のオブジェクトへの参照が集中してしまうため,一般的なDIの利用手法とは違った感じになる。使いたいときにそこ(=インスタンスフィールド)にある,という形態ではなく,いちいちApplicationオブジェクトから取得処理を行わなければならないため,感覚的にはDIコンテナを自分でルックアップするのと変わらない。
2つ目の方法は,インジェクション対象のインスタンスフィールドに@SpringBeanアノテーションを記述することで連携を実現する手法となる。実際には,オブジェクトがインジェクションされてしまうわけではなく,実行時にはプロキシオブジェクトが間に入り,利用の度にDIコンテナから対象オブジェクトをルックアップする動作となる。そのために,WebPageインスタンスのライフサイクルに関係なくSpringFrameworkとの連携が可能となっている。
ここでは,2つ目の方法を採用し,そのために必要な事柄を説明することにしよう。
@SpringBeanアノテーションを使うためには,Wicketのコアライブラリでは足りず,SpringFramework連携用の以下のライブラリが必要となる。
- wicket-spring
- wicket-spring-annot
- spring
maven2を利用している場合は,wicket-spring-annotのみを依存ライブラリとして指定しておけば,自動的にwicket-springやSpringFramework自体のライブラリも依存ライブラリとして含まれるようになる。具体的には,以下のように記述すれば良い。
最新バージョンは1.2.4なのだが,pom.xmlファイルに記述ミスがあるらしく,maven2の実行時にエラーが生じてしまうため,1.2.3を指定するのが現状では良いだろう。
次に,Applicationクラスのサブクラスにて,@SpringBeanアノテーションを処理してくれるSpringComponentInjectorオブジェクトを登録する処理を記述する。登録には,Application#addComponentInstanciationListener()メソッドを使用する。登録する場所は,init()メソッドをオーバーライドして,その中で行うのが良いだろう。
Wicket側に対する準備はこれで完了。次にSpringFramework側の準備に取り掛かる。先ほど登録したSpringComponentInjectorクラス内では,サーブレットコンテキストからSpringFrameworkが提供するWebApplicationContextオブジェクトを取得する処理が行われる。つまり,SpringFrameworkが提供するContextLoaderListenerクラスを使用して,WebApplicationContextオブジェクトをサーブレットコンテキストに登録しておけば良い。ContextLoaderListenerオブジェクトは,web.xmlファイルに記述しておくことにより実行される。
org.springframework.web.context.ContextLoaderListener
ContextLoaderListenerクラスでは,/WEB-INF/applicationContext.xmlファイルが初期値として採用される。applicationContext.xmlファイルは,Wicketに依存した記述というものはない。インジェクションしたいオブジェクトをbean要素を使って普通に記述すれば良い。
以上で準備完了である。上記のコードで定義したDIコンテナ管理下のhogeオブジェクトを,あるWebPageクラス内で使用する場合のコード例を,以下に示す。
@SpringBeanアノテーションは,name属性により,ルックアップするDIコンテナのbean名を指定することができる。hogeインスタンスフィールドに@SpringBeanアノテーションを付与することにより,btnHogePressed()メソッド内でhoge.foo()メソッド呼び出しを行った際には,DIコンテナからhogeオブジェクトが取得され,foo()メソッドの呼び出しがデレゲートされる。
あとは,applicationContext.xml内でAOPをかけるなりインジェクションをネストするなり,DIの恩恵を思う存分受ければ良い。単体テスト用にモックオブジェクトを利用することを考える場合は,hogeインスタンスフィールドのスコープをprotectedやpackage privateにすることを考えれば良いだろう。もちろんリフレクションを使用するのもありだと思う。
WicketにおけるSpring Frameworkとの連携は,コンポーネントのライフサイクルが開発者次第となってしまうことと,コンポーネントがHttpSessionに格納されてしまうことにより,実現方法にちょっとした議論が起きた。しかし,JDK1.5の登場により,スマートな決着がついたといえるだろう。
ちなみに,もちろん今回紹介した方式はJDK1.5以上が必要である。Java2SE1.4でWicketを使用する場合は,Applicationクラスに対してインジェクションする方式のみが選択肢となる。
- Posted:
- 01.05.2007
- Category:
- Wicket
