2013-08-30 1 views
1

J'essaie d'utiliser l'implémentation JAXB pour convertir mes objets de classe en XML et vice versa. J'ai implémenté ceci en observant un tutoriel.Implémentation de JAXB sans classes POJO et avec linkedHashmaps

Mon XML ressemble à ceci

<Alphabet> 
    <a>Apple</a> 
    <b>Ball</b> 
    <c>Cat</c> 
    <d>Dog</d> 
    <e>Elephant</e> 
    <f>Fox</f> 
</Alphabet> 

j'ai écrit les classes suivantes

import java.util.LinkedHashMap; 
import java.util.Map.Entry; 
import java.util.Set; 

public class Alph { 

    @XmlElement 
    private LinkedHashMap<String, String> cLinkedHashMap = new 
      LinkedHashMap<String, String>(); 

    protected void put(String theKey, String theValue) { 
     cLinkedHashMap.put(theKey, theValue); 
    } 

    protected String get(String theKey) { 
     return (String) cLinkedHashMap.get(theKey); 
    } 

    protected Set<Entry<String,String>> getCEntrySet() { 
     return cLinkedHashMap.entrySet(); 
    } 

    protected LinkedHashMap<String, String> getCLinkedHashMap() { 
     return cLinkedHashMap; 
    } 

    public String toCXML() throws XMLHandlingException { 
     return null; 
    } 

} 

@XmlRootElement 
public class Alphabet extends Alph { 

    public static Alphabet getInstance(String theAlphabetXML) throws 
    XMLHandlingException { 
     return XMLUtils.parseAlphabetXML(theAlphabetXML); 
    } 

    public String toCXML() throws XMLHandlingException { 
     return XMLUtils.getAlphabetXML(this); 
    } 

} 

J'ai créé les méthodes utilitaires XMLUtil suivantes pour permettre le rassemblement et unmarshalling

public static String getAlphabetXML(Alph theAlphabet) throws XMLHandlingException { 
    ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); 
    Writer writer = null; 
    try { 
     writer = new OutputStreamWriter(byteArrayOutputStream, "UTF-8"); 
    } catch (UnsupportedEncodingException e) { 
     e.printStackTrace(); 
    } 

    try { 
     writer.write("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>"); 
    } catch (IOException e) { 
     e.printStackTrace(); 
    } 

    try { 
     JAXBContext JContext = JAXBContext.newInstance(Alphabet.class); 
     Marshaller JMarshaller = JContext.createMarshaller(); 
     JMarshaller.marshal(theAlphabet, writer); 
    } catch (Throwable e) { 
     e.printStackTrace(); 
    } 

    String theAlphabetXML = byteArrayOutputStream.toString(); 
    return theAlphabetXML; 
} 

public static Alphabet parseAlphabetXML(String theAlphabetXML) throws 
XMLHandlingException { 

    if(null == theAlphabetXML) { 
     return null; 
    } 
    try { 
     InputStream IPStream = new ByteArrayInputStream(theALphabetXML.getBytes()); 
     JAXBContext JContext = JAXBContext.newInstance(Alphabet.class); 
     Unmarshaller JUnmarshaller = JContext.createUnmarshaller(); 
     Alphabet alphabet = (Alphabet) JUnmarshaller.unmarshal(IPStream); 
     return alphabet; 
    } catch(Throwable t) { 
     t.printStackTrace(); 
    } 
} 

Mon problème est que lorsque jamais j'essaye de marécher ou de marmotter je reçois l'erreur follower "javax.xml.bind.UnmarshalException: élément inattendu (a:" ", local:" Alphabet "). éléments attendus sont < {} Alphabet> »

Ai-je raté quelque chose? Toute aide est appréciée.

Merci


Mise à jour


Je suivais http://blog.bdoughan.com/2013/06/moxys-xmlvariablenode-using-maps-key-as.html et mis à jour mon code comme suit

demande et la réponse XML

<AlphabetReq> 
    <a>Apple</a> 
    <b>Ball</b> 
    <c>Cat</c> 
    <d>Dog</d> 
    <e>Elephant</e> 
    <f>Fox</f> 
</AlphabetReq> 

<AlphabetResp> 
    <a>Apple</a> 
    <b>Ball</b> 
    <c>Cat</c> 
    <d>Dog</d> 
    <e>Elephant</e> 
    <f>Fox</f> 
</AlphabetResp> 

AlphabetReq et les classes AlphabetResp

import java.util.LinkedHashMap; 
import java.util.Map.Entry; 
import java.util.Set; 
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter; 
import org.eclipse.persistence.oxm.annotations.XmlPath; 

@XmlRootElement 
@XmlAccessorType(XmlAccessType.FIELD) 
public class Alph { 

@XmlPath(".") 
@XmlJavaTypeAdapter(AlphAdapter.class) 
private LinkedHashMap<String, String> cLinkedHashMap = new 
     LinkedHashMap<String, String>(); 

@XmlPath(".") 
@XmlJavaTypeAdapter(AlphAdapter.class) 
private LinkedHashMap<String, String> gLinkedHashMap = new 
     LinkedHashMap<String, String>(); 

protected void put(String theKey, String theValue) { 
    cLinkedHashMap.put(theKey, theValue); 
    gLinkedHashMap.put(theKey, theValue); 
} 

protected String get(String theKey) { 
    return (String) cLinkedHashMap.get(theKey); 
} 

protected Set<Entry<String,String>> getCEntrySet() { 
    return cLinkedHashMap.entrySet(); 
} 

protected Set<Entry<String,String>> getGEntrySet() { 
    return gLinkedHashMap.entrySet(); 
} 

protected LinkedHashMap<String, String> getCLinkedHashMap() { 
    return cLinkedHashMap; 
} 

protected LinkedHashMap<String, String> getGLinkedHashMap() { 
    return gLinkedHashMap; 
} 

public String toCXML() throws XMLHandlingException { 
    return null; 
} 

public String toGXML() throws XMLHandlingException { 
    return null; 
} 

} 

@XmlRootElement(name="AlphReq") 
@XmlDiscriminatorValue("AlphabetReq") 
@XmlAccessorType(XmlAccessType.FIELD) 
public class AlphabetReq extends Alph { 

public static AlphabetReq getInstance(String theAlphabetReqXML) throws 
XMLHandlingException { 
    return XMLUtils.parseAlphabetReqXML(theAlphabetReqXML); 
} 

public String toCXML() throws XMLHandlingException { 
    return XMLUtils.getAlphabetReqXML(this); 
} 

} 

@XmlRootElement(name="AlphResp") 
@XmlDiscriminatorValue("AlphabetResp") 
@XmlAccessorType(XmlAccessType.FIELD) 
public class AlphabetResp extends Alph { 

public static AlphabetResp getInstance(String theAlphabetRespXML) throws 
XMLHandlingException { 
    return XMLUtils.parseAlphabetRespXML(theAlphabetRespXML); 
} 

public String toCXML() throws XMLHandlingException { 
    return XMLUtils.getAlphabetRespXML(this); 
} 

} 

J'ai créé les éléments suivants utilitaires XMLUtil méthodes de triage et unmarshalling

public static String getAlphabetReqXML(Alph theAlphabet) throws XMLHandlingException { 

ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); 
Writer writer = null; 

try { 
    writer = new OutputStreamWriter(byteArrayOutputStream, "UTF-8"); 
} catch (UnsupportedEncodingException e) { 
    e.printStackTrace(); 
} 

try { 
    writer.write("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>"); 
} catch (IOException e) { 
    e.printStackTrace(); 
} 

try { 
    JAXBContext JContext = JAXBContext.newInstance(AlphabetReq.class); 
    Marshaller JMarshaller = JContext.createMarshaller(); 
    JMarshaller.marshal(theAlphabet, writer); 
} catch (Throwable e) { 
    e.printStackTrace(); 
} 

String theAlphabetReqXML = byteArrayOutputStream.toString(); 
return theAlphabetReqXML; 

} 

public static AlphabetReq parseAlphabetReqXML(String theAlphabetReqXML) throws 
XMLHandlingException { 

if(null == theAlphabetReqXML) { 
    return null; 
} 
try { 
    InputStream IPStream = new ByteArrayInputStream(theAlphabetReqXML.getBytes()); 
    JAXBContext JContext = JAXBContext.newInstance(AlphabetReq.class); 
    Unmarshaller JUnmarshaller = JContext.createUnmarshaller(); 
    AlphabetReq alphabetreq = (AlphabetReq) JUnmarshaller.unmarshal(IPStream); 
    return alphabetreq; 
} catch(Throwable t) { 
    t.printStackTrace(); 
} 
} 

public static String getAlphabetRespXML(Alph theAlphabet) throws XMLHandlingException { 

ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); 
Writer writer = null; 

try { 
    writer = new OutputStreamWriter(byteArrayOutputStream, "UTF-8"); 
} catch (UnsupportedEncodingException e) { 
    e.printStackTrace(); 
} 

try { 
    writer.write("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>"); 
} catch (IOException e) { 
    e.printStackTrace(); 
} 

try { 
    JAXBContext JContext = JAXBContext.newInstance(AlphabetResp.class); 
    Marshaller JMarshaller = JContext.createMarshaller(); 
    JMarshaller.marshal(theAlphabet, writer); 
} catch (Throwable e) { 
    e.printStackTrace(); 
} 

String theAlphabetRespXML = byteArrayOutputStream.toString(); 
return theAlphabetRespXML; 

} 

public static AlphabetResp parseAlphabetReqXML(String theAlphabetRespXML) throws 
XMLHandlingException { 

if(null == theAlphabetRespXML) { 
    return null; 
} 
try { 
    InputStream IPStream = new ByteArrayInputStream(theAlphabetRespXML.getBytes()); 
    JAXBContext JContext = JAXBContext.newInstance(AlphabetResp.class); 
    Unmarshaller JUnmarshaller = JContext.createUnmarshaller(); 
    AlphabetResp alphabetresp = (AlphabetResp) JUnmarshaller.unmarshal(IPStream); 
    return alphabetresp; 
} catch(Throwable t) { 
    t.printStackTrace(); 
} 
} 

et introduit une classe d'adaptateur

import java.util.*; 
import java.util.Map.Entry; 
import javax.xml.bind.annotation.*; 
import javax.xml.bind.annotation.adapters.XmlAdapter; 
import org.eclipse.persistence.oxm.annotations.XmlVariableNode; 

public class AlphAdapter extends XmlAdapter<AlphAdapter.AdaptedMap, LinkedHashMap<String, String>>{ 

public static class AdaptedMap { 
    @XmlVariableNode("key") 
    List<AdaptedEntry> entries = new ArrayList<AdaptedEntry>(); 
} 

public static class AdaptedEntry { 
    @XmlTransient 
    public String key; 

    @XmlValue 
    public String value; 
} 

@Override 
public AdaptedMap marshal(LinkedHashMap<String, String> map) throws Exception { 
    AdaptedMap adaptedMap = new AdaptedMap(); 
    for(Entry<String, String> entry : map.entrySet()) { 
     AdaptedEntry adaptedEntry = new AdaptedEntry(); 
     adaptedEntry.key = entry.getKey(); 
     adaptedEntry.value = entry.getValue(); 
     adaptedMap.entries.add(adaptedEntry); 
    } 
    return adaptedMap; 
} 

@Override 
public LinkedHashMap<String, String> unmarshal(AdaptedMap adaptedMap) throws Exception { 
    List<AdaptedEntry> adaptedEntries = adaptedMap.entries; 
    LinkedHashMap<String, String> map = new LinkedHashMap<String, String>(adaptedEntries.size()); 
    for(AdaptedEntry adaptedEntry : adaptedMap.entries) { 
     map.put(adaptedEntry.key, adaptedEntry.value); 
    } 
    return map; 
} 
} 

Lorsque j'exécute cela, je n'obtiens aucune valeur dans ma carte adaptée. il a des touches mais des valeurs que null par ex:

  • clé: A, valeur: null
  • clé: B, valeur: null
  • clé: C, valeur: null
  • clé
  • : D , valeur: null
  • clé: E, valeur: null
  • clé: F, valeur: null

Toute aide est appréciée.

Merci

+0

'catch (Throwable e) {return null; } '- ne fais pas ça. Cela rendra le débogage impossible – artbristol

+2

Ce qui suit peut être ce que vous cherchez: http://blog.bdoughan.com/2013/06/moxys-xmlvariablenode-using-maps-key-as.html –

+0

Bonjour @BlaiseDoughan, j'ai suivi votre lien et mis à jour mon code, il commet des erreurs. Toute aide est appréciée. merci – kvbrahmam

Répondre

1

Vous pouvez réaliser cette simple création XML (que vous avez donné) comme ci-dessous:

@XmlRootElement 
public class Alphabet { 
    private String a; 
    private String b; 
    private String c; 
    private String d; 
    private String e; 
    private String f; 

    public Alphabet() { 

    } 

    public Alphabet(String a, String b, String c, String d, String e, String f) { 
     super(); 
     this.a = a; 
     this.b = b; 
     this.c = c; 
     this.d = d; 
     this.e = e; 
     this.f = f; 
    } 

    public String getA() { 
     return a; 
    } 

    public void setA(String a) { 
     this.a = a; 
    } 

    public String getB() { 
     return b; 
    } 

    public void setB(String b) { 
     this.b = b; 
    } 

    public String getC() { 
     return c; 
    } 

    public void setC(String c) { 
     this.c = c; 
    } 

    public String getD() { 
     return d; 
    } 

    public void setD(String d) { 
     this.d = d; 
    } 

    public String getE() { 
     return e; 
    } 

    public void setE(String e) { 
     this.e = e; 
    } 

    public String getF() { 
     return f; 
    } 

    public void setF(String f) { 
     this.f = f; 
    } 

} 

Cette classe est de créer le fichier xml:

public class AlphabetToXML { 
    public static void main(String[] args) { 
     Alphabet alpha = new Alphabet("Apple", "Ball", "Cat", "Dog", 
       "Elephant", "Fox"); 
     try { 
      String filePath = "PATH_TO_SAVE_YOUR_FILE"; 
      File file = new File(filePath); 
      JAXBContext jaxbContext = JAXBContext.newInstance(Alphabet.class); 
      Marshaller jaxbMarshaller = jaxbContext.createMarshaller(); 

      // output pretty printed 
      jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); 

      jaxbMarshaller.marshal(alpha, file); 
      jaxbMarshaller.marshal(alpha, System.out); 
     } catch (JAXBException e) { 
      e.printStackTrace(); 
     } 
    } 
} 

Et ce est de lire votre XML vers l'objet Java:

public class XMLToAplhabet { 
    public static void main(String[] args) { 
     try { 
      String filePath = "XML_FILE_PATH"; 
      File file = new File(filePath); 
      JAXBContext jaxbContext = JAXBContext.newInstance(Alphabet.class); 

      Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller(); 
      Alphabet aplha = (Alphabet) jaxbUnmarshaller.unmarshal(file); 
      System.out.println(aplha); 
     } catch (JAXBException e) { 
      e.printStackTrace(); 
     } 
    } 
} 

Je ne vois aucune utilisation de LinkedHashMap pour créer un simple XML comme celui-ci.

+0

Bonjour Debojit Saikia, Désolé Dans ma question j'ai donné un exemple XML, Mon XML va avoir beaucoup d'éléments sous la racine . Je ne pense pas que la mise en œuvre ci-dessus va fonctionner. Merci – kvbrahmam

+0

+1 - BTW, j'ai supprimé les annotations inutiles '@ XmlElement'. –

+0

Est-il possible pour vous de donner un exemple de votre fichier XML? Cela vous aidera à obtenir des réponses correctes. Merci. –

Questions connexes