2016-06-01 29 views
0

Ich benutze Jaxb-Plugin (rg.jvnet.jaxb2.maven2), um meine Java-Klassen zu generieren. Also verwende ich xsd, das automatisch Java-Klassen generiert. Ich möchte, dass meine Lösung abstrakt ist.Jaxb -Unmarshalling der abstrakten Liste in der abstrakten Klasse

Ich habe eine XML

<RESULTS> 
    <RESULT> 
     <TOKEN>XXXXXXXXXXXXXXXXXXXXXXXXX</TOKEN> 
     <LANGUAGE>en</LANGUAGE> 
     <SEARCHTYPE>PO</SEARCHTYPE> 
    </RESULT> 
    </RESULTS> 

Später habe ich für andere Produkt gleiche XML haben, werde aber mit einem zusätzlichen NUMBER Element

<RESULTS> 
    <RESULT> 
     <TOKEN>XXXXXXXXXXXXXXXXXXXXXXXXX</TOKEN> 
     <LANGUAGE>en</LANGUAGE> 
     <SEARCHTYPE>PO</SEARCHTYPE> 
     <NUMBER>123456789</NUMBER> 
    </RESULT> 
    </RESULTS> 

Ich möchte meine Lösung als abstrakt machen. Unten ist meine Jaxb-Implementierung.

1) Meine Ergebnisklasse enthält eine Ergebnisliste. Ich habe dieses Ergebnis als BaseResult gemacht.

@XmlAccessorType(XmlAccessType.FIELD) 
    @XmlType(name = "RESULTS", propOrder = { 
     "baseresult" 
    }) 
    public class Results implements Equals2, HashCode2, ToString2 
    { 

     @XmlElement(name = "BASERESULT", required = true) 
     protected List<BaseResult> baseresult; 
    } 

2) Dies ist meine BaseResult Klasse, die gemeinsame Felder.

public abstract class BaseResult implementiert Equals2, HashCode2, ToString2 {

@XmlElement(name = "TOKEN", required = true) 
    protected String token; 
    @XmlElement(name = "LANGUAGE", required = true) 
    protected String language; 
} 

Diese meine XSD-Datei ist über Code

<xs:complexType name="RESULTS"> 
      <xs:annotation> 
       <xs:documentation> 
        Holds results tag <!-- <RESULTS></RESULTS> --> 
       </xs:documentation> 
      </xs:annotation> 
      <xs:sequence> 
       <xs:element name="BASERESULT" type="BASERESULT" maxOccurs="unbounded" /> 
      </xs:sequence> 
     </xs:complexType> 

<xs:complexType name="BASERESULT" abstract="true"> 
     <xs:annotation> 
      <xs:documentation> 
       Holds result <!-- <RESULT></RESULT> -->token , with all common elements in result tag 
      </xs:documentation> 
     </xs:annotation> 
     <xs:sequence> 
      <xs:element name="TOKEN" type="xs:string" /> 
      <xs:element ref="LANGUAGE" type="xs:string"/> 
     </xs:sequence> 
    </xs:complexType> 

3) Dies ist Kind Klasse für Ergebnis zu erzeugen, Das hat untergeordnete Felder.

@XmlAccessorType(XmlAccessType.FIELD) 
    @XmlType(name = "RESULT", propOrder = { 
     "searchType" 
    }) 
    public class Result extends BaseResult 
     implements Equals2, HashCode2, ToString2 
    { 

     @XmlElement(name = "SEARCHTYPE", required = true) 
     @XmlJavaTypeAdapter(CollapsedStringAdapter.class) 
     @XmlSchemaType(name = "NCName") 
     protected String searchType; 
    } 

Dies ist meine XSD-Datei über Code

<xs:complexType name="RESULT"> 
     <xs:complexContent> 
      <xs:extension base="BASERESULT"> 
       <xs:sequence> 
        <xs:element ref="SEARCHTYPE" type="xs:string"/> 
       </xs:sequence> 
      </xs:extension> 
     </xs:complexContent> 
    </xs:complexType> 

Die Ausgabe zu erzeugen ist, ich bin nicht in der Lage meine xml zu machen, wie oben angegeben. Es ist nicht möglich, das Ergebnis in mu xml zu füllen.

Bitte Beratung

Antwort

0

Ihr Problem aus dieser kommen:

@XmlElement(name = "BASERESULT", required = true) 
protected List<BaseResult> baseresult; 

Dies sagt, dass Sie ein BASERESULT Element in Ihrem XML zu finden sind zu erwarten.

Wechsle zu:

@XmlElement(name="result") 
protected List<BaseResult> baseresult; 

Damit werden Sie nur Ihre commons Eigenschaften erhalten (oder einen Fehler, da BaseResult abstrakt ist).

Ihr anderes Problem ist, dass Sie Karte haben, zu welcher Klasse JAXB das Element binden soll, das es findet.

Was sollte man so etwas verwenden:

@XmlElements({ 
    @XmlElement(name="result",type=Result.class), 
    @XmlElement(name="result2",type=Result2.class) 
}) 
protected List<BaseResult> baseresult; 

Das Problem ist, dass Sie das gleiche Elementname für beide Klasse verwenden. Normalerweise sollte ein XML-Element nur von einer Klasse beschrieben werden, damit JAXB die passende Klasse für die Bindung findet.

Sie sollten also in Ihrer XML-Datei für jede Klasse, die BaseResult erweitert, verschiedene Elementnamen verwenden.

Wenn Sie das nicht können, sehe ich keine Problemumgehung, mit der Sie eine abstrakte Lösung implementieren können, wie Sie möchten.