My advice to you would be to not fall into the common trap that I see, which is to think that you need to choose between mocking and using the built-in EJB container.
You can use both options, you must use both options, and where it is difficult for you to use both, you should demand improved support and additional features from your EJB container.
Of course, you will find people in OpenEJB truly supportive and more than happy to add features to support the best of both worlds. Almost all really good features were created around user requests that try to do very specific things and find it hard.
Standard EJBContainer API
package org.superbiz.stateless.basic; import junit.framework.TestCase; import javax.ejb.embeddable.EJBContainer; public class CalculatorTest extends TestCase { private CalculatorBean calculator; 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; }
Full source here
This scans the classpath and loads all the beans.
No scan, simpler calculation approach
A slightly different approach in which you define everything in code. Obviously, taunting is easier, as you can provide mock beans implementations where necessary.
@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
Final result
It is tempting to focus on the differences between different types of testing, etc., but of course there is something that can be said about the pragmatic middle. I personally do not see anything wrong with the ability to mix the styles of "unity" and "integration" as badly as possible.
Of course, this is a wonderful goal. Ideas and feature requests to get closer to us are very welcome.