[Seasar-user:17473] [S2 Container, Tiger 2.4.36] S2JUnit4 + Cool Deployモードでテストが失敗してしまう問題について

Toshiaki Takashima [E-MAIL ADDRESS DELETED]
2009年 5月 19日 (火) 09:24:50 JST


高島と申します。


 S2JUnit4を使ったテストの実施でエラーが発生する問題
についてご相談させてください。

問題発生状況の詳細については後述しますが、本問題について、

1.こちらのモジュール構成がSMART Deploy機能を利用する
上で好ましくない構成となっている

2.S2JUnit4の使い方(機能制限?)を良く理解していない

のいづれによるものなのか判断できませんでしたので、アドバイス
を頂けないでしょうか?

<<問題発生状況の詳細>>

■ 問題が発生するプロジェクトの構成
<設定ファイルの構成>
・"hoge.piyo"パッケージを、SMART Deploy対象としてconvention.diconに追加
・creator.dicon / customizer.diconについてはカスタマイズなし
・app.diconには、"s2jdbc-internal.dicon"のinclude指定のみ追加
  ⇒後述のモジュール内で、EntityMetaFactoryコンポーネントを利用したいため。
・s2junit4.diconの定義内容は以下の通り(抜粋)
↓
==========
<components namespace="s2junit4">
  <component name="context" class="org.seasar.framework.unit.impl.SimpleInternalTestContext"/>
  <component class="org.seasar.framework.unit.impl.ConfigFileIncluderImpl">
    <!-- app.diconの読込みを追加 -->
    <initMethod name="addConfigFile">
      <arg>"app.dicon"</arg>
    </initMethod>
    <initMethod name="addConfigFile">
      <arg>context.testClassShortName + ".dicon"</arg>
    </initMethod>
  </component>
</components>
==========

<モジュールの構成>
・hoge.piyo.entity.EntityUtilクラス(抜粋)。

// EntityMetaFactoryを使ってエンティティのメタ情報を提供するクラス
public class EntityUtil {
    private static EntityMetaFactory entityMetaFactory;
    static {
        try {
            SingletonS2ContainerFactory.init();
            entityMetaFactory = SingletonS2Container
                .getComponent("entityMetaFactory");
        } catch (Exception e) {
            e.printStackTrace();
            throw new IllegalStateException(e);
        }
    }

    public static EntityMetaFactory getInstance() {
        return entityMetaFactory;
    }

    public static void main(String[] args) {
        // S2JUnit4を介しない場合は、モードに関係なく
        // 正常にコンポーネント取得が可能
        System.out.println(entityMetaFactory);
    }
}

■ 問題の再現
 上記の構成において、以下のような簡単なS2 Junit4のテストクラス
を作成します(抜粋)。
import static org.junit.Assert.*;

@RunWith(Seasar2.class)
public class DummyTest {

    public void test1() {
        // Warm / Hot Deploy モードの時はテストOK
        assertNotNull(EntityUtil.getInstance());
    }
}

 このとき、env_ut.txtにて、Cool Deloyモードでテストを実施する
ように設定してテスト実行すると、エラーが発生してしまいます。
上述のEntityUtilのstaticブロック内から以下の例外がスローされてしまいます。
↓
==========
org.seasar.framework.container.ComponentNotFoundRuntimeException: [ESSR0046]コンポーネント(entityMetaFactory)が見つかりません
    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.SingletonS2Container.getComponent(SingletonS2Container.java:62)
    at hoge.piyo.entity.EntityUtil.<clinit>(EntityUtil.java:13)
    at java.lang.Class.forName0(Native Method)
    at java.lang.Class.forName(Class.java:242)
    at org.seasar.framework.util.ClassUtil.forName(ClassUtil.java:98)
    at org.seasar.framework.container.cooldeploy.CoolComponentAutoRegister.processClass(CoolComponentAutoRegister.java:149)
    at org.seasar.framework.util.ClassTraversal.traverseFileSystem(ClassTraversal.java:213)
    at org.seasar.framework.util.ClassTraversal.traverseFileSystem(ClassTraversal.java:207)
    at org.seasar.framework.util.ClassTraversal.forEach(ClassTraversal.java:79)
    at org.seasar.framework.util.ResourcesUtil$FileSystemResources.forEach(ResourcesUtil.java:374)
    at org.seasar.framework.container.cooldeploy.CoolComponentAutoRegister.registerAll(CoolComponentAutoRegister.java:128)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:585)
    at org.seasar.framework.util.MethodUtil.invoke(MethodUtil.java:96)
    at org.seasar.framework.container.assembler.AbstractMethodAssembler.invoke(AbstractMethodAssembler.java:94)
    at org.seasar.framework.container.assembler.DefaultInitMethodAssembler.assemble(DefaultInitMethodAssembler.java:49)
    at org.seasar.framework.container.deployer.SingletonComponentDeployer.assemble(SingletonComponentDeployer.java:69)
    at org.seasar.framework.container.deployer.SingletonComponentDeployer.deploy(SingletonComponentDeployer.java:48)
    at org.seasar.framework.container.deployer.SingletonComponentDeployer.init(SingletonComponentDeployer.java:76)
    at org.seasar.framework.container.impl.ComponentDefImpl.init(ComponentDefImpl.java:236)
    at org.seasar.framework.container.impl.S2ContainerImpl.init(S2ContainerImpl.java:563)
    at org.seasar.framework.container.impl.S2ContainerImpl.init(S2ContainerImpl.java:560)
    at org.seasar.framework.unit.impl.SimpleInternalTestContext.initContainer(SimpleInternalTestContext.java:190)
    at org.seasar.framework.unit.S2TestMethodRunner.initContainer(S2TestMethodRunner.java:461)
    at org.seasar.framework.unit.S2TestMethodRunner.runMethod(S2TestMethodRunner.java:246)
    at org.seasar.framework.unit.S2TestMethodRunner.run(S2TestMethodRunner.java:172)
    at org.seasar.framework.unit.S2TestClassMethodsRunner.invokeTestMethod(S2TestClassMethodsRunner.java:227)
    at org.seasar.framework.unit.S2TestClassMethodsRunner.run(S2TestClassMethodsRunner.java:89)
    at org.seasar.framework.unit.S2TestClassRunner.run(S2TestClassRunner.java:67)
    at org.seasar.framework.unit.Seasar2.run(Seasar2.java:168)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:45)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:460)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:673)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:386)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:196)
==========

なお、ソース内コメントにあるように、S2JUnit4を介さないでJavaアプリケーションとして
直接実行した場合や、S2JUnit4によるテストであってもWarm / Hot Deployモードでは問題
が発生しません。



以上ご教授よろしくお願いします。





Seasar-user メーリングリストの案内