From c9427191ee7e6175493b6557e2f604213ce8342c Mon Sep 17 00:00:00 2001 From: Andy Wilkinson Date: Mon, 21 Nov 2016 10:40:34 +0000 Subject: [PATCH] Set TCCL before initialising test class in FilteredClassPathRunner Closes gh-7435 --- .../testutil/FilteredClassPathRunner.java | 73 ++++++++++++++----- 1 file changed, 53 insertions(+), 20 deletions(-) diff --git a/spring-boot/src/test/java/org/springframework/boot/testutil/FilteredClassPathRunner.java b/spring-boot/src/test/java/org/springframework/boot/testutil/FilteredClassPathRunner.java index c89aa161e768..84f111338364 100644 --- a/spring-boot/src/test/java/org/springframework/boot/testutil/FilteredClassPathRunner.java +++ b/spring-boot/src/test/java/org/springframework/boot/testutil/FilteredClassPathRunner.java @@ -62,6 +62,19 @@ protected TestClass createTestClass(Class testClass) { } } + @Override + protected Object createTest() throws Exception { + FilteredTestClass testClass = (FilteredTestClass) getTestClass(); + return testClass.doWithFilteredContextClassLoader( + new FilteredTestClass.FilteredTcclAction() { + + @Override + public Object perform() throws Exception { + return FilteredClassPathRunner.super.createTest(); + } + }); + } + private URLClassLoader createTestClassLoader(Class testClass) throws Exception { URLClassLoader classLoader = (URLClassLoader) this.getClass().getClassLoader(); return new FilteredClassLoader(filterUrls(extractUrls(classLoader), testClass), @@ -183,40 +196,60 @@ private List wrapFrameworkMethods( List wrapped = new ArrayList( methods.size()); for (FrameworkMethod frameworkMethod : methods) { - wrapped.add(new FilteredFrameworkMethod(this.classLoader, - frameworkMethod.getMethod())); + wrapped.add(new FilteredFrameworkMethod(frameworkMethod.getMethod())); } return wrapped; } - } - - /** - * Filtered version of JUnit's {@link FrameworkMethod}. - */ - private static final class FilteredFrameworkMethod extends FrameworkMethod { - - private final ClassLoader classLoader; - - private FilteredFrameworkMethod(ClassLoader classLoader, Method method) { - super(method); - this.classLoader = classLoader; - } - - @Override - public Object invokeExplosively(Object target, Object... params) - throws Throwable { + private T doWithFilteredContextClassLoader( + FilteredTcclAction action) throws E { ClassLoader originalClassLoader = Thread.currentThread() .getContextClassLoader(); Thread.currentThread().setContextClassLoader(this.classLoader); try { - return super.invokeExplosively(target, params); + return action.perform(); } finally { Thread.currentThread().setContextClassLoader(originalClassLoader); } } + /** + * An action to be performed with the {@link FilteredClassLoader} set as the + * thread context class loader. + */ + private interface FilteredTcclAction { + + T perform() throws E; + + } + + /** + * Filtered version of JUnit's {@link FrameworkMethod}. + */ + private final class FilteredFrameworkMethod extends FrameworkMethod { + + private FilteredFrameworkMethod(Method method) { + super(method); + } + + @Override + public Object invokeExplosively(final Object target, final Object... params) + throws Throwable { + return doWithFilteredContextClassLoader( + new FilteredTcclAction() { + + @Override + public Object perform() throws Throwable { + return FilteredFrameworkMethod.super.invokeExplosively( + target, params); + } + + }); + } + + } + } private static final class FilteredClassLoader extends URLClassLoader {