[GRADLE-2052] Cannot use dom4j from task action attached to built-in task Created: 17/Jan/12  Updated: 04/Jan/13  Resolved: 18/Jan/12

Status: Resolved
Project: Gradle
Affects Version/s: 1.0-milestone-5
Fix Version/s: 1.0-milestone-8

Type: Improvement
Reporter: Gradle Forums Assignee: Unassigned
Resolution: Fixed Votes: 0


 Description   

The Hibernate build has been stuck at m2/m3 for many reasons. Recently I decided to get it moved up to m7. But I am running into class loader isolation problems in many of our plugins. As far as I can tell based on forums.gradle.org/gradle/topics/gradle_runtime_classpath et al, starting in m5 there was a change in how classes for plugins get loaded.

This has led to lots of ClassCastExceptions for me in plugins that use libraries that Gradle also uses under the covers. I only know most of this because Adam helped me with one such issue: [1]https://github.com/sebersole/gradle-u... That change was specifically dealing with access to Maven jars. The "solution" was to use reflection to access that Maven stuff I needed. It works, but obviously that is a PITA if you need to do that each and every time your plugin uses a jar or library that Maven also uses, but does not expose.

Take for example, dom4j. The plugin mentioned above is also using dom4j and now I get the same types of errors pertaining to that library:
Nested exception:
java.lang.ClassCastException: org.dom4j.DocumentFactory cannot be cast to org.dom4j.DocumentFactory
at org.dom4j.DocumentFactory.getInstance(DocumentFactory.java:97)
at org.dom4j.io.SAXReader.getDocumentFactory(SAXReader.java:645)
at org.dom4j.io.SAXReader.createContentHandler(SAXReader.java:969)
at org.dom4j.io.SAXReader.read(SAXReader.java:449)
at org.hibernate.build.gradle.upload.StandardMavenAuthenticationProvider.loadRepositoryAuthenticationMap(StandardMavenAuthenticationProvider.java:104)

So what is the solution?
----------------------------------------------------------------------------------------
[1] https://github.com/sebersole/gradle-upload-auth-plugin/pull/2



 Comments   
Comment by Gradle Forums [ 17/Jan/12 ]

Do you have dom4j specified as a dependency of your plugin?

In general, I wonder if a parent-last delegation model would be a better solution than completely hiding away all those libraries. For example, it would solve the mentioned Maven problem immediately (I think).

Comment by Gradle Forums [ 17/Jan/12 ]

Hey Peter, thanks for the response.

So if I understand correctly there is nothing I can do within the constraints of Gradle releases up through m7 at least? I will have to use reflection and remove the shared library (dom4j in this case) off my plugins explicit class-path?

Not sure parent-last delegation is appropriate in all cases either since it could lead to issues when the plugin class-path has access to the shared lib. Maybe I am missing something, but in the Maven deal wouldn't it still be a problem if my plugin defines a dep on Maven jars?

Comment by Gradle Forums [ 17/Jan/12 ]

Can't you just have your own dom4j library in your plugin? You don't need to share dom4j objects with anyone else, do you?

With parent-last delegation, plugins wouldn't themselves declare dependencies for libraries that need to be shared with Gradle and/or other plugins. But they could still have their own version of libraries that don't need to be shared.

Comment by Gradle Forums [ 17/Jan/12 ]

> Can't you just have your own dom4j library in your plugin?

Note sure I follow. That is exactly what I do today and what causes problems. When I say "shared" I simply mean that I need to use a library that Gradle is using also, dom4j in this case. dom4j is defined in my plugin's compile configuration. I tried removing it from compile thinking I would then pick up the dom4j classes from Gradle's class loader. But of course then I cannot compile because the dom4j cannot be found for compilation (as a side-note, I am using gradleApi() also to define compile configuration, but gradleApi() does not account for dom4j)

I guess maybe could get away with adding dom4j in a "provided" configuration (you know, needed for compilation, but not exported to runtime classpath). Too bad Gradle does not think provided is useful

> You don't need to share dom4j objects with anyone else, do you?

No. Hence why I add it to my compile classpath. Though actually I follow the belief that any library I explicitly bind to in my code should be explicitly added to my dependency configuration.

Comment by Gradle Forums [ 17/Jan/12 ]

I didn't look at your code, so I didn't know exactly what you do. However, the problem seems different from the Maven case. In the dom4j case you don't need to share objects with Gradle or other plugins, and having a compile dependency in your plugin should suffice. Or so I thought. A deeper look into org.dom4j.DocumentFactory might reveal what the problem is.

Comment by Gradle Forums [ 17/Jan/12 ]

Well looking at the stack trace I assume that it tries to reuse JAXP components that are loaded/cached as part of Gradle's using dom4j.

My usage it about as basic as it gets:

private void loadRepositoryAuthenticationMap() {
...
InputSource inputSource = new InputSource( new FileInputStream( settingsFile ) );
final Document document = buildSAXReader().read( inputSource );
...
}

private SAXReader buildSAXReader() {
SAXReader saxReader = new SAXReader();
saxReader.setMergeAdjacentText( true );
return saxReader;
}

Thats it.

Comment by Gradle Forums [ 17/Jan/12 ]

@Steve, do you have the rest of that stack trace?

Comment by Gradle Forums [ 17/Jan/12 ]

Error reading Maven settings.xml
org.dom4j.DocumentException: org.dom4j.DocumentFactory cannot be cast to org.dom4j.DocumentFactory Nested exception: org.dom4j.DocumentFactory cannot be cast to org.dom4j.DocumentFactory
at org.dom4j.io.SAXReader.read(SAXReader.java:484)
at org.hibernate.build.gradle.upload.StandardMavenAuthenticationProvider.loadRepositoryAuthenticationMap(StandardMavenAuthenticationProvider.java:104)
at org.hibernate.build.gradle.upload.StandardMavenAuthenticationProvider.determineAuthentication(StandardMavenAuthenticationProvider.java:64)
at org.hibernate.build.gradle.upload.AuthenticationHandler.locateAuthenticationDetails(AuthenticationHandler.java:77)
at org.hibernate.build.gradle.upload.AuthenticationHandler.access$000(AuthenticationHandler.java:41)
at org.hibernate.build.gradle.upload.AuthenticationHandler$1.execute(AuthenticationHandler.java:57)
at org.hibernate.build.gradle.upload.AuthenticationHandler$1.execute(AuthenticationHandler.java:52)
at org.gradle.api.internal.FilteredAction.execute(FilteredAction.java:33)
at org.gradle.api.internal.DefaultDomainObjectCollection.all(DefaultDomainObjectCollection.java:144)
at org.hibernate.build.gradle.upload.AuthenticationHandler.execute(AuthenticationHandler.java:51)
at org.hibernate.build.gradle.upload.AuthenticationHandler.execute(AuthenticationHandler.java:41)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.executeActions(ExecuteActionsTaskExecuter.java:63)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.execute(ExecuteActionsTaskExecuter.java:48)
at org.gradle.api.internal.tasks.execution.PostExecutionAnalysisTaskExecuter.execute(PostExecutionAnalysisTaskExecuter.java:34)
at org.gradle.api.internal.changedetection.CacheLockHandlingTaskExecuter$1.run(CacheLockHandlingTaskExecuter.java:34)
at org.gradle.cache.internal.DefaultCacheAccess$2.create(DefaultCacheAccess.java:200)
at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:172)
at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:198)
at org.gradle.cache.internal.DefaultPersistentDirectoryStore.longRunningOperation(DefaultPersistentDirectoryStore.java:111)
at org.gradle.api.internal.changedetection.DefaultTaskArtifactStateCacheAccess.longRunningOperation(DefaultTaskArtifactStateCacheAccess.java:83)
at org.gradle.api.internal.changedetection.CacheLockHandlingTaskExecuter.execute(CacheLockHandlingTaskExecuter.java:32)
at org.gradle.api.internal.tasks.execution.SkipUpToDateTaskExecuter.execute(SkipUpToDateTaskExecuter.java:55)
at org.gradle.api.internal.tasks.execution.ValidatingTaskExecuter.execute(ValidatingTaskExecuter.java:57)
at org.gradle.api.internal.tasks.execution.SkipEmptySourceFilesTaskExecuter.execute(SkipEmptySourceFilesTaskExecuter.java:41)
at org.gradle.api.internal.tasks.execution.SkipTaskWithNoActionsExecuter.execute(SkipTaskWithNoActionsExecuter.java:51)
at org.gradle.api.internal.tasks.execution.SkipOnlyIfTaskExecuter.execute(SkipOnlyIfTaskExecuter.java:52)
at org.gradle.api.internal.tasks.execution.ExecuteAtMostOnceTaskExecuter.execute(ExecuteAtMostOnceTaskExecuter.java:42)
at org.gradle.api.internal.AbstractTask.executeWithoutThrowingTaskFailure(AbstractTask.java:243)
at org.gradle.execution.DefaultTaskGraphExecuter.executeTask(DefaultTaskGraphExecuter.java:192)
at org.gradle.execution.DefaultTaskGraphExecuter.doExecute(DefaultTaskGraphExecuter.java:177)
at org.gradle.execution.DefaultTaskGraphExecuter.execute(DefaultTaskGraphExecuter.java:83)
at org.gradle.execution.SelectedTaskExecutionAction.execute(SelectedTaskExecutionAction.java:36)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.access$200(DefaultBuildExecuter.java:23)
at org.gradle.execution.DefaultBuildExecuter$2.proceed(DefaultBuildExecuter.java:67)
at org.gradle.api.internal.changedetection.TaskCacheLockHandlingBuildExecuter$1.run(TaskCacheLockHandlingBuildExecuter.java:31)
at org.gradle.cache.internal.DefaultCacheAccess$1.create(DefaultCacheAccess.java:111)
at org.gradle.cache.internal.DefaultCacheAccess.useCache(DefaultCacheAccess.java:126)
at org.gradle.cache.internal.DefaultCacheAccess.useCache(DefaultCacheAccess.java:109)
at org.gradle.cache.internal.DefaultPersistentDirectoryStore.useCache(DefaultPersistentDirectoryStore.java:103)
at org.gradle.api.internal.changedetection.DefaultTaskArtifactStateCacheAccess.useCache(DefaultTaskArtifactStateCacheAccess.java:79)
at org.gradle.api.internal.changedetection.TaskCacheLockHandlingBuildExecuter.execute(TaskCacheLockHandlingBuildExecuter.java:29)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.access$200(DefaultBuildExecuter.java:23)
at org.gradle.execution.DefaultBuildExecuter$2.proceed(DefaultBuildExecuter.java:67)
at org.gradle.execution.DryRunBuildExecutionAction.execute(DryRunBuildExecutionAction.java:32)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:54)
at org.gradle.initialization.DefaultGradleLauncher.doBuildStages(DefaultGradleLauncher.java:152)
at org.gradle.initialization.DefaultGradleLauncher.doBuild(DefaultGradleLauncher.java:108)
at org.gradle.initialization.DefaultGradleLauncher.run(DefaultGradleLauncher.java:76)
at org.gradle.launcher.cli.RunBuildAction.execute(RunBuildAction.java:42)
at org.gradle.launcher.cli.RunBuildAction.execute(RunBuildAction.java:28)
at org.gradle.launcher.exec.ExceptionReportingAction.execute(ExceptionReportingAction.java:32)
at org.gradle.launcher.exec.ExceptionReportingAction.execute(ExceptionReportingAction.java:21)
at org.gradle.launcher.cli.CommandLineActionFactory$WithLoggingAction.execute(CommandLineActionFactory.java:238)
at org.gradle.launcher.cli.CommandLineActionFactory$WithLoggingAction.execute(CommandLineActionFactory.java:222)
at org.gradle.launcher.Main.doAction(Main.java:48)
at org.gradle.launcher.exec.EntryPoint$1.execute(EntryPoint.java:53)
at org.gradle.launcher.exec.EntryPoint$1.execute(EntryPoint.java:51)
at org.gradle.launcher.exec.Execution.execute(Execution.java:28)
at org.gradle.launcher.exec.EntryPoint.run(EntryPoint.java:39)
at org.gradle.launcher.Main.main(Main.java:39)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.gradle.launcher.ProcessBootstrap.runNoExit(ProcessBootstrap.java:51)
at org.gradle.launcher.ProcessBootstrap.run(ProcessBootstrap.java:33)
at org.gradle.launcher.GradleMain.main(GradleMain.java:24)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.gradle.wrapper.BootstrapMainStarter.start(BootstrapMainStarter.java:33)
at org.gradle.wrapper.Wrapper.execute(Wrapper.java:51)
at org.gradle.wrapper.GradleWrapperMain.main(GradleWrapperMain.java:37)
Nested exception:
java.lang.ClassCastException: org.dom4j.DocumentFactory cannot be cast to org.dom4j.DocumentFactory
at org.dom4j.DocumentFactory.getInstance(DocumentFactory.java:97)
at org.dom4j.io.SAXReader.getDocumentFactory(SAXReader.java:645)
at org.dom4j.io.SAXReader.createContentHandler(SAXReader.java:969)
at org.dom4j.io.SAXReader.read(SAXReader.java:449)
at org.hibernate.build.gradle.upload.StandardMavenAuthenticationProvider.loadRepositoryAuthenticationMap(StandardMavenAuthenticationProvider.java:104)
at org.hibernate.build.gradle.upload.StandardMavenAuthenticationProvider.determineAuthentication(StandardMavenAuthenticationProvider.java:64)
at org.hibernate.build.gradle.upload.AuthenticationHandler.locateAuthenticationDetails(AuthenticationHandler.java:77)
at org.hibernate.build.gradle.upload.AuthenticationHandler.access$000(AuthenticationHandler.java:41)
at org.hibernate.build.gradle.upload.AuthenticationHandler$1.execute(AuthenticationHandler.java:57)
at org.hibernate.build.gradle.upload.AuthenticationHandler$1.execute(AuthenticationHandler.java:52)
at org.gradle.api.internal.FilteredAction.execute(FilteredAction.java:33)
at org.gradle.api.internal.DefaultDomainObjectCollection.all(DefaultDomainObjectCollection.java:144)
at org.hibernate.build.gradle.upload.AuthenticationHandler.execute(AuthenticationHandler.java:51)
at org.hibernate.build.gradle.upload.AuthenticationHandler.execute(AuthenticationHandler.java:41)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.executeActions(ExecuteActionsTaskExecuter.java:63)
at org.gradle.api.internal.tasks.execution.ExecuteActionsTaskExecuter.execute(ExecuteActionsTaskExecuter.java:48)
at org.gradle.api.internal.tasks.execution.PostExecutionAnalysisTaskExecuter.execute(PostExecutionAnalysisTaskExecuter.java:34)
at org.gradle.api.internal.changedetection.CacheLockHandlingTaskExecuter$1.run(CacheLockHandlingTaskExecuter.java:34)
at org.gradle.cache.internal.DefaultCacheAccess$2.create(DefaultCacheAccess.java:200)
at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:172)
at org.gradle.cache.internal.DefaultCacheAccess.longRunningOperation(DefaultCacheAccess.java:198)
at org.gradle.cache.internal.DefaultPersistentDirectoryStore.longRunningOperation(DefaultPersistentDirectoryStore.java:111)
at org.gradle.api.internal.changedetection.DefaultTaskArtifactStateCacheAccess.longRunningOperation(DefaultTaskArtifactStateCacheAccess.java:83)
at org.gradle.api.internal.changedetection.CacheLockHandlingTaskExecuter.execute(CacheLockHandlingTaskExecuter.java:32)
at org.gradle.api.internal.tasks.execution.SkipUpToDateTaskExecuter.execute(SkipUpToDateTaskExecuter.java:55)
at org.gradle.api.internal.tasks.execution.ValidatingTaskExecuter.execute(ValidatingTaskExecuter.java:57)
at org.gradle.api.internal.tasks.execution.SkipEmptySourceFilesTaskExecuter.execute(SkipEmptySourceFilesTaskExecuter.java:41)
at org.gradle.api.internal.tasks.execution.SkipTaskWithNoActionsExecuter.execute(SkipTaskWithNoActionsExecuter.java:51)
at org.gradle.api.internal.tasks.execution.SkipOnlyIfTaskExecuter.execute(SkipOnlyIfTaskExecuter.java:52)
at org.gradle.api.internal.tasks.execution.ExecuteAtMostOnceTaskExecuter.execute(ExecuteAtMostOnceTaskExecuter.java:42)
at org.gradle.api.internal.AbstractTask.executeWithoutThrowingTaskFailure(AbstractTask.java:243)
at org.gradle.execution.DefaultTaskGraphExecuter.executeTask(DefaultTaskGraphExecuter.java:192)
at org.gradle.execution.DefaultTaskGraphExecuter.doExecute(DefaultTaskGraphExecuter.java:177)
at org.gradle.execution.DefaultTaskGraphExecuter.execute(DefaultTaskGraphExecuter.java:83)
at org.gradle.execution.SelectedTaskExecutionAction.execute(SelectedTaskExecutionAction.java:36)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.access$200(DefaultBuildExecuter.java:23)
at org.gradle.execution.DefaultBuildExecuter$2.proceed(DefaultBuildExecuter.java:67)
at org.gradle.api.internal.changedetection.TaskCacheLockHandlingBuildExecuter$1.run(TaskCacheLockHandlingBuildExecuter.java:31)
at org.gradle.cache.internal.DefaultCacheAccess$1.create(DefaultCacheAccess.java:111)
at org.gradle.cache.internal.DefaultCacheAccess.useCache(DefaultCacheAccess.java:126)
at org.gradle.cache.internal.DefaultCacheAccess.useCache(DefaultCacheAccess.java:109)
at org.gradle.cache.internal.DefaultPersistentDirectoryStore.useCache(DefaultPersistentDirectoryStore.java:103)
at org.gradle.api.internal.changedetection.DefaultTaskArtifactStateCacheAccess.useCache(DefaultTaskArtifactStateCacheAccess.java:79)
at org.gradle.api.internal.changedetection.TaskCacheLockHandlingBuildExecuter.execute(TaskCacheLockHandlingBuildExecuter.java:29)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.access$200(DefaultBuildExecuter.java:23)
at org.gradle.execution.DefaultBuildExecuter$2.proceed(DefaultBuildExecuter.java:67)
at org.gradle.execution.DryRunBuildExecutionAction.execute(DryRunBuildExecutionAction.java:32)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:61)
at org.gradle.execution.DefaultBuildExecuter.execute(DefaultBuildExecuter.java:54)
at org.gradle.initialization.DefaultGradleLauncher.doBuildStages(DefaultGradleLauncher.java:152)
at org.gradle.initialization.DefaultGradleLauncher.doBuild(DefaultGradleLauncher.java:108)
at org.gradle.initialization.DefaultGradleLauncher.run(DefaultGradleLauncher.java:76)
at org.gradle.launcher.cli.RunBuildAction.execute(RunBuildAction.java:42)
at org.gradle.launcher.cli.RunBuildAction.execute(RunBuildAction.java:28)
at org.gradle.launcher.exec.ExceptionReportingAction.execute(ExceptionReportingAction.java:32)
at org.gradle.launcher.exec.ExceptionReportingAction.execute(ExceptionReportingAction.java:21)
at org.gradle.launcher.cli.CommandLineActionFactory$WithLoggingAction.execute(CommandLineActionFactory.java:238)
at org.gradle.launcher.cli.CommandLineActionFactory$WithLoggingAction.execute(CommandLineActionFactory.java:222)
at org.gradle.launcher.Main.doAction(Main.java:48)
at org.gradle.launcher.exec.EntryPoint$1.execute(EntryPoint.java:53)
at org.gradle.launcher.exec.EntryPoint$1.execute(EntryPoint.java:51)
at org.gradle.launcher.exec.Execution.execute(Execution.java:28)
at org.gradle.launcher.exec.EntryPoint.run(EntryPoint.java:39)
at org.gradle.launcher.Main.main(Main.java:39)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.gradle.launcher.ProcessBootstrap.runNoExit(ProcessBootstrap.java:51)
at org.gradle.launcher.ProcessBootstrap.run(ProcessBootstrap.java:33)
at org.gradle.launcher.GradleMain.main(GradleMain.java:24)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.gradle.wrapper.BootstrapMainStarter.start(BootstrapMainStarter.java:33)
at org.gradle.wrapper.Wrapper.execute(Wrapper.java:51)
at org.gradle.wrapper.GradleWrapperMain.main(GradleWrapperMain.java:37)

Comment by Gradle Forums [ 17/Jan/12 ]

I should note that I also tried changing up [new SAXReader()] to be [new SAXReader( new DocumentFactory() )] thinking that might get around the problem even if I think its NotRight that plugin developers would need to manage this. But I still got errors. For completeness...

Generated at Wed Jun 30 12:11:30 CDT 2021 using Jira 8.4.2#804003-sha1:d21414fc212e3af190e92c2d2ac41299b89402cf.