SimpleFormControllerで指定可能なプロパティ

SimpleFormControllerで指定可能なプロパティを調べてみる。

まずは、階層関係

java.lang.Object
  + org.springframework.context.support.ApplicationObjectSupport
      + org.springframework.web.context.support.WebApplicationObjectSupport
          + org.springframework.web.servlet.support.WebContentGenerator
              + org.springframework.web.servlet.mvc.AbstractController
                  + org.springframework.web.servlet.mvc.BaseCommandController
                      + org.springframework.web.servlet.mvc.AbstractFormController
                          + org.springframework.web.servlet.mvc.SimpleFormController

org.springframework.web.servlet.mvc.AbstractControllerから、コントローラで設定可能なプロパティがでてくる。
このクラスで指定可能なプロパティは、

  • supportedMethods
  • requireSession
  • cacheSeconds
  • synchronizeOnSession

サブクラスのorg.springframework.web.servlet.mvc.BaseCommandControllerでは、

  • commandName
  • commandClass
  • validators
  • validator
  • validateOnBinding

さらに下がってorg.springframework.web.servlet.mvc.AbstractFormControllerでは、

  • bindOnNewForm
  • sessionForm

そして最後のSimpleFormControllerでは、

  • formView
  • successView

これらをまとめるとこんな感じでしょうか。

プロパティ名 デフォルト値 詳細 指定可能なクラス
supportedMethods GET,POST サポートするHTTPメソッドをカンマ区切り(CSV形式)で指定 AbstractController
requireSession false リクエスト処理にセッションが必要かどうか AbstractController
cacheSeconds -1 キャッシュの有効期間を秒単位で指定(0指定時:no-cache -1指定時:キャッシュヘッダなし AbstractController
synchronizeOnSession false 同一セッションでのリクエストをシリアライズするか AbstractController
commandName command コマンド名 BaseCommandController
commandClass null コマンドオブジェクトとして利用するクラス名 BaseCommandController
validators null バリデータを配列で指定 BaseCommandController
validator null バリデータ名 BaseCommandController
validateOnBinding true リクエストパラメータをコマンドオブジェクトにバインドした後にバリデータを実行するか BaseCommandController
bindOnNewForm false 新規フォーム作成時(表示時)もリクエストパラメータを保存したままにするか AbstractFormController
sessionForm false フォームの値をセッション内で保存するか AbstractFormController
formView null フォーム入力画面 or validationチェック失敗時に表示する画面 SimpleFormController
successView null formViewで指定した画面でのsubmitが成功した場合に表示する画面 SimpleFormController

いまいちわかっていないプロパティもあるけど、その辺はいじり倒しながら確認するか。

SpringMVCとかServlet周りのメモ

Servletのライフサイクル

  1. サーブレットロード時(初回リクエスト時)にコンテナからinit()が呼び出される。
  2. リクエスト単位でservice()がコンテナから呼び出され、service()はリクエストの種別(GETとかPOST)に応じてdoXXX()を呼び出す。
  3. サーブレットのアンロード時にdestory()が呼び出される。

一応動作確認

package com.sample;

import java.io.IOException;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class ServletTest extends HttpServlet {
    public ServletTest() {
    }

	public void init(ServletConfig config) throws ServletException {
		System.out.println("init()が呼び出されました");
	}

	public void destroy() {
		System.out.println("destory()が呼び出されました");
	}

	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("service()が呼び出されました");
		super.service(request, response);
	}
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		System.out.println("doGet()が呼び出されました");
	}

}

SpringMVCでの処理順序
まずはorg.springframework.web.servlet.DispatcherServletからみてみる。
このクラスにはinit()/service()の両方が実装されてないので、親クラスをたどってみる。
階層関係はこんな感じ

java.lang.Object
  +- javax.servlet.GenericServlet
       +- javax.servlet.http.HttpServlet
             +- org.springframework.web.servlet.HttpServletBean
                     +- org.springframework.web.servlet.FrameworkServlet
                             +- org.springframework.web.servlet.DispatcherServlet

org.springframework.web.servlet.HttpServletBeanでfinal宣言された init() を見つけたので処理内容の確認。やってることは

  • Beanプロパティの設定
  • initServletBean()の呼び出し

の二つ。

initServletBean()の実装はこのクラスにはなく、サブクラスのFrameworkServletで行っている。こいつの処理内容は・・・

try {
    this.webApplicationContext = initWebApplicationContext();
    initFrameworkServlet();
}

initFrameworkServlet()については、サブクラスのほうにも処理の実体は存在しないので、カスタムのDispatcherを作った時に使うのかな?initWebApplicationContext()では

  • WebApplicationContextの生成
  • onRefresh()の呼び出し

などをやっている様子。

onRefresh()はDispatcherServletで処理が実装されていて、initStrategies()を呼び出す。
initStrategies()の処理は、

initMultipartResolver(context);
initLocaleResolver(context);
initThemeResolver(context);
initHandlerMappings(context);
initHandlerAdapters(context);
initHandlerExceptionResolvers(context);
initRequestToViewNameTranslator(context);
initViewResolvers(context);

となっていて、ようやくResolverとかの見慣れたものが出てきました。
あとは、ApplicationContext周りの処理を勉強すればこの辺の流れはすっきり確認できそう。


続いて、service()が同処理されるか。
これは、FrameworkServlet内でdoXXXメソッドがprocessRequest()を呼び出すように処理されていて、このメソッド内で

  • doService()の呼び出し
  • webApplicationContext.publishEventの実行

を行っている。

doService()はDispatcherServlet内で実装されていて、さらにdoDispatch()を呼び出す仕組みとなっている。

処理の詳細はいまいちわかっていないが、全体像はぼんやりつかめた感じ

一人合宿その2

SpringMVCと格闘中
アプリケーション構築の手順

1. dispatcherServletのマッピングをweb.xmlに記述


servlet_name

org.springframework.web.servlet.DispatcherServlet

1*1


servlet_name
url_pattern

2. bean定義ファイルの作成

  • 手順1.で指定した-servlet.xmlファイルを作成する。
  • 記述内容は
    • ViewResolverの設定:JSPファイルの指定
    • HandlerMappingの設定:コントローラの指定(URLマッピング)
    • Controllerの設定:リクエスト・コントローラの指定
    • beanクラス定義
    • メッセージリソースの指定

*1:要調査

一人合宿

強制的なリハビリのため一人合宿開催中
過去の書籍とかを漁りに漁ってひぃひぃ言ってます。

とりあえず

  • Spring
    • AOP
    • DIコンテナ
    • SpringMVC

あたりから手をつけてます。

[追加]

  • log4Jの設定方法
  • Eclipse全般の使い方
  • Tomcat5.5(6)

頭がパンクする・・・ちょっと休憩。
夜はSpringMVCとHibernateをやろう

SpringAOPについては、ひとまずおしまい。全体の勉強が終わったらまた戻ってこよう。

超久々のJSP/Servlet。設定ファイルの書き方とかいい感じで忘れてます。