On Aug 17, 2009, at 7:49 AM, Laird Nelson wrote:
Hi, David; thanks for the tips.
Two things of note:
1. Something I just discovered: SureFire forking doesn't actually
fork
per test, even if you tell it to. That is, in JUnit 4, a test is
any method
annotated with @Test. It appears to be the case that SureFire
will fork
once *per test class*, but that isn't the same thing. If you only
have
one @Test method per class, then obviously this doesn't matter,
but in my
case I have several. So SureFire forking on its own can't solve
my problem,
unless I move to a test architecture where I have one test method
per
class. For various reasons I can't do that.
That would be a real pain as well.
2. The undocumented property called out in the article you
referenced
works great--but I don't think it causes the connection pool to
close. That
is, the context does in fact close, and the container system is
destroyed,
and classpath.ear is undeployed. But when the context is
reinitialized, the
DDL generation doesn't run again (and the H2 database is not
zapped). I'm
using a way of opening an H2 database so that when the last
connection to
the database is closed, the database is destroyed. The fact that
the
database is still present for the second test run tells me that the
connection pool is not also being destroyed as part of the context
shutdown.
I had a look in the "destroy" code and we do unbind all configured
resources from JNDI so they will be garbage collected, as well we call
stop() on all ResourceAdapter impls. The DataSource pool doesn't
implement the ResourceAdapter interface so therefore isn't getting
explicitly closed. We use a variation of commons-dbcp, looking around
to see if there's some way to close the pool -- don't see anything
just yet.
One clever way to work around the issue with the existing code might
be to specify a different in memory db name for each test. Maybe
something like:
properties.setProperty("test.JdbcUrl", testDatabaseConnectionURL +
(count++));
Would be cool if Junit could inject the test name so you could use
that as the in-memory db name.
In case it helps, here's how I'm building my context:
final Properties properties = new Properties();
properties.putAll(System.getProperties()); // allow for -D
properties to
affect context construction
Just a note that this is default behavior for any props that OpenEJB
understands. Internally we first grab a copy of the system properties
the overlay the initial context properties, then use the result.
Definitely let us know if there's a situation where that isn't working
for you.
-David