且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

使用不同的类加载器进行不同的JUnit测试?

更新时间:2023-01-10 10:30:21

这个问题可能很旧但是因为这是我遇到这个问题时最接近的答案,但我会描述我的解决方案。

This question might be old but since this was the nearest answer I found when I had this problem I though I'd describe my solution.

使用JUnit 4

将测试分开,以便每个类有一个测试方法(此解决方案只更改类之间的类加载器,而不是方法之间,因为父级运行器每个类收集一次所有方法)

Split your tests up so that there is one test method per class (this solution only changes classloaders between classes, not between methods as the parent runner gathers all the methods once per class)

@RunWith(SeparateClassloaderTestRunner.class)注释添加到测试类中。

Add the @RunWith(SeparateClassloaderTestRunner.class) annotation to your test classes.

创建 SeparateClassloaderTestRunner ,如下所示:

public class SeparateClassloaderTestRunner extends BlockJUnit4ClassRunner {

    public SeparateClassloaderTestRunner(Class<?> clazz) throws InitializationError {
        super(getFromTestClassloader(clazz));
    }

    private static Class<?> getFromTestClassloader(Class<?> clazz) throws InitializationError {
        try {
            ClassLoader testClassLoader = new TestClassLoader();
            return Class.forName(clazz.getName(), true, testClassLoader);
        } catch (ClassNotFoundException e) {
            throw new InitializationError(e);
        }
    }

    public static class TestClassLoader extends URLClassLoader {
        public TestClassLoader() {
            super(((URLClassLoader)getSystemClassLoader()).getURLs());
        }

        @Override
        public Class<?> loadClass(String name) throws ClassNotFoundException {
            if (name.startsWith("org.mypackages.")) {
                return super.findClass(name);
            }
            return super.loadClass(name);
        }
    }
}

注意我必须这样做测试在遗留框架中运行的代码,我无法改变。鉴于选择,我会减少使用静态和/或放入测试挂钩以允许系统重置。它可能不是很漂亮,但它允许我测试很多代码,否则很难。

Note I had to do this to test code running in a legacy framework which I couldn't change. Given the choice I'd reduce the use of statics and/or put test hooks in to allow the system to be reset. It may not be pretty but it allows me to test an awful lot of code that would be difficult otherwise.

此解决方案还会破坏依赖于类加载技巧的其他任何东西,例如: Mockito。

Also this solution breaks anything else that relies on classloading tricks such as Mockito.