HHH-16911 Integration test for empty SessionFactory to not leak the CL
This commit is contained in:
parent
187e637b68
commit
6ff15ff3fb
|
@ -0,0 +1,71 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.bootstrap.registry.classloading;
|
||||
|
||||
import java.sql.Driver;
|
||||
import java.sql.DriverManager;
|
||||
import java.sql.SQLException;
|
||||
import java.util.Set;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.hibernate.dialect.H2Dialect;
|
||||
|
||||
import org.hibernate.testing.orm.junit.RequiresDialect;
|
||||
import org.junit.Assert;
|
||||
import org.junit.jupiter.api.AfterAll;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
/**
|
||||
* Verifies that Hibernate ORM won't leak the classloader.
|
||||
* We only test in H2 to save some time; we also need to avoid
|
||||
* leaks by JDBC drivers, and since these aren't our responsibility
|
||||
* it's best to focus on a single DB.
|
||||
*/
|
||||
@RequiresDialect(H2Dialect.class)
|
||||
public class HibernateClassLoaderLeaksTest {
|
||||
|
||||
private static Set<Driver> knownDrivers;
|
||||
|
||||
@BeforeAll
|
||||
public static void prepareForClassLoaderLeakTest() {
|
||||
final String property = System.getProperty( "log4j2.disableJmx" );
|
||||
Assert.assertEquals( "To be able to test against leaks, the system property 'log4j2.disableJmx' must be set to true",
|
||||
"true", property );
|
||||
|
||||
//Attempt to workaround the mess of DriverManager leaks by clearing it before the test;
|
||||
//it will most certainly re-register all drivers again within the test running context,
|
||||
//but that will imply that the isolated classloader will also have permission to de-register them.
|
||||
knownDrivers = DriverManager.drivers().collect( Collectors.toUnmodifiableSet() );
|
||||
knownDrivers.forEach( HibernateClassLoaderLeaksTest::cleanup );
|
||||
}
|
||||
|
||||
@AfterAll
|
||||
public static void restoreRegisteredDrivers() throws SQLException {
|
||||
if ( knownDrivers != null ) {
|
||||
for ( Driver driver : knownDrivers ) {
|
||||
DriverManager.registerDriver( driver );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void hibernateDoesNotLeakClassloader() {
|
||||
ClassLoaderLeakDetector.assertNotLeakingAction( HibernateLoadingTestAction.class.getName() );
|
||||
}
|
||||
|
||||
private static void cleanup(Driver driver) {
|
||||
System.out.println( "Attempting de-registration of driver: " + driver );
|
||||
try {
|
||||
DriverManager.deregisterDriver( driver );
|
||||
}
|
||||
catch ( SQLException e ) {
|
||||
throw new RuntimeException( e );
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.bootstrap.registry.classloading;
|
||||
|
||||
import java.sql.Driver;
|
||||
import java.sql.DriverManager;
|
||||
import java.sql.SQLException;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.hibernate.jpa.boot.spi.Bootstrap;
|
||||
import org.hibernate.orm.test.jpa.BaseEntityManagerFunctionalTestCase;
|
||||
|
||||
import jakarta.persistence.EntityManagerFactory;
|
||||
|
||||
/**
|
||||
* A Runnable which initializes an EntityManagerFactory;
|
||||
* this is meant to test against classloader leaks, so needs
|
||||
* to be packaged as a Runnable rather than using our usual
|
||||
* testing facilities.
|
||||
*/
|
||||
public class HibernateLoadingTestAction extends NotLeakingTestAction implements Runnable {
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
super.run(); //for basic sanity self-check
|
||||
final Map config = new HashMap();
|
||||
EntityManagerFactory emf = Bootstrap.getEntityManagerFactoryBuilder(
|
||||
new BaseEntityManagerFunctionalTestCase.TestingPersistenceUnitDescriptorImpl( getClass().getSimpleName() ),
|
||||
config
|
||||
).build();
|
||||
try {
|
||||
emf.close();
|
||||
}
|
||||
finally {
|
||||
cleanupJDBCDrivers();
|
||||
}
|
||||
}
|
||||
|
||||
private void cleanupJDBCDrivers() {
|
||||
DriverManager.drivers().forEach( this::deregister );
|
||||
}
|
||||
|
||||
private void deregister(final Driver driver) {
|
||||
System.out.println( "Unregistering driver: " +driver);
|
||||
try {
|
||||
DriverManager.deregisterDriver( driver );
|
||||
}
|
||||
catch ( SQLException e ) {
|
||||
throw new RuntimeException( e );
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue