コンピュータクワガタ

かっぱのかっぱによるコンピュータ関連のサイトです

Formのパス分割

大規模なアプリケーションでは、パスを分割することもできます。例えば、/aaa/bbb/のパスに対応するアクションクラスは、ルートパッケージ.action.aaa.BbbActionになります。

http://sastruts.seasar.org/featureReference.html#Action

にあるように、Actionはパスを分割できます。Actionと同じ階層にFormもあったほうがいいのでFormもパス分割してみました。
まずはAction。

package sample.action.foo;

import javax.annotation.Resource;

import org.seasar.struts.annotation.ActionForm;
import org.seasar.struts.annotation.Execute;

import sample.form.foo.TestForm;

public class TestAction {
    @ActionForm
    @Resource
    protected TestForm testForm;
    
    @Execute(validator = false)
    public String index() {
        testForm.hoge="aaa";
        return "test.jsp";
    }
}

Formは、以下。

package sample.form.foo;

public class TestForm {
    public String hoge;
}

これで動かすと、問題なく動きます。
この状態から、Formの変数名をformにしたいので、ActionクラスのForm指定部分の@Resourceのnameを指定します。

package sample.action.foo;

import javax.annotation.Resource;

import org.seasar.struts.annotation.ActionForm;
import org.seasar.struts.annotation.Execute;

import sample.form.foo.TestForm;

public class TestAction {
    @ActionForm
    @Resource(name = "testForm")
    protected TestForm form;

    @Execute(validator = false)
    public String index() {
        form.hoge = "aaa";
        return "test.jsp";
    }
}

そうすると、以下のエラーになります。

2008-08-18 12:19:52,619 [http-8080-Processor24] ERROR org.apache.struts.action.RequestProcessor - パス /foo/test に対するアクションのインスタンスがありません
org.seasar.framework.beans.IllegalPropertyRuntimeException: [ESSR0059]クラス(sample.action.foo.TestAction$$EnhancedByS2AOP$$3cb075)のプロパティ(form)の設定に失敗しました。理由はorg.seasar.framework.exception.OgnlRuntimeException: [ESSR0073]OGNLで例外が発生しました。理由は[ESSR0046]コンポーネント(testForm)が見つかりません
	at org.seasar.framework.container.assembler.AbstractBindingTypeDef.getValue(AbstractBindingTypeDef.java:273)
	at org.seasar.framework.container.assembler.AbstractBindingTypeDef.bindManual(AbstractBindingTypeDef.java:109)
	at org.seasar.framework.container.assembler.AbstractBindingTypeDef.bind(AbstractBindingTypeDef.java:87)
	at org.seasar.framework.container.assembler.AccessTypeFieldDef.bind(AccessTypeFieldDef.java:50)
	at org.seasar.framework.container.assembler.AccessTypeFieldDef.bind(AccessTypeFieldDef.java:42)
	at org.seasar.framework.container.assembler.AutoPropertyAssembler.assemble(AutoPropertyAssembler.java:56)
	at org.seasar.framework.container.deployer.RequestComponentDeployer.deploy(RequestComponentDeployer.java:67)
	at org.seasar.framework.container.impl.ComponentDefImpl.getComponent(ComponentDefImpl.java:111)
	at org.seasar.struts.config.S2ActionMapping.getAction(S2ActionMapping.java:320)
	at org.seasar.struts.action.ActionWrapper.<init>(ActionWrapper.java:74)
	at org.seasar.struts.action.S2RequestProcessor.processActionCreate(S2RequestProcessor.java:237)
	at org.seasar.struts.action.S2RequestProcessor.process(S2RequestProcessor.java:121)
	at org.apache.struts.action.ActionServlet.process(ActionServlet.java:1196)
	at org.apache.struts.action.ActionServlet.doGet(ActionServlet.java:414)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:269)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.seasar.framework.container.hotdeploy.HotdeployFilter.doFilter(HotdeployFilter.java:75)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.seasar.framework.container.filter.S2ContainerFilter.doFilter(S2ContainerFilter.java:77)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.apache.catalina.core.ApplicationDispatcher.invoke(ApplicationDispatcher.java:679)
	at org.apache.catalina.core.ApplicationDispatcher.processRequest(ApplicationDispatcher.java:461)
	at org.apache.catalina.core.ApplicationDispatcher.doForward(ApplicationDispatcher.java:399)
	at org.apache.catalina.core.ApplicationDispatcher.forward(ApplicationDispatcher.java:301)
	at org.seasar.struts.filter.RoutingFilter.forward(RoutingFilter.java:196)
	at org.seasar.struts.filter.RoutingFilter.doFilter(RoutingFilter.java:73)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.seasar.framework.container.hotdeploy.HotdeployFilter.doFilter(HotdeployFilter.java:63)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.seasar.framework.container.filter.S2ContainerFilter.doFilter(S2ContainerFilter.java:77)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.seasar.extension.filter.EncodingFilter.doFilter(EncodingFilter.java:69)
	at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:215)
	at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:188)
	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:213)
	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:174)
	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
	at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:117)
	at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:108)
	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:174)
	at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:874)
	at org.apache.coyote.http11.Http11BaseProtocol$Http11ConnectionHandler.processConnection(Http11BaseProtocol.java:665)
	at org.apache.tomcat.util.net.PoolTcpEndpoint.processSocket(PoolTcpEndpoint.java:528)
	at org.apache.tomcat.util.net.LeaderFollowerWorkerThread.runIt(LeaderFollowerWorkerThread.java:81)
	at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run(ThreadPool.java:689)
	at java.lang.Thread.run(Thread.java:595)
Caused by: org.seasar.framework.exception.OgnlRuntimeException: [ESSR0073]OGNLで例外が発生しました。理由は[ESSR0046]コンポーネント(testForm)が見つかりません
	at org.seasar.framework.util.OgnlUtil.getValue(OgnlUtil.java:106)
	at org.seasar.framework.container.ognl.OgnlExpression.evaluate(OgnlExpression.java:64)
	at org.seasar.framework.container.impl.ArgDefImpl.getValue(ArgDefImpl.java:60)
	at org.seasar.framework.container.assembler.AbstractBindingTypeDef.getValue(AbstractBindingTypeDef.java:271)
	... 52 more
Caused by: org.seasar.framework.container.ComponentNotFoundRuntimeException: [ESSR0046]コンポーネント(testForm)が見つかりません
	at org.seasar.framework.container.impl.S2ContainerBehavior$DefaultProvider.acquireFromGetComponentDef(S2ContainerBehavior.java:165)
	at org.seasar.framework.container.impl.S2ContainerBehavior$DefaultProvider.acquireFromGetComponent(S2ContainerBehavior.java:158)
	at org.seasar.framework.container.impl.S2ContainerBehavior.acquireFromGetComponent(S2ContainerBehavior.java:62)
	at org.seasar.framework.container.impl.S2ContainerImpl.getComponent(S2ContainerImpl.java:124)
	at org.seasar.framework.container.ognl.S2ContainerPropertyAccessor.getProperty(S2ContainerPropertyAccessor.java:36)
	at ognl.OgnlRuntime.getProperty(OgnlRuntime.java:1758)
	at ognl.ASTProperty.getValueBody(ASTProperty.java:92)
	at ognl.SimpleNode.evaluateGetValueBody(SimpleNode.java:171)
	at ognl.SimpleNode.getValue(SimpleNode.java:211)
	at ognl.Ognl.getValue(Ognl.java:333)
	at ognl.Ognl.getValue(Ognl.java:310)
	at org.seasar.framework.util.OgnlUtil.getValue(OgnlUtil.java:98)
	... 55 more

上記は、HotDeployですが、CoolDeployでも同じです。
じゃあ、それならと、パスを分割せずにルートパッケージ以下の、actionとformパッケージに上記のソースを移動(以下)すると動きます。

package sample.action;

import javax.annotation.Resource;

import org.seasar.struts.annotation.ActionForm;
import org.seasar.struts.annotation.Execute;

import sample.form.TestForm;

public class TestAction {
    @ActionForm
    @Resource(name = "testForm")
    protected TestForm form;

    @Execute(validator = false)
    public String index() {
        form.hoge = "aaa";
        return "test.jsp";
    }
}

これは仕様?