JAXB-Vererbung, unmarshal zur Unterklasse der Marshalling-Klasse
Bin ich mit JAXB zum Lesen und schreiben von XML. Was ich will, ist die Verwendung einer base JAXB-Klasse für marshalling und eine geerbte JAXB-Klasse für das unmarshalling. Dies ermöglicht es einem sender-Java-Anwendung zum senden von XML zu einem anderen Empfänger-Java-Anwendung. Sender und Empfänger teilen sich eine gemeinsame JAXB-Bibliothek. Ich will den Empfänger zu unmarshall die XML-Daten in eine Empfänger-spezifische JAXB-Klasse, die erweitert die generische JAXB-Klasse.
Beispiel:
Dies ist die gemeinsame JAXB-Klasse, die vom sender verwendet wird.
@XmlRootElement(name="person")
public class Person {
public String name;
public int age;
}
Ist der Empfänger spezifische JAXB-Klasse verwendet, wenn unmarshalling der XML. Die receiver-Klasse enthält die Logik der spezifisch auf die receiver-Anwendung.
@XmlRootElement(name="person")
public class ReceiverPerson extends Person {
public doReceiverSpecificStuff() ...
}
Marshalling funktioniert wie erwartet. Das problem ist mit unmarshalling es noch unmarshals zu Person
trotz der JAXBContext mit dem Paket-Namen der Unterklassen ReceiverPerson
.
JAXBContext jaxbContext = JAXBContext.newInstance(package name of ReceiverPerson);
Was ich will, ist zu unmarshall zu ReceiverPerson
. Der einzige Weg, ich habe in der Lage, dies zu tun ist, zu entfernen @XmlRootElement
aus Person
. Leider tun dies verhindert, dass Person
aus gemarshallt. Es ist, als ob JAXB beginnt an der Basis-Klasse und arbeitet seinen Weg nach unten, bis es findet die erste @XmlRootElement
mit dem entsprechenden Namen. Ich habe versucht, das hinzufügen einer createPerson()
Methode gibt ReceiverPerson
zu ObjectFactory
aber das hilft nicht.
InformationsquelleAutor der Frage Steve Kuo | 2009-03-06
Du musst angemeldet sein, um einen Kommentar abzugeben.
Bist du mit JAXB 2.0 richtig? (da JDK6)
Gibt es eine Klasse:
denen man eine Unterklasse und überschreiben der folgenden Methoden:
Beispiel:
Nutzung erfolgt durch folgende Schritte:
Ich bin mir ziemlich sicher, mit diesem Konzept können Sie Steuern, das marshalling/unmarshalling-Prozess selbst (inklusive der Wahl der richtigen [sub - |super -] - Typ zu erstellen).
InformationsquelleAutor der Antwort ivan_ivanovich_ivanoff
Folgende snippet ist eine Methode von Junit 4 test mit einem grünen Licht:
Wichtig ist nur die Nutzung der
JAXBContext.newInstance(Class... classesToBeBound)
Methode für das unmarshalling Kontext:Mit diesem Ruf, JAXB berechnen einer Referenz-Verschluss auf der Klassen angegeben und erkennen
RecieverPerson
. Der test erfolgreich verläuft. Und wenn Sie die Parameter ändern, um, erhalten Sie einejava.lang.ClassCastException
(so Sie muss übergeben werden, die in dieser Reihenfolge).InformationsquelleAutor der Antwort Pascal Thivent
Unterklasse Person zweimal, einmal für den Empfänger und einmal für den Absender, und nur die XmlRootElement auf diese subclassses (verlassen der Superklasse
Person
ohne XmlRootElement). Beachten Sie, dass sender und Empfänger beide teilen sich die gleiche Basis JAXB-Klassen.[getestet und bestätigt die Arbeit mit JAXB]. Es umgeht das problem, das Sie beachten, wenn mehrere Klassen in der Vererbungshierarchie müssen den XmlRootElement-annotation.
Dies ist wohl auch ein ordentlicher und mehr OO Ansatz, denn es trennt die gemeinsame Datenmodell, so dass es nicht einen "workaround" überhaupt.
InformationsquelleAutor der Antwort 13ren
Erstellen Sie eine benutzerdefinierte ObjectFactory zur Instanziierung die gewünschte Klasse während des unmarshalling. Beispiel:
InformationsquelleAutor der Antwort vocaro
Ich bin nicht sicher, warum würden Sie wollen, dies zu tun... es scheint nicht ganz sicher zu mir.
Überlegen, was passieren würde, in ReceiverPerson hat zusätzlichen Instanz-Variablen... dann würden Sie wind mit (ich Schätze) auf diese Variablen wird null, 0 oder false... und was ist, wenn null nicht erlaubt ist oder die Zahl muss größer als 0?
Denke ich, was wollen Sie wahrscheinlich zu tun ist, Lesen Sie in der Person und dann der Bau einer neuen ReceiverPerson aus, dass (wahrscheinlich einen Konstruktor, eine Person).
InformationsquelleAutor der Antwort TofuBeer
Da wirklich zwei getrennte apps, kompilieren Sie Sie mit verschiedenen Versionen von der Klasse "Person" - mit der Empfänger-app nicht mit
@XmlRootElement(name="person")
aufPerson
. Dies ist nicht nur hässlich, aber es besiegt die Wartbarkeit Sie wollte von der Verwendung der gleichen definition von Person, die für Absender und Empfänger. Seine eine erlösende Funktion ist, dass es funktioniert.InformationsquelleAutor der Antwort 13ren