spring-projects / spring-boot

Spring Boot
https://spring.io/projects/spring-boot
Apache License 2.0
74.54k stars 40.54k forks source link

LinkageError: loader org.springframework.boot.loader.launch.LaunchedClassLoader @3941a79c attempted duplicate class definition for jakarta.mail.Message$RecipientType #42087

Closed xtermi2 closed 1 week ago

xtermi2 commented 2 weeks ago

We traced the issue to the changes made by https://github.com/spring-projects/spring-boot/pull/41665 at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.JarUrlClassLoader.java (ClassLoader.registerAsParallelCapable();): Wenn I build a bootJar with 3.3.3 and copy the JarUrlClassLoader.class file from a 3.3.2 bootJar, our application starts without the LinkageError! I think there is something not sycronized or something like this in the JarUrlClassLoader so it's not capable for parallel execution. But we have not yet identified the Problem in our application/dependencies, as this problem only occurs in one application out of several dozen applications. We are therefore unable to provide a reproducible demo application.

In the debuger i can see 2 calls in parallel:

both entering LaunchedURLClassLoader.loadClass on main thread, then the first returns the loaded class, then the second fails with the LinkageError

 Caused by: java.lang.IllegalStateException: Failed to introspect Class [...EmailServiceImpl] from ClassLoader [org.springframework.boot.loader.launch.LaunchedClassLoader@3941a79c]
      at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:483)
      at org.springframework.util.ReflectionUtils.doWithLocalMethods(ReflectionUtils.java:320)
      at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.buildPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:446)
      at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:417)
      at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findInjectionMetadata(PersistenceAnnotationBeanPostProcessor.java:376)
      at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.postProcessMergedBeanDefinition(PersistenceAnnotationBeanPostProcessor.java:353)
      at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyMergedBeanDefinitionPostProcessors(AbstractAutowireCapableBeanFactory.java:1103)
      at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:574)
      ... 75 common frames omitted
 Caused by: java.lang.LinkageError: loader org.springframework.boot.loader.launch.LaunchedClassLoader @3941a79c attempted duplicate class definition for jakarta.mail.Message$RecipientType. (jakarta.mail.Message$RecipientType is in unnamed module of loader org.springframework.boot.loader.launch.LaunchedClassLoader @3941a79c, parent loader 'app')
      at java.base/java.lang.ClassLoader.defineClass1(Native Method)
      at java.base/java.lang.ClassLoader.defineClass(Unknown Source)
      at java.base/java.security.SecureClassLoader.defineClass(Unknown Source)
      at java.base/java.net.URLClassLoader.defineClass(Unknown Source)
      at java.base/java.net.URLClassLoader$1.run(Unknown Source)
      at java.base/java.net.URLClassLoader$1.run(Unknown Source)
      at java.base/java.security.AccessController.doPrivileged(Unknown Source)
      at java.base/java.net.URLClassLoader.findClass(Unknown Source)
      at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
      at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:107)
      at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
      at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
      at java.base/java.lang.Class.getDeclaredMethods0(Native Method)
      at java.base/java.lang.Class.privateGetDeclaredMethods(Unknown Source)
      at java.base/java.lang.Class.getDeclaredMethods(Unknown Source)
      at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:465)
      ... 82 common frames omitted

The same issue with the classic classloader:

 Caused by: java.lang.LinkageError: loader org.springframework.boot.loader.LaunchedURLClassLoader @b81eda8 attempted duplicate class definition for jakarta.mail.Message$RecipientType. (jakarta.mail.Message$RecipientType is in unnamed module of loader org.springframework.boot.loader.LaunchedURLClassLoader @b81eda8, parent loader 'app')
    at java.base/java.lang.ClassLoader.defineClass1(Native Method)
    at java.base/java.lang.ClassLoader.defineClass(Unknown Source)
    at java.base/java.security.SecureClassLoader.defineClass(Unknown Source)
    at java.base/java.net.URLClassLoader.defineClass(Unknown Source)
    at java.base/java.net.URLClassLoader$1.run(Unknown Source)
    at java.base/java.net.URLClassLoader$1.run(Unknown Source)
    at java.base/java.security.AccessController.doPrivileged(Unknown Source)
    at java.base/java.net.URLClassLoader.findClass(Unknown Source)
    at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
    at org.springframework.boot.loader.LaunchedURLClassLoader.loadClass(LaunchedURLClassLoader.java:150)
    at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
    at java.base/java.lang.Class.getDeclaredMethods0(Native Method)
    at java.base/java.lang.Class.privateGetDeclaredMethods(Unknown Source)
    at java.base/java.lang.Class.getDeclaredMethods(Unknown Source)
    at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:465)
    ... 84 common frames omitted
wilkinsona commented 2 weeks ago

Thanks for the report.

Unfortunately, looking at the code, the cause of the LinkageError isn't apparent. The ClassLoader.loadClass method, under which the LinkageError is being thrown, synchronises on the class loading lock. Changing to being parallel capable means that this lock will be per-class-name rather than the class loader itself, but that should still protect against duplicate class definition attempts.

I don't think I understand the description of what you've seen in the debugger. You say that you can see two calls in parallel but that they're "both entering LaunchedURLClassLoader.loadClass on main thread". Are they definitely both on the main thread? I'd expect separate threads to be involved given the problem that you're seeing.

xtermi2 commented 2 weeks ago

I've found a workaround to prevent the LinkageError: I load the affected classes "manually" a bit earlier in a @Configuration Constructor. Because of the big ammount of classes I just load all classes from the classpath in these packages:

I don't know whats wrong with these jakarta.* classes in our application in combination with hibernate and spring jpa.

@wilkinsona My wording wasn't precise enough, but I also confirmed this with a patched LaunchedClassLoader.loadClass method with trace logging when entering the method and before returning the result to eliminate any “debugger” side effects:

...
enter loadClass jakarta.mail.Message$RecipientType on thread main
enter loadClass jakarta.mail.Message$RecipientType on thread main
return loadClass with class jakarta.mail.Message$RecipientType on thread main
then the LinkageError is thrown

it looks like the parallel loading of classes is not done with multiple threads, but reactive, executing another "class load task" on the main thread when IO is happening and the thread entering waiting state.

wilkinsona commented 2 weeks ago

Thanks, @xtermi2, that's very interesting. So it looks like the loading of jakarta.mail.Message$RecipientType is re-entrant. While the first attempt to load the class is in progress, a second attempt to load it is being made. This second attempt succeeds and the first attempt then proceeds and fails as the class has already been defined. If possible, could you please capture and share the complete stack trace of the main thread for each of the enter loadClass … lines above?

philwebb commented 2 weeks ago

Our class loading delegates to super.loadClass() which has synchronized (getClassLoadingLock(name)) protection. Perhaps you can also try updating your logging to output the result of getClassLoadingLock(name) to check that the same lock object is being returned for both calls.

xtermi2 commented 2 weeks ago

@wilkinsona Here the extended logging with stacktraces on enter and return @philwebb the lock object is the same

enter loadClass: jakarta.mail.Message$RecipientType on thread main with lockObject java.lang.Object@69049967 and stacktrace java.lang.Exception: Stack trace
     at java.base/java.lang.Thread.dumpStack(Unknown Source)
     at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:106)
     at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods0(Native Method)
     at java.base/java.lang.Class.privateGetDeclaredMethods(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods(Unknown Source)
     at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:465)
     at org.springframework.util.ReflectionUtils.doWithLocalMethods(ReflectionUtils.java:320)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.buildPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:446)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:417)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findInjectionMetadata(PersistenceAnnotationBeanPostProcessor.java:376)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.postProcessMergedBeanDefinition(PersistenceAnnotationBeanPostProcessor.java:353)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyMergedBeanDefinitionPostProcessors(AbstractAutowireCapableBeanFactory.java:1103)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:574)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:975)
     at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:971)
     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:625)
     at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:146)
     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:754)
     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:456)
     at org.springframework.boot.SpringApplication.run(SpringApplication.java:335)
     at org.springframework.boot.builder.SpringApplicationBuilder.run(SpringApplicationBuilder.java:149)
     at de.jato.grc.cases.CasesApplication.main(CasesApplication.java:27)
     at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(Unknown Source)
     at java.base/java.lang.reflect.Method.invoke(Unknown Source)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:102)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:64)
     at org.springframework.boot.loader.launch.JarLauncher.main(JarLauncher.java:40)
enter loadClass: jakarta.mail.Message$RecipientType on thread main with lockObject java.lang.Object@69049967 and stacktrace java.lang.Exception: Stack trace
     at java.base/java.lang.Thread.dumpStack(Unknown Source)
     at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:106)
     at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at java.base/java.lang.Class.forName0(Native Method)
     at java.base/java.lang.Class.forName(Unknown Source)
     at java.base/java.lang.Class.forName(Unknown Source)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.CoreTypePool.actualResolve(CoreTypePool.java:90)
     at java.base/java.util.concurrent.ConcurrentHashMap.computeIfAbsent(Unknown Source)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.CoreTypePool.doDescribe(CoreTypePool.java:79)
     at net.bytebuddy.pool.TypePool$AbstractBase.describe(TypePool.java:598)
     at net.bytebuddy.pool.TypePool$AbstractBase$Hierarchical.describe(TypePool.java:678)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.EnhancerImpl.enhance(EnhancerImpl.java:115)
     at org.hibernate.jpa.internal.enhance.EnhancingClassTransformerImpl.transform(EnhancingClassTransformerImpl.java:49)
     at org.springframework.orm.jpa.persistenceunit.ClassFileTransformerAdapter.transform(ClassFileTransformerAdapter.java:70)
     at org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver$FilteringClassFileTransformer.transform(InstrumentationLoadTimeWeaver.java:192)
     at java.instrument/java.lang.instrument.ClassFileTransformer.transform(Unknown Source)
     at java.instrument/sun.instrument.TransformerManager.transform(Unknown Source)
     at java.instrument/sun.instrument.InstrumentationImpl.transform(Unknown Source)
     at java.base/java.lang.ClassLoader.defineClass1(Native Method)
     at java.base/java.lang.ClassLoader.defineClass(Unknown Source)
     at java.base/java.security.SecureClassLoader.defineClass(Unknown Source)
     at java.base/java.net.URLClassLoader.defineClass(Unknown Source)
     at java.base/java.net.URLClassLoader$1.run(Unknown Source)
     at java.base/java.net.URLClassLoader$1.run(Unknown Source)
     at java.base/java.security.AccessController.doPrivileged(Unknown Source)
     at java.base/java.net.URLClassLoader.findClass(Unknown Source)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:115)
     at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods0(Native Method)
     at java.base/java.lang.Class.privateGetDeclaredMethods(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods(Unknown Source)
     at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:465)
     at org.springframework.util.ReflectionUtils.doWithLocalMethods(ReflectionUtils.java:320)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.buildPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:446)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:417)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findInjectionMetadata(PersistenceAnnotationBeanPostProcessor.java:376)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.postProcessMergedBeanDefinition(PersistenceAnnotationBeanPostProcessor.java:353)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyMergedBeanDefinitionPostProcessors(AbstractAutowireCapableBeanFactory.java:1103)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:574)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:975)
     at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:971)
     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:625)
     at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:146)
     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:754)
     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:456)
     at org.springframework.boot.SpringApplication.run(SpringApplication.java:335)
     at org.springframework.boot.builder.SpringApplicationBuilder.run(SpringApplicationBuilder.java:149)
     at de.jato.grc.cases.CasesApplication.main(CasesApplication.java:27)
     at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(Unknown Source)
     at java.base/java.lang.reflect.Method.invoke(Unknown Source)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:102)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:64)
     at org.springframework.boot.loader.launch.JarLauncher.main(JarLauncher.java:40)
return loadClass class jakarta.mail.Message$RecipientType on thread main with lockObject java.lang.Object@69049967 and stacktrace java.lang.Exception: Stack trace
     at java.base/java.lang.Thread.dumpStack(Unknown Source)
     at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:118)
     at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at java.base/java.lang.Class.forName0(Native Method)
     at java.base/java.lang.Class.forName(Unknown Source)
     at java.base/java.lang.Class.forName(Unknown Source)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.CoreTypePool.actualResolve(CoreTypePool.java:90)
     at java.base/java.util.concurrent.ConcurrentHashMap.computeIfAbsent(Unknown Source)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.CoreTypePool.doDescribe(CoreTypePool.java:79)
     at net.bytebuddy.pool.TypePool$AbstractBase.describe(TypePool.java:598)
     at net.bytebuddy.pool.TypePool$AbstractBase$Hierarchical.describe(TypePool.java:678)
     at org.hibernate.bytecode.enhance.internal.bytebuddy.EnhancerImpl.enhance(EnhancerImpl.java:115)
     at org.hibernate.jpa.internal.enhance.EnhancingClassTransformerImpl.transform(EnhancingClassTransformerImpl.java:49)
     at org.springframework.orm.jpa.persistenceunit.ClassFileTransformerAdapter.transform(ClassFileTransformerAdapter.java:70)
     at org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver$FilteringClassFileTransformer.transform(InstrumentationLoadTimeWeaver.java:192)
     at java.instrument/java.lang.instrument.ClassFileTransformer.transform(Unknown Source)
     at java.instrument/sun.instrument.TransformerManager.transform(Unknown Source)
     at java.instrument/sun.instrument.InstrumentationImpl.transform(Unknown Source)
     at java.base/java.lang.ClassLoader.defineClass1(Native Method)
     at java.base/java.lang.ClassLoader.defineClass(Unknown Source)
     at java.base/java.security.SecureClassLoader.defineClass(Unknown Source)
     at java.base/java.net.URLClassLoader.defineClass(Unknown Source)
     at java.base/java.net.URLClassLoader$1.run(Unknown Source)
     at java.base/java.net.URLClassLoader$1.run(Unknown Source)
     at java.base/java.security.AccessController.doPrivileged(Unknown Source)
     at java.base/java.net.URLClassLoader.findClass(Unknown Source)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at org.springframework.boot.loader.net.protocol.jar.JarUrlClassLoader.loadClass(JarUrlClassLoader.java:115)
     at org.springframework.boot.loader.launch.LaunchedClassLoader.loadClass(LaunchedClassLoader.java:91)
     at java.base/java.lang.ClassLoader.loadClass(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods0(Native Method)
     at java.base/java.lang.Class.privateGetDeclaredMethods(Unknown Source)
     at java.base/java.lang.Class.getDeclaredMethods(Unknown Source)
     at org.springframework.util.ReflectionUtils.getDeclaredMethods(ReflectionUtils.java:465)
     at org.springframework.util.ReflectionUtils.doWithLocalMethods(ReflectionUtils.java:320)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.buildPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:446)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findPersistenceMetadata(PersistenceAnnotationBeanPostProcessor.java:417)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.findInjectionMetadata(PersistenceAnnotationBeanPostProcessor.java:376)
     at org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor.postProcessMergedBeanDefinition(PersistenceAnnotationBeanPostProcessor.java:353)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyMergedBeanDefinitionPostProcessors(AbstractAutowireCapableBeanFactory.java:1103)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:574)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:542)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1355)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1185)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:254)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1443)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1353)
     at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:904)
     at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:782)
     at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:237)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1375)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1212)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:562)
     at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:522)
     at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:337)
     at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234)
     at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:335)
     at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200)
     at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:975)
     at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:971)
     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:625)
     at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:146)
     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:754)
     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:456)
     at org.springframework.boot.SpringApplication.run(SpringApplication.java:335)
     at org.springframework.boot.builder.SpringApplicationBuilder.run(SpringApplicationBuilder.java:149)
     at de.jato.grc.cases.CasesApplication.main(CasesApplication.java:27)
     at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(Unknown Source)
     at java.base/java.lang.reflect.Method.invoke(Unknown Source)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:102)
     at org.springframework.boot.loader.launch.Launcher.launch(Launcher.java:64)
     at org.springframework.boot.loader.launch.JarLauncher.main(JarLauncher.java:40)

And here the correspondic code:

    @Override
    protected Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException {
        if (!this.hasJarUrls) {
            return super.loadClass(name, resolve);
        }
        final String loggingOnClass = "jakarta.mail.Message";
        if (name.startsWith(loggingOnClass)) {
            System.out.println("enter loadClass: " + name + " on thread " + Thread.currentThread().getName() + " with lockObject " + getClassLoadingLock(name) + " and stacktrace ");
            Thread.dumpStack();
        }
        Optimizations.enable(true);
        try {
            try {
                definePackageIfNecessary(name);
            } catch (IllegalArgumentException ex) {
                tolerateRaceConditionDueToBeingParallelCapable(ex, name);
            }
            final Class<?> loadedClass = super.loadClass(name, resolve);
            if (name.startsWith(loggingOnClass)) {
                System.out.println("return loadClass " + loadedClass + " on thread " + Thread.currentThread().getName() + " with lockObject " + getClassLoadingLock(name) + " and stacktrace ");
                Thread.dumpStack();
            }
            return loadedClass;
        } finally {
            Optimizations.disable();
        }
    }
philwebb commented 1 week ago

Thanks for the extra details. I hadn't noticed before that both calls are on the same thread which is interesting.

philwebb commented 1 week ago

@xtermi2 Are you running the failing application with any kind of -javaagent parameters? I notice InstrumentationLoadTimeWeaver is in the stack trace.

xtermi2 commented 1 week ago

@xtermi2 Are you running the failing application with any kind of -javaagent parameters? I notice InstrumentationLoadTimeWeaver is in the stack trace.

Yes, with spring-instrument - we use AspectJ load-time weaving, but all other our applications do the same.

wilkinsona commented 1 week ago

As far as I can tell, it is illegal for a class file transformer to load the class that it's being asked to transform and doing so results in a LinkageError. This applies whether or not Spring Boot is involved. Here's a minimal agent that reproduces a LinkageError:

package com.example.agent;

import java.lang.instrument.ClassFileTransformer;
import java.lang.instrument.IllegalClassFormatException;
import java.lang.instrument.Instrumentation;
import java.security.ProtectionDomain;

public class Agent {

    public static void premain(String argument, Instrumentation instrumentation) {
        instrumentation.addTransformer(new ClassFileTransformer() {

            @Override
            public byte[] transform(ClassLoader loader, String className, Class<?> classBeingRedefined,
                    ProtectionDomain protectionDomain, byte[] classfileBuffer) throws IllegalClassFormatException {
                if (className.equals("com/example/app/Main")) {
                    try {
                        loader.loadClass("com.example.app.Main");
                    }
                    catch (Exception ex) {
                        ex.printStackTrace();
                        return null;
                    }
                }
                return null;
            }

        });
    }

}

Here's the main class that the transformer attempts to load:

package com.example.app;

public class Main {

    public static void main(String[] args) {
        System.out.println("App main method");
    }

}

Running com.example.app.Main using the above agent, produces the following failure:

Error: LinkageError occurred while loading main class com.example.app.Main
        java.lang.LinkageError: loader 'app' attempted duplicate class definition for com.example.app.Main. (com.example.app.Main is in unnamed module of loader 'app')

I think this is a bug in Hibernate's class transformation. jakarta.mail.Message$RecipientType is being loaded and org.hibernate.jpa.internal.enhance.EnhancingClassTransformerImpl is called to apply any transformations that may be necessary. As part of this, another call to load jakarta.mail.Message$RecipientType is made. This succeeds but, as the stack unwinds, the first call to load it then fails due to the duplicate definition.

I believe the required fix is to ensure that org.hibernate.jpa.internal.enhance.EnhancingClassTransformerImpl does not trigger the loading of the class that it is being asked to transform.

xtermi2 commented 1 week ago

thanks a lot @wilkinsona for your analysis

xtermi2 commented 1 week ago

Just for the record: Here is the Hibernate issue: https://hibernate.atlassian.net/browse/HHH-18108 It's already fixed in hibernate 6.6.0 And in 6.5.0 it's also working .. so only 6.5.1 and 6.5.2 is broken