Skip to content

Commit ebe7a02

Browse files
chrisr3sbrannen
authored andcommitted
Load classes using the test's own ClassLoader
Prior to this commit, the extensions supporting @MethodSource, @EnabledIf, and @DisabledIf failed to load an external class if the external class was not visible to JUnit's default ClassLoader. This commit addresses those issues by loading external classes using the ClassLoader obtained from the test class or falling back to JUnit's default ClassLoader if the test's ClassLoader cannot be obtained. This allows JUnit to find the classes while running in a custom ClassLoader arrangement -- for example, inside an OSGi framework. Closes #3292 Closes #3279 Closes #3280
1 parent 334860a commit ebe7a02

File tree

3 files changed

+11
-8
lines changed

3 files changed

+11
-8
lines changed

documentation/src/docs/asciidoc/release-notes/release-notes-5.10.0-M1.adoc

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,8 @@ repository on GitHub.
1515

1616
==== Bug Fixes
1717

18-
* ❓
18+
* Use a test class's own classloader to search for `@MethodSource` and `MethodBasedCondition` methods.
19+
This allows these features to work correctly inside an OSGi framework.
1920

2021
==== Deprecations and Breaking Changes
2122

junit-jupiter-api/src/main/java/org/junit/jupiter/api/condition/MethodBasedCondition.java

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -57,13 +57,14 @@ public ConditionEvaluationResult evaluateExecutionCondition(ExtensionContext con
5757
}
5858

5959
private Method getConditionMethod(String fullyQualifiedMethodName, ExtensionContext context) {
60+
final Class<?> testClass = context.getRequiredTestClass();
6061
if (!fullyQualifiedMethodName.contains("#")) {
61-
return findMethod(context.getRequiredTestClass(), fullyQualifiedMethodName);
62+
return findMethod(testClass, fullyQualifiedMethodName);
6263
}
6364
String[] methodParts = ReflectionUtils.parseFullyQualifiedMethodName(fullyQualifiedMethodName);
6465
String className = methodParts[0];
6566
String methodName = methodParts[1];
66-
Class<?> clazz = ReflectionUtils.tryToLoadClass(className).getOrThrow(
67+
Class<?> clazz = ReflectionUtils.tryToLoadClass(className, testClass.getClassLoader()).getOrThrow(
6768
cause -> new JUnitException(format("Could not load class [%s]", className), cause));
6869
return findMethod(clazz, methodName);
6970
}

junit-jupiter-params/src/main/java/org/junit/jupiter/params/provider/MethodArgumentsProvider.java

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,7 @@ private static Method findFactoryMethod(Class<?> testClass, Method testMethod, S
7373
}
7474

7575
// Find factory method using fully-qualified name.
76-
Method factoryMethod = findFactoryMethodByFullyQualifiedName(testMethod, factoryMethodName);
76+
Method factoryMethod = findFactoryMethodByFullyQualifiedName(testClass, testMethod, factoryMethodName);
7777

7878
// Ensure factory method has a valid return type and is not a test method.
7979
Preconditions.condition(isFactoryMethod.test(factoryMethod), () -> format(
@@ -103,12 +103,13 @@ private static boolean looksLikeAFullyQualifiedMethodName(String factoryMethodNa
103103
return true;
104104
}
105105

106-
private static Method findFactoryMethodByFullyQualifiedName(Method testMethod, String fullyQualifiedMethodName) {
106+
private static Method findFactoryMethodByFullyQualifiedName(Class<?> testClass, Method testMethod,
107+
String fullyQualifiedMethodName) {
107108
String[] methodParts = ReflectionUtils.parseFullyQualifiedMethodName(fullyQualifiedMethodName);
108109
String className = methodParts[0];
109110
String methodName = methodParts[1];
110111
String methodParameters = methodParts[2];
111-
Class<?> clazz = loadRequiredClass(className);
112+
Class<?> clazz = loadRequiredClass(className, testClass.getClassLoader());
112113

113114
// Attempt to find an exact match first.
114115
Method factoryMethod = ReflectionUtils.findMethod(clazz, methodName, methodParameters).orElse(null);
@@ -170,8 +171,8 @@ private static boolean isTestMethod(Method candidate) {
170171
|| isAnnotated(candidate, TestFactory.class);
171172
}
172173

173-
private static Class<?> loadRequiredClass(String className) {
174-
return ReflectionUtils.tryToLoadClass(className).getOrThrow(
174+
private static Class<?> loadRequiredClass(String className, ClassLoader classLoader) {
175+
return ReflectionUtils.tryToLoadClass(className, classLoader).getOrThrow(
175176
cause -> new JUnitException(format("Could not load class [%s]", className), cause));
176177
}
177178

0 commit comments

Comments
 (0)