[jsword-devel] NullPointer in JSword, at runtime using the maven dependency

DM Smith dmsmith at crosswire.org
Thu Apr 22 03:33:18 MST 2010


On Apr 21, 2010, at 6:54 PM, Chris Burrell wrote:

> After some hunting and some testing, I found that this is in fact not anything to do with jsword, common or the TyndaleStep code.
> 
> Maven internally uses different Class realms, presumably to separate the different contexts in which it runs things. As a result it deals with its own ClassLoaders. Apparently Plexus which it relies on uses File.toURL() instead of File.toURI().toURL() when populating the class realms.
> 
> This is documented here: http://jira.codehaus.org/browse/MNG-3607 and apparently gets fixed in maven 3 alpha!

Whew! That makes me feel better. BTW, a significant Java difference between a URI and an URL: A URI does not have to describe something that exists but a URL always resolves it's target, going out on the network/filesystem to ensure that the object exists. Thus, using URIs is much faster.


> 
> Do you still want me to raise a defect? The easiest workaround (but affects most maven developers) is to change the settings.xml to specify the local repository as c:\docume~1\username\... The other work around would be to do a nasty url.getExternalForm().replace("%20", " "), but then all the resources across the whole of JSword would take a hit, for no other reason than it doesn't work during dev.

If the defect is expressed in JSwords poms and can be fixed then then yes, with a patch to those pom or xml files. Otherwise, it is just a learning experience for maven users on Windows. But, we may want to open an issue, describe the work around and resolve it as "Won't Fix."

I don't think that we want to have a bug work around in the code when we don't have to.

> 
> Chris
> 
> 
> On 20 April 2010 01:25, DM Smith <dmsmith at crosswire.org> wrote:
> 
> On Apr 18, 2010, at 12:31 PM, Chris Burrell wrote:
> 
>> Ok, so here's an answer to this weird problem... As DM said, it seemed to be a classpath issue, but then since NetUtils is being executed, at least part of the jar file is being found. And the maven output shows it's on the path.
>> 
>> But here's what is happening:
>> - My Maven repository is located on Windows under c:\Documents and Settings\username\.m2
>> 
>> The following method in NetUtils returns a null because a URISyntaxException is being caught
>>     public static URI toURI(URL url) {
>>         try {
>>             return new URI(url.toExternalForm());
>>         } catch (URISyntaxException e) {
>>             return null;
>>         }
>>     }
>> 
>> Now the reason for that is "Illegal character in opaque part at index 22: jar:file:/C:/Documents and"
>> 
>> That character is a space character. It seems the toExternalForm() method doesn't like the space. Perhaps because the space should probably be a %20? (haven't tried that).
> 
> Hmm. Not sure what the problem is. According to Java 1.5 the proper way to convert a URL to a URI is to call url.toURI(). This is just a wrapper for new URI(url.toString()); In both Java 1.5 and Java 1.4.2, url.toString() is just a wrapper to url.toExternalForm(), and url.toExternalForm() merely calls handler.toExternalForm(this).
> 
> The documentation clearly states that some URLs cannot be encoded via toExternalForm. And it seems that we've clearly hit that.
> 
> What frustrates me is that it appears that Java is returning an URL from the class loader that is not URL encoded.
> 
> From the RFC for URIs it says the proper way to do URL encoding is to construct an URL from parts. Each part can be encoded.
> 
>> 
>> My quick workaround is to do as suggested on this post: http://www.mail-archive.com/users@maven.apache.org/msg84160.html and rewrite my Maven settings.xml so that the local repository is at c:\Docume~1\username\.m2
>> 
>> A better solution would be to do the following to test whether we can pass a URL encoded form to the URL object above (I assume that will have quite a lot of impact so we'd need to test this quite a bit)
>> 
>> Also perhaps some logging of the exception would be nice.
>> I assume people will have the same problem if they happen to install Bible Desktop at c:\bible desktop\ because of the space (but again haven't tested)
>> 
>> Happy to try and create a patch for it, or not.
> 
> Yes please. Also create an issue in www.crosswire.org/bugs under JSword and attach your patches to it.
> 
> Many thanks.
> 
> 
>> Cheers
>> Chris :)
>> 
>> 
>> 
>> 
>> 
>> On 18 April 2010 01:43, DM Smith <dmsmith at crosswire.org> wrote:
>> I'm not to familiar with maven, but I don't think I checked in the latest poms.
>> 
>> I'm not clear as to why it would get a ClassDefNotFoundError. That sounds like a class path error.
>> 
>> -- DM
>> 
>> On Apr 17, 2010, at 1:50 PM, Chris Burrell wrote:
>> 
>>> Hi
>>> 
>>> I'm trying to get my project to compile/run against the JSword POM. I'm hitting a couple of issues (which might be related)
>>> 
>>> 1st: mvn clean install fails to retrieve a dependency, which is not very helpful. However it does seem  to build common and JSword properly. I posted a message recently on this, but there was no feedback?
>>> 
>>> 2nd, when trying to use it to install some bible versions, I get a ClassDefNotFoundError which is due to a NullPointerException in NetUtil class.
>>> 
>>> It seems that we're not forming a proper URL from:
>>>             URL index = ResourceUtil.getResource(ReadingsBookDriver.class, "readings.txt"); //$NON-NLS-1$
>>> 
>>> I'm not familiar with what the correct behaviour should be. I've checked that JAR that the Maven plugin builds, and readings.txt does indeed exist. Does anyone have any ideas?
>>> 
>>> This only happens through Maven when I run my packaged jar. When I run this through Eclipse it seems fine, which sounded to me like it be a dependency issue, but I can't figure our what the problem is...
>>> Any ideas anyone?
>>> Cheers,
>>> Chris
>>> 
>>> 
>>> Output from Maven:
>>> [DEBUG] Collected project classpath [D:\temp\release_final_test\step-dataloader\target\classes]
>>> [DEBUG] Adding to classpath : file:/D:/temp/release_final_test/step-dataloader/target/classes/
>>> [DEBUG] Adding project dependency artifact: jsword to classpath
>>> [DEBUG] Adding project dependency artifact: log4j to classpath
>>> [DEBUG] Adding project dependency artifact: jsword-common to classpath
>>> [DEBUG] Adding project dependency artifact: commons-codec to classpath
>>> [DEBUG] Adding project dependency artifact: commons-httpclient to classpath
>>> [DEBUG] Adding project dependency artifact: commons-logging to classpath
>>> [DEBUG] Adding project dependency artifact: commons-net to classpath
>>> [DEBUG] Adding project dependency artifact: oro to classpath
>>> [DEBUG] Adding project dependency artifact: javatar to classpath
>>> [DEBUG] Adding project dependency artifact: jdom to classpath
>>> [DEBUG] Adding project dependency artifact: lucene-core to classpath
>>> [DEBUG] Adding project dependency artifact: lucene-snowball to classpath
>>> [DEBUG] Adding project dependency artifact: lucene-smartcn to classpath
>>> [DEBUG] Adding project dependency artifact: lucene-analyzers to classpath
>>> [DEBUG] Adding project dependency artifact: commons-dbutils to classpath
>>> [DEBUG] Adding project dependency artifact: commons-io to classpath
>>> [DEBUG] Adding project dependency artifact: commons-lang to classpath
>>> [DEBUG] Adding project dependency artifact: opencsv to classpath
>>> [DEBUG] Adding project dependency artifact: derbyclient to classpath
>>> [DEBUG] Adding project dependency artifact: derby to classpath
>>> [DEBUG] joining on thread Thread[com.tyndalehouse.step.dataloader.Dataloader.main(),5,com.tyndalehouse.step.dataloader.Dataloader]
>>> [DEBUG] Setting accessibility to true in order to invoke main().
>>> Using connection string: jdbc:derby:C:\Documents and Settings\CJBurrell/TyndaleStep/StepDB;create=true
>>> 0    [com.tyndalehouse.step.dataloader.Dataloader.main()] WARN  com.tyndalehouse.step.dataloader.loaders.JSwordModuleInstaller  - Creating new installer for JSw
>>> ord
>>> Currently hardcoded installer host to:www.crosswire.org
>>> Currently hardcoded property names for step
>>> Setting to (www.crosswire.org via 10.154.1.44:8080)
>>> Setting package and catalog directories
>>> 641  [com.tyndalehouse.step.dataloader.Dataloader.main()] INFO  com.tyndalehouse.step.dataloader.loaders.JSwordModuleInstaller  - installing ESV
>>> [INFO] ------------------------------------------------------------------------
>>> [ERROR] BUILD ERROR
>>> [INFO] ------------------------------------------------------------------------
>>> [INFO] An exception occured while executing the Java class. null
>>> 
>>> [INFO] ------------------------------------------------------------------------
>>> [DEBUG] Trace
>>> org.apache.maven.lifecycle.LifecycleExecutionException: An exception occured while executing the Java class. null
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeGoals(DefaultLifecycleExecutor.java:719)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeStandaloneGoal(DefaultLifecycleExecutor.java:569)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeGoal(DefaultLifecycleExecutor.java:539)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeGoalAndHandleFailures(DefaultLifecycleExecutor.java:387)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeTaskSegments(DefaultLifecycleExecutor.java:348)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.execute(DefaultLifecycleExecutor.java:180)
>>>         at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:328)
>>>         at org.apache.maven.DefaultMaven.execute(DefaultMaven.java:138)
>>>         at org.apache.maven.cli.MavenCli.main(MavenCli.java:362)
>>>         at org.apache.maven.cli.compat.CompatibleMain.main(CompatibleMain.java:60)
>>>         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.codehaus.classworlds.Launcher.launchEnhanced(Launcher.java:315)
>>>         at org.codehaus.classworlds.Launcher.launch(Launcher.java:255)
>>>         at org.codehaus.classworlds.Launcher.mainWithExitCode(Launcher.java:430)
>>>         at org.codehaus.classworlds.Launcher.main(Launcher.java:375)
>>> Caused by: org.apache.maven.plugin.MojoExecutionException: An exception occured while executing the Java class. null
>>>         at org.codehaus.mojo.exec.ExecJavaMojo.execute(ExecJavaMojo.java:338)
>>>         at org.apache.maven.plugin.DefaultPluginManager.executeMojo(DefaultPluginManager.java:490)
>>>         at org.apache.maven.lifecycle.DefaultLifecycleExecutor.executeGoals(DefaultLifecycleExecutor.java:694)
>>>         ... 17 more
>>> Caused by: java.lang.reflect.InvocationTargetException
>>>         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.codehaus.mojo.exec.ExecJavaMojo$1.run(ExecJavaMojo.java:283)
>>>         at java.lang.Thread.run(Thread.java:619)
>>> Caused by: java.lang.ExceptionInInitializerError
>>>         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.crosswire.jsword.book.Books.autoRegister(Books.java:426)
>>>         at org.crosswire.jsword.book.Books.initialize(Books.java:407)
>>>         at org.crosswire.jsword.book.Books.<init>(Books.java:59)
>>>         at org.crosswire.jsword.book.Books.<clinit>(Books.java:473)
>>>         at com.tyndalehouse.step.dataloader.loaders.JSwordModuleInstaller.installBible(JSwordModuleInstaller.java:46)
>>>         at com.tyndalehouse.step.dataloader.loaders.JSwordModuleInstaller.installDefaultModules(JSwordModuleInstaller.java:33)
>>>         at com.tyndalehouse.step.dataloader.Dataloader.main(Dataloader.java:33)
>>>         ... 6 more
>>> Caused by: java.lang.NullPointerException
>>>         at org.crosswire.common.util.NetUtil.getInputStream(NetUtil.java:415)
>>>         at org.crosswire.common.util.NetUtil.listByIndexFile(NetUtil.java:544)
>>>         at org.crosswire.jsword.book.readings.ReadingsBookDriver.getInstalledReadingsSets(ReadingsBookDriver.java:91)
>>>         at org.crosswire.jsword.book.readings.ReadingsBookDriver.<init>(ReadingsBookDriver.java:50)
>>>         at org.crosswire.jsword.book.readings.ReadingsBookDriver.<clinit>(ReadingsBookDriver.java:119)
>>> 
>>> 
>>> my dependencies:
>>> <dependency>
>>> 				<groupId>org.crosswire</groupId>
>>> 				<artifactId>jsword</artifactId>
>>> 				<version>1.6.1-SNAPSHOT</version>
>>> </dependency>
>>> 
>>> My plugin to run the jar:
>>> 
>>> 		<plugins>
>>> 			<plugin>
>>> 				<groupId>org.codehaus.mojo</groupId>
>>> 				<artifactId>exec-maven-plugin</artifactId>
>>> 				<configuration>
>>> 					<mainClass>com.tyndalehouse.step.dataloader.Dataloader</mainClass>
>>> 					<systemProperties>
>>> 						<systemProperty>
>>> 							<key>db.location</key>
>>> 							<value>${db.directory}</value>
>>> 						</systemProperty>
>>> 						<systemProperty>
>>> 							<key>step.http.proxy</key>
>>> 							<value>${step.http.proxy}</value>
>>> 						</systemProperty>
>>> 						<systemProperty>
>>> 							<key>step.http.port</key>
>>> 							<value>${step.http.port}</value>
>>> 						</systemProperty>
>>> 					</systemProperties>
>>> 					<classpathScope>runtime</classpathScope>
>>> 				</configuration>
>>> 			</plugin>
>>> 
>>> 
>>> _______________________________________________
>>> jsword-devel mailing list
>>> jsword-devel at crosswire.org
>>> http://www.crosswire.org/mailman/listinfo/jsword-devel
>> 
>> 
> 
> 

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.crosswire.org/pipermail/jsword-devel/attachments/20100422/4540efee/attachment-0001.html>


More information about the jsword-devel mailing list