New to grails - problem with JAVA jar dependencies

johan313

New member
Hello,

So i decided to try out GRAILS, but im stuck at a (hopefully) very minor problem.

I have an existing JAVA (jar) library that i wish to use in my grails app. I managed to get the jar imported to my grails app, but when calling methods from the package i get the expected class not found exception. This offcourse is expected since i have not imported any of the dependencies. My jar uses the following dependencies:

Code:
                         <dependencies>
                                                          <dependency>
                                                                                       <groupId>joda-time</groupId>
                                                                                       <artifactId>joda-time</artifactId>
                                                                                       <version>2.1</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>commons-codec</groupId>
                                                                                       <artifactId>commons-codec</artifactId>
                                                                                       <version>1.7</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>commons-collections</groupId>
                                                                                       <artifactId>commons-collections</artifactId>
                                                                                       <version>3.2.1</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>commons-io</groupId>
                                                                                       <artifactId>commons-io</artifactId>
                                                                                       <version>2.4</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>commons-logging</groupId>
                                                                                       <artifactId>commons-logging</artifactId>
                                                                                       <version>1.1.1</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>net.sourceforge.cssparser</groupId>
                                                                                       <artifactId>cssparser</artifactId>
                                                                                       <version>0.9.8</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>net.sourceforge.htmlunit</groupId>
                                                                                       <artifactId>htmlunit-core-js</artifactId>
                                                                                       <version>2.11</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>net.sourceforge.nekohtml</groupId>
                                                                                       <artifactId>nekohtml</artifactId>
                                                                                       <version>1.9.17</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.apache.commons</groupId>
                                                                                       <artifactId>commons-lang3</artifactId>
                                                                                       <version>3.1</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.apache.httpcomponents</groupId>
                                                                                       <artifactId>httpclient</artifactId>
                                                                                       <version>4.2.2</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.apache.httpcomponents</groupId>
                                                                                       <artifactId>httpmime</artifactId>
                                                                                       <version>4.2.2</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.eclipse.jetty</groupId>
                                                                                       <artifactId>jetty-websocket</artifactId>
                                                                                       <version>8.1.7.v20120910</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>xalan</groupId>
                                                                                       <artifactId>xalan</artifactId>
                                                                                       <version>2.7.1</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>xerces</groupId>
                                                                                       <artifactId>xercesImpl</artifactId>
                                                                                       <version>2.10.0</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>net.sourceforge.htmlunit</groupId>
                                                                                       <artifactId>htmlunit</artifactId>
                                                                                       <version>2.11</version>
                                                                                       <scope>compile</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>junit</groupId>
                                                                                       <artifactId>junit</artifactId>
                                                                                       <version>4.9</version>
                                                                                       <scope>test</scope>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.slf4j</groupId>
                                                                                       <artifactId>slf4j-api</artifactId>
                                                                                       <version>1.6.0</version>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.slf4j</groupId>
                                                                                       <artifactId>slf4j-log4j12</artifactId>
                                                                                       <version>1.6.0</version>
                                                          </dependency>
                                                          <dependency>
                                                                                       <groupId>org.slf4j</groupId>
                                                                                       <artifactId>jcl-over-slf4j</artifactId>
                                                                                       <version>1.6.0</version>
                                                          </dependency>
                             </dependencies>

What is the proper way to have GRAILS resolve these? I tried adding them one by one with the shell command install-dependency, and I tried adding them to the /lib folder of my grails project and running refresh dependency after that.

The result is that i always end up with the following exception,
java.lang.NoClassDefFoundError: org/apache/xerces/dom/DeferredElementImpl
at org.apache.xerces.dom.DeferredDocumentImpl.getNodeObject(Unknown Source)

so i'm kinda stuck here. Any help is appreciated, been banging my head against a wall for too many hours now.

R
johan
 

dave

Administrator
Staff member
When I've needed to add my own jars to a Grails app, all I've done is copy them into the lib folder then they will be available for use.

I'd say double check you have the xerces jar in your lib folder as that's the one its complaining about.
 

johan313

New member
Thx for your answer Dave!

I actually worked a bit on this yesterday, and I now think it's a classlaoder / dependency issue. Maybe their is more than one instances of some given class in my applications context? After all the final error was ClassDefNotFound.

My problem can actually be duplicated very easily:

1. Create a new standard GRAILS project.
2. Open BuildConfig.groovy
3. Add the following dependency: compile 'net.sourceforge.htmlunit:htmlunit:2.11'
4. Run the project.

These steps results in the same exception being thrown that i get from running my project if i import my JAR + its dependecies.

Any ideas on how to approach / debug / resolve this?

I must admit, im truly stuck. Will take a second look at it tomorrow afer work.

Regards
Johan
 

dave

Administrator
Staff member
Hi Johan,

Funnily enough I also did something once with HTMLUnit and also had issues, I'm sure the problem was because of a dependancy Grails itself had which was an incompatiable version to what htmlunit was trying to use...

You can supply a closure when declaring the dependancy to tell it to ignore grails dependancies already present..

runtime ('htmlunit:htmlunit:2.11') {
exclude "groovy-all"
}

That might fix it for you.. in my case however (just looking back at my project) for whatever reason I gave up on HTMLUnit and found JSOUP much easier for my data scraping task.
 

johan313

New member
Hello Dave,

I played around with the eclusion a bit, but unfortunately I still end up with the same ClassDefNotFoundError as before (org/apache/xerces/dom/DeferredElementImpl) when i run-app. There might be something I dont understand about dependency management in GRAILS.

Is there some way to see what dependencies are actually present and who uses them? With maven and JAVA the command mvn dependency:tree was good for debugging these problems. Is there anything like that? Any other ideas are also welcome.

in my case however (just looking back at my project) for whatever reason I gave up on HTMLUnit and found JSOUP much easier for my data scraping task

Thanks for that idea, i looked into it and it seems very good. Maybe I also give up on HTMLUnit. Only problem is that there is a lot of legacy code in the JAR, and I would rather not rewrite it =)

R
Johan
 

johan313

New member
Solved the first problem (getting just HTMUnit to compile):

Code:
	compile 'net.sourceforge.htmlunit:htmlunit:2.11'{
			excludes 'xercesImpl'
		}

Tommorrow i will se how I can get rid of the transitive dependency which is still bothering my own JAR.

For some reason:
Code:
compile ('myJar:myJar:1.0.0')  {
			excludes '"xercesImpl'
		}

does not work.

Maybe i will try not loading any transitative dependencies and declaring them on a case by case basis. At least some progress...

Johan
 

dave

Administrator
Staff member
Thanks for keeping me updated, it will be useful for others who encounter the same problem.
 

johan313

New member
Whops, typo in code, this works fine (removed the ["]):

Code:
compile ('myJar:myJar:1.0.0')  {
			excludes 'xercesImpl'
		}

Well, now I end up with a new error,

Code:
Error Fatal error during compilation org.apache.tools.ant.BuildException: java.lang.NoClassDefFoundError: com/gargoylesoftware/htmlunit/html/DomElement

I wonder which library conflicts this time, any ideas? I'll call this tomorrows problem. But would appriciate ideas.

Thanks for keeping me updated, it will be useful for others who encounter the same problem.

Try to guess how many times i encountered a problem, searched the web and found other people with the same problem posting the same questions in forums, but ending the threads with "I solved this" without explaining what the solution was :p

R,
Johan
 

johan313

New member
UPDATE:

Ok, so I finally solved this, but I’m considering raising an issue on JIRA. Dependency management through ivy (in this case concerning xml-apis) is really not working as expected, or at all.

The dependency report shoved dependencies on zero sized libraries that in actually were never loaded to ivy cache or used by the class loader. Also, a transitative dependency on xml-apis was completely ignored and had to be declared explicitly (after which it was recongnized, but not loaded). In the end, I had to manually add the needed libraries and exclude their conflicting counterparts from GRAILS to get the application to work.

After some reaserch and some grails mailing lsit spamming found out that there seems to be a ticket concerning this issue, not sure however, if it is compleatly the same:
http://jira.grails.org/browse/GRAILS-9331

Will wait for release 2.1.3 and see if it works better, if not I will raise a ticket a JIRA.

Nice little “welcome to GRAILS problem”. So if someone else ever has problems getting HTMLUnit to work on GRAILS, above is the solution.

Regards,
johan
 

dave

Administrator
Staff member
Thanks for taking the time to update the thread with your results, much appreciated !
 
Top