我給你的建議是不要陷入我看到的共同陷阱,那就是認爲你需要在模擬和使用嵌入式EJB容器之間進行選擇。
您可以同時使用兩者,您應該同時使用兩者,並且在難以使用的地方,您應該要求EJB容器提供更好的支持和更多功能。
當然,你會發現在OpenEJB的人真的很支持,並且很樂意添加功能來支持獲得兩全其美的好處。幾乎所有真正優秀的功能都是圍繞用戶嘗試做出非常具體的事情並發現困難的請求而創建的。
標準API的EJBContainer
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;
}
完整的源here
這會掃描類路徑和加載所有豆類。
沒有掃描,更容易嘲諷方法
略有不同的方法,你在代碼中定義的一切。顯然,嘲笑更容易,因爲您可以隨時提供需要的模擬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();
}
}
}
Full source here
最終的結果
人們很容易把重點放在不同類型的測試,等之間的差異,但肯定有什麼東西了務實的中間可說的。我個人並不認爲能夠儘可能流利地混合「單元」和「集成」的風格。
當然,這是一個令人欽佩的目標。理念和功能要求讓我們更接近非常受歡迎。
大衛您好,非常感謝您的回覆。我也在考慮將兩種方法混合起來,這將有助於收穫這兩種方法的好處。 – Bala