# JAXB NullPointerException im ContextFinder



## Jimbo84 (21. Mai 2010)

Hi zusammen! Ich habe da ein Problem, welches ich mir absolut nicht erklären kann.
Ich arbeite an einem Converter, welcher xml Nachrichten in ein für die verwendete Event Processing Engine (Sybase Aleri) lesbares Format umbaut. Die Methode ist simpel. Über xjc habe ich die Klassen ausgehend von einem xsd Schema gebaut.

Lese ich nun xml Nachrichten in meiner eclipse umgebung ein funktioniert das ganze wunderbar. Baue ich mir jedoch ein jar, lege es wie in der Dokumentation von Aleri beschrieben in den Classpath und benutze den Converter bekomme ich folgende Exception:


```
java.lang.NullPointerException
	at javax.xml.bind.ContextFinder.find(ContextFinder.java:269)
	at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:412)
	at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:375)
	at javax.xml.bind.JAXBContext.newInstance(JAXBContext.java:279)
	at slipstream.converters.BpafToAleriConverter.parse(Unknown Source)
	at slipstream.converters.BpafToAleriConverter.externalToAleri(Unknown Source)
	at com.aleri.connectors.JmsConnector.customMessageToStringArray(JmsConnector.java:584)
	at com.aleri.connectors.JmsConnector.receiveCustomMessage(JmsConnector.java:547)
```


der Aufruf findet wie folgt statt, wobei Event die zu Deserialisierende Klasse ist:

```
...

			String packageName = Event.class.getPackage().getName();

                        //HIER KNALLTS
			JAXBContext jc = JAXBContext.newInstance(packageName);
			
			Unmarshaller u = jc.createUnmarshaller();

                        ...
```

Ich habe mir die JAXB Quellen mal angeschaut und gesehen, dass ich das Problem umgehen könnte, wenn ich den in der ContextFinder.find() Methode ermittelten JAXBContext über die jaxb.properties definiere oder aber über eine 'system property' übergebe. 

*Warum tritt die NPE auf? Kann mir jemand sagen, wie genau ich das Problem umgehen kann?*

system property wird dabei wie folgt ermittelt, sagt mir allerdings nicht viel:

```
// search for a system property second (javax.xml.bind.JAXBContext)
        factoryClassName = AccessController.doPrivileged(new GetPropertyAction(jaxbContextFQCN));
        if(  factoryClassName != null ) {
            return newInstance( contextPath, factoryClassName, classLoader, properties );
        }
```


Der für die NullPointerException verantwortliche Codeblock sieht wie folgt aus:

```
// search META-INF services next
        BufferedReader r;
        try {
            final StringBuilder resource = new StringBuilder().append("META-INF/services/").append(jaxbContextFQCN);
            final InputStream resourceStream =  
                    classLoader.getResourceAsStream(resource.toString()); // HIER TRITT DIE NPE AUF
            
            if (resourceStream != null) {
            ...
```



Ich hoffe mal, dass ich alle notwendigen Informationen drin hab. Bin für jede Hilfe dankbar! Bisher war meine Suche vergebens. 

Grüße, Jimbo


----------



## Noctarius (21. Mai 2010)

Vermutlich (jetzt geraten) ist das Problem, dass getName nicht den Canonical Path sondern einfach nur den Namen des Packages ausgibt.


----------



## CHE123 (22. Mai 2010)

hi,

versuch


```
...
  String packageName = Event.class.getPackage().getName();
  packageName = packageName.replace('.', '/');
  ...
```

g,
Christian


----------



## Jimbo84 (23. Mai 2010)

@Noctarius Wie genau hab ich das zu verstehen? Bzw. wie würde denn der kanonische Pfad aussehen? Ich find nur was über Dateisystempfade für I/O 

@CHE123 Hat leider nicht funktioniert, Fehler bleibt gleich. Danke trotzdem für den Tipp!


----------



## Noctarius (23. Mai 2010)

Canonical Path ist der komplette Pfad.

Beispiel einer Klasse:
Klasse getName() => Foo
Klasse getCanonicalName() => com.example.my.classes.Foo

Soweit ich mich erinnere wird JAXB den Canonical Path brauchen, ich denke aber, dass Package.getName() nur den eigenen Packagenamen wiedergibt, aber nicht den kompletten Package Path.
Weißt du denn eine Klasse des Context-Pfades aus der du dir den Canonical Path holen kannst?


----------



## Jimbo84 (23. Mai 2010)

Das ist es leider auch nicht. Habs so verändert:

```
String packageName = Event.class.getPackage().getName();
			writeLine(packageName);
			JAXBContext jc;
			//try to get the Context with dots
			try {
				writeLine("First try: "+packageName);
				jc = JAXBContext.newInstance(packageName);
			} catch (NullPointerException ex){
				//looks like this didnt work, so lets try to retrieve it with slashes
			}
			packageName = packageName.replace('.', '/');
			writeLine("Second try: "+packageName);
			jc = JAXBContext.newInstance(packageName);
```


und bekomme in mein Log folgendes geschrieben, gefolgt von der genannten NPE in der letzten Codezeile:
Sun May 23 13:31:38 UTC 2010 - slipstream.xml.domain
Sun May 23 13:31:38 UTC 2010 - First try: slipstream.xml.domain
Sun May 23 13:31:38 UTC 2010 - Second try: slipstream/xml/domain


----------



## Noctarius (23. Mai 2010)

Vielleicht liegen die JAXB Klassen nicht wirklich da? Ist Event denn eine von den Klassen?


----------

