From cc8c852c2bd59d87afb90fe79b850161b23acf26 Mon Sep 17 00:00:00 2001 From: Juergen Hoeller Date: Mon, 12 Jun 2023 11:33:54 +0200 Subject: [PATCH] Specific check for parent of MethodInvocationInfo ClassLoader See gh-30389 --- .../annotation/MvcUriComponentsBuilder.java | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/MvcUriComponentsBuilder.java b/spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/MvcUriComponentsBuilder.java index 46c3ab1543b..5086cf055e7 100644 --- a/spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/MvcUriComponentsBuilder.java +++ b/spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/MvcUriComponentsBuilder.java @@ -780,11 +780,24 @@ public class MvcUriComponentsBuilder { else if (controllerType.isInterface()) { ClassLoader classLoader = controllerType.getClassLoader(); - if (classLoader == null || classLoader.getParent() == null) { - // JDK interface type from bootstrap loader or platform loader -> - // use higher-level loader which can see Spring infrastructure classes + if (classLoader == null) { + // JDK bootstrap loader -> use MethodInvocationInfo ClassLoader instead. classLoader = MethodInvocationInfo.class.getClassLoader(); } + else if (classLoader.getParent() == null) { + // Potentially the JDK platform loader on JDK 9+ + ClassLoader miiClassLoader = MethodInvocationInfo.class.getClassLoader(); + ClassLoader miiParent = miiClassLoader.getParent(); + while (miiParent != null) { + if (classLoader == miiParent) { + // Suggested ClassLoader is ancestor of MethodInvocationInfo ClassLoader + // -> use MethodInvocationInfo ClassLoader itself instead. + classLoader = miiClassLoader; + break; + } + miiParent = miiParent.getParent(); + } + } Class[] ifcs = new Class[] {controllerType, MethodInvocationInfo.class}; return (T) Proxy.newProxyInstance(classLoader, ifcs, interceptor); }