7

EJB 3.1 の単体テストに関する小さな調査を行っています。最後に、私の目標は、EJB 3.1 の単体テスト用の使いやすいソリューションを作成することです。

  1. 私は大規模な EJB の実装に関する知識があまりないため、最初に経験豊富な手 (あなた) を獲得して、EJB の単体テストで何が難しいかについてのアイデアをプールしたいと思います。
  2. すでに行った最初の調査で、組み込みコンテナーを使用するのではなく、単体テストにモッキング フレームワークを使用する利点を理解できます。どちらも優れていますが、単体テストに関しては、モッキング フレームワークが少し優れています。もちろん、組み込みコンテナーは非常に優れており、独自の利点がありますが、単体テストの別のフェーズになる可能性があります。このようなフレームワークを使用する場合、少なくとも一部のシナリオでは、改善可能な欠点があるはずだと私はまだ信じています。

ユニット テスト EJB の完全なソリューションを作成して、このフォーラムで共有できることを願っています。

ご協力ありがとうございました。

4

3 に答える 3

14

皆さんへの私のアドバイスは、私が目にするよくある落とし穴にはまらないようにすることです。それは、モックを作成するか、組み込み EJB コンテナーを使用するかを選択する必要があると考えることです。

両方を使用できます。両方を使用する必要があります。両方を使用することが困難な場合は、EJB コンテナーのサポートと機能を強化する必要があります。

確かに、OpenEJB の人々は本当に協力的で、両方の長所を活かすための機能を喜んで追加してくれます。本当に優れた機能のほとんどは、非常に具体的なことをしようとして、それが難しいと感じているユーザーの要求に基づいて作成されています。

標準 EJBContainer API

package org.superbiz.stateless.basic;

import junit.framework.TestCase;

import javax.ejb.embeddable.EJBContainer;

public class CalculatorTest extends TestCase {

    private CalculatorBean calculator;

    /**
     * Bootstrap the Embedded EJB Container
     *
     * @throws Exception
     */
    protected void setUp() throws Exception {

        EJBContainer ejbContainer = EJBContainer.createEJBContainer();

        Object object = ejbContainer.getContext().lookup("java:global/simple-stateless/CalculatorBean");

        assertTrue(object instanceof CalculatorBean);

        calculator = (CalculatorBean) object;
    }

完全なソースはこちら

これにより、クラスパスがスキャンされ、すべての Bean がロードされます。

スキャン不要、より簡単なモッキング アプローチ

すべてをコードで定義する、わずかに異なるアプローチ。必要に応じてBeanのモック実装を自由に提供できるため、明らかにモックの方が簡単です。

@RunWith(ApplicationComposer.class)
public class MoviesTest extends TestCase {

    @EJB
    private Movies movies;

    @Resource
    private UserTransaction userTransaction;

    @PersistenceContext
    private EntityManager entityManager;

    @Module
    public PersistenceUnit persistence() {
        PersistenceUnit unit = new PersistenceUnit("movie-unit");
        unit.setJtaDataSource("movieDatabase");
        unit.setNonJtaDataSource("movieDatabaseUnmanaged");
        unit.getClazz().add(Movie.class.getName());
        unit.setProperty("openjpa.jdbc.SynchronizeMappings", "buildSchema(ForeignKeys=true)");
        return unit;
    }

    @Module
    public EjbJar beans() {
        EjbJar ejbJar = new EjbJar("movie-beans");
        ejbJar.addEnterpriseBean(new StatefulBean(MoviesImpl.class));
        return ejbJar;
    }

    @Configuration
    public Properties config() throws Exception {
        Properties p = new Properties();
        p.put("movieDatabase", "new://Resource?type=DataSource");
        p.put("movieDatabase.JdbcDriver", "org.hsqldb.jdbcDriver");
        p.put("movieDatabase.JdbcUrl", "jdbc:hsqldb:mem:moviedb");
        return p;
    }

    @Test
    public void test() throws Exception {

        userTransaction.begin();

        try {
            entityManager.persist(new Movie("Quentin Tarantino", "Reservoir Dogs", 1992));
            entityManager.persist(new Movie("Joel Coen", "Fargo", 1996));
            entityManager.persist(new Movie("Joel Coen", "The Big Lebowski", 1998));

            List<Movie> list = movies.getMovies();
            assertEquals("List.size()", 3, list.size());

            for (Movie movie : list) {
                movies.deleteMovie(movie);
            }

            assertEquals("Movies.getMovies()", 0, movies.getMovies().size());

        } finally {
            userTransaction.commit();
        }
    }
}

完全なソースはこちら

最終結果

さまざまな種類のテストの違いなどに焦点を合わせたくなるかもしれませんが、実用的な中間については確かに何か言いたいことがあります。個人的には、「ユニット」スタイルと「統合」スタイルをできるだけ流暢に組み合わせることができることに問題はないと思います。

確かに、それは立派な目標です。私たちを近づけるためのアイデアや機能のリクエストは大歓迎です。

于 2011-10-16T03:43:56.953 に答える
5

実際には、考慮したい 2 つの異なるタイプのテストがあります (排他的ではありません)。

  • 単体テスト: EJB は結局のところ POJO であるため、好みの単体テスト フレームワーク (JUnit など) と、Mockito や EasyMock などのモック フレームワークを使用できます。
  • 統合テスト: ここでは、EJB を (分離ではなく) コンテナー内にあるかのようにテストするため、何らかの方法でそのコンテナーをエミュレートする必要があります。単体テスト フレームワークを使用してテスト (JUnit など) をコーディングすることもできますが、これらの EJB がコンテナー内でどのように動作し、他のコラボレーター (他の EJB など) と対話するかをテストしています。これにはArquillianをお勧めします
于 2011-10-18T12:46:55.483 に答える
3

Needleは、JavaEEコンポーネントの単体テストに使用できます。

Needleは、コンテナの外部でJavaEEコンポーネントを分離してテストするための軽量フレームワークです。依存関係を分析し、モックオブジェクトを自動的に挿入することで、テストセットアップコードを削減します。

http://needle.spree.de

于 2012-10-28T20:27:40.170 に答える