I create an java class:
public class ReturnObj {
private String returncode;
private String returndesc;
private Pkg pkg;
public String getReturncode() {
return returncode;
}
public void setReturncode(String returncode) {
this.returncode = returncode;
}
public String getReturndesc() {
return returndesc;
}
public void setReturndesc(String returndesc) {
this.returndesc = returndesc;
}
}
and other class:
public class Pkg {
private String packagecode;
private String cycle;
private String price;
private String desc;
public String getPackagecode() {
return packagecode;
}
public void setPackagecode(String packagecode) {
this.packagecode = packagecode;
}
public String getCycle() {
return cycle;
}
public void setCycle(String cycle) {
this.cycle = cycle;
}
public String getPrice() {
return price;
}
public void setPrice(String price) {
this.price = price;
}
public String getDesc() {
return desc;
}
public void setDesc(String desc) {
this.desc = desc;
}
}
And I Want to convert object ReturnObj to this XML
<return>
<returncode>1</returncode>
<returndesc>DANG_KY_THANH_CONG</returndesc>
<package>
<packagecode>BD30</packagecode>
<cycle>1</cycle>
<price>15000</price>
<desc> BD30</desc>
</package>
</return>
So how do I serialize an attribute pkg to package in XML? Because Java doesn't allow to name variable as an keyword anh package is an keyword in Java !
You can use JAXB marshling in your class it will convert the object to XML, here is link to help you JAXB Marshling
Try xstream
XStream xstream = new XStream();
xstream.alias("package", Pkg.class);
String xml = xstream.toXML(myReturnObj);
You can use JAXB API that comes with java for converting java object to XML.
Below is the code that will solve your requirement.
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;
#XmlRootElement(name = "return")
public class ReturnObj {
private String returncode;
private String returndesc;
private Pkg pkg;
public Pkg getPkg() {
return pkg;
}
#XmlElement(name = "package")
public void setPkg(Pkg pkg) {
this.pkg = pkg;
}
public String getReturncode() {
return returncode;
}
#XmlElement(name = "returncode")
public void setReturncode(String returncode) {
this.returncode = returncode;
}
public String getReturndesc() {
return returndesc;
}
#XmlElement(name = "returndesc")
public void setReturndesc(String returndesc) {
this.returndesc = returndesc;
}
}
#XmlRootElement
public class Pkg {
private String packagecode;
private String cycle;
private String price;
private String desc;
public String getPackagecode() {
return packagecode;
}
#XmlElement(name="packagecode")
public void setPackagecode(String packagecode) {
this.packagecode = packagecode;
}
public String getCycle() {
return cycle;
}
#XmlElement(name="cycle")
public void setCycle(String cycle) {
this.cycle = cycle;
}
public String getPrice() {
return price;
}
#XmlElement(name="price")
public void setPrice(String price) {
this.price = price;
}
public String getDesc() {
return desc;
}
#XmlElement
public void setDesc(String desc) {
this.desc = desc;
}
}
import java.io.File;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;
public class JAXBExample {
private static final String FILE_NAME = "C:\\ru\\jaxb-returnObj.xml";
public static void main(String[] args) {
ReturnObj returnObj = new ReturnObj();
returnObj.setReturncode("1");
returnObj.setReturndesc("DANG_KY_THANH_CONG");
Pkg pkg = new Pkg();
pkg.setCycle("1");
pkg.setPrice("15000");
pkg.setDesc("BD30");
returnObj.setPkg(pkg);
jaxbObjectToXML(returnObj);
}
private static void jaxbObjectToXML(ReturnObj emp) {
try {
JAXBContext context = JAXBContext.newInstance(ReturnObj.class);
Marshaller m = context.createMarshaller();
// for pretty-print XML in JAXB
m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
// Write to System.out, this will print the xml on console
m.marshal(emp, System.out);
// Write to File
m.marshal(emp, new File(FILE_NAME));
} catch (JAXBException e) {
e.printStackTrace();
}
}
}
Explanation:
#XmlRootElement: This is a must have annotation for the Object to be used in JAXB. It defines the root element for the XML content.
#XmlElement: This will create the element. If you want to give some other name to the xml element when converting java object to xml then you can pass name attribute to the #XmlElement Example:
#XmlElement(name = "package")
Execute above code to see the desired output.
Happy Coding.
Related
How to convert java object to xml using JAXB to get the following xml:
<Case>
<Version>1.0</Version>
<Code>457123</Code>
<Meta uc=\"Sample\" pip=\"116.0.1.1\" lot=\"P\"/>
</Case>
There are many answers regarding how to get XML. I have gone through all those. But my question is how to get the XML as what I have shown. It contains a self-closing tag which even contains attributes.
I am using Eclipse IDE. Please suggest a method.
This is my case class:
import auth.Res.Meta;
#XmlRootElement (name="Case")
public class Test {
private Meta mt;
private String version;
private String code;
#XmlRootElement
public class Meta {
#XmlAttribute
private String uc;
#XmlAttribute
private String pip;
public String getUc() {
return uc;
}
public void setUc(String uc) {
this.uc = uc;
}
public String getPip() {
return pip;
}
public void setPip(String pip) {
this.pip = pip;
}
}
public Meta getMt() {
return mt;
}
public void setMt(Meta mt) {
this.mt = mt;
}
public String getVersion() {
return version;
}
public void setVersion(String version) {
this.version = version;
}
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
}
Solution:
I solved it by creating seperate class for Meta as suggested by LazerBanana in the first answer.
This is how your Meta class should look like.
public class Meta {
private String uc;
private String pip;
private String lot;
public String getUc() {
return uc;
}
#XmlAttribute
public void setUc(String uc) {
this.uc = uc;
}
public String getPip() {
return pip;
}
#XmlAttribute
public void setPip(String pip) {
this.pip = pip;
}
public String getLot() {
return lot;
}
#XmlAttribute
public void setLot(String lot) {
this.lot = lot;
}
}
this is your Case class which is the root element
#XmlRootElement
public class Case {
private int version;
private String code;
private String id;
private Meta meta;
public int getVersion() {
return version;
}
#XmlElement
public void setVersion(int version) {
this.version = version;
}
public String getCode() {
return code;
}
#XmlElement
public void setCode(String code) {
this.code = code;
}
public String getId() {
return id;
}
#XmlElement
public void setId(String id) {
this.id = id;
}
public Meta getMeta() {
return meta;
}
#XmlElement
public void setMeta(Meta meta) {
this.meta = meta;
}
}
And this is the marshaling bit to the console and to the file it you want.
public class Main {
public static void main(String... args) {
Case fcase = new Case();
Meta meta = new Meta();
meta.setLot("asd");
meta.setPip("sdafa");
meta.setUc("asgd4");
fcase.setMeta(meta);
fcase.setVersion(1);
fcase.setId("sah34");
fcase.setCode("code34");
try {
// File file = new File("C:\\file.xml");
JAXBContext jaxbContext = JAXBContext.newInstance(Case.class, Meta.class);
Marshaller jaxbMarshaller = jaxbContext.createMarshaller();
// output pretty printed
jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
// jaxbMarshaller.marshal(fcase, file);
jaxbMarshaller.marshal(fcase, System.out);
} catch (JAXBException e) {
e.printStackTrace();
}
}
}
Output:
<case>
<code>code34</code>
<id>sah34</id>
<meta lot="asd" pip="sdafa" uc="asgd4"/>
<version>1</version>
</case>
Next time please try to do more research i am not an expert and I just googled it.
https://www.mkyong.com/java/jaxb-hello-world-example/
i need to create a rest service which accepts xml of format i have gien. Thats y i need it in a single class.
#POST
#Path("/add")
#Consumes("application/xml")
#Produces("application/xml")
public Response getper(Test test)
{
String nam=test.getVersion();
int cd=test.getCode();
Res rs=new Res();
rs.setMessage(nam);
.
.
return Response.status(200).entity(rs).build();
}
i have an XML document that have some configuration information i have to access the information from a java class.I am able to access the information using java unmarshalling,but the problem is that i can not access a specific portion of the xml file.Every time i am accessing the information i have to take the root tag first i.e i only can access the root tag elements,but i need to access the tag that is in the another section.This is my XML file
<?xml version="1.0" encoding="UTF-8"?>
<adapter name="Hua_GPRS_CS5_4.7" type="ASN.1" version="1.0" description="Huawie GPRS Output CDR Version 4.7"
execclass="hua.gprs.HuaGPRSFileExecutor" parallel="1" mode="server" statusfile="HuaGPRSStatus.csv" merge_factor="1" active="true">
<dirconfig>
<Poll protocol="" host="" path="./data/huagprs/source" pwd="" user="" clogging="true" startdir="" enddir=""
pattern="(.*)\.(\d{6})(\d{6})(\d{4})_(.*)" metafields="fileName,exchange,fileDate,fileTime,fileSeq,junk"/>
<Source path="./data/huagprs/source" clogging="false"/>
<Backup path="./data/huagprs/backup" active="false"/>
<Staging path="./data/huagprs/staging" clogging="false"/>
<Output path="./data/huagprs/output" clogging="false" compress="gz"/>
<Error path="./data/huagprs/error" clogging="true"/>
<Target protocol="" host="" path="/" pwd="" user="" active="true"/>
</dirconfig>
<dbConf id="1" name ="jjj" drivername="oracle.jdbc.driver.OracleDriver" hostname="localhost" portname="1521" dbname="rrr" servicename="orcl" user="param" password="param" sid="orcl">
<TableConfig ID= "1" TableName="">
</TableConfig>
</dbConf>
</adapter>
i can access only the elements of the adapter tag.but what i need to use dbconf.. here i am posting the class es i am using to get the value of the adapter tag.The model class
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlRootElement;
#XmlRootElement
public class Adapter {
String name;
String type;
String version;
String description;
String execclass;
String parallel;
String mode;
String statusfile;
String merge_factor;
String active;
String drivername;
public String getDrivername() {
return drivername;
}
#XmlAttribute
public void setDrivername(String drivername) {
this.drivername = drivername;
}
public String getName() {
return name;
}
#XmlAttribute
public void setName(String name) {
this.name = name;
}
public String getType() {
return type;
}
#XmlAttribute
public void setType(String type) {
this.type = type;
}
public String getVersion() {
return version;
}
#XmlAttribute
public void setVersion(String version) {
this.version = version;
}
public String getDescription() {
return description;
}
#XmlAttribute
public void setDescription(String description) {
this.description = description;
}
public String getExecclass() {
return execclass;
}
#XmlAttribute
public void setExecclass(String execclass) {
this.execclass = execclass;
}
public String getParallel() {
return parallel;
}
#XmlAttribute
public void setParallel(String parallel) {
this.parallel = parallel;
}
public String getMode() {
return mode;
}
#XmlAttribute
public void setMode(String mode) {
this.mode = mode;
}
public String getStatusfile() {
return statusfile;
}
#XmlAttribute
public void setStatusfile(String statusfile) {
this.statusfile = statusfile;
}
public String getMerge_factor() {
return merge_factor;
}
#XmlAttribute
public void setMerge_factor(String merge_factor) {
this.merge_factor = merge_factor;
}
public String getActive() {
return active;
}
#XmlAttribute
public void setActive(String active) {
this.active = active;
}
}
The main class to get the values
import java.io.File;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Unmarshaller;
public class ReadXML {
/**
* #param args
*/
public static void main(String[] args) {
try {
File file = new File("./file/config.ds");
JAXBContext jaxbContext2 = JAXBContext.newInstance(Adapter.class);
Unmarshaller jaxbUnmarshaller2 = jaxbContext2.createUnmarshaller();
Adapter db2 = (Adapter) jaxbUnmarshaller2.unmarshal(file);
System.out.println(db2.active);
} catch (JAXBException e) {
e.printStackTrace();
}
}
}
You can use a StAX XMLStreamReader to advance parse the XML document. Then advance to the XML element you want to unmarshal. Then use the unmarshal method that takes XMLStreamReader as a parameter.
http://blog.bdoughan.com/2012/08/handle-middle-of-xml-document-with-jaxb.html
I can marshall a ObservableList using a "Wrapper"-class like below. But I cannot unmarshall it back to the wrapperclass it was before.
The idea is:
I have an ObservableList of "Expenses". I put this List into a wrapper-class and save this class to XML. The result looks like this:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<List>
<root>
<category>[none]</category>
<period>Year</period>
<title>asd</title>
<value>354</value>
</root>
</List>
I cannot bring it back to the wrapper-object.
I really appreciate any kind of help.
Main-class JAXBContext (visible for all):
JAXBContext jc = JAXBContext.newInstance(MyWrapperForList.class, Expense.class);
Main-class SAVEBUTTON:
public class SaveButtonListener implements EventHandler<ActionEvent> {
#Override
public void handle(ActionEvent arg0) {
File serializedFile = new File(PATH);
try {
if (serializedFile.exists() == false)
serializedFile.createNewFile();
PrintWriter xmlOut = new PrintWriter(serializedFile);
Marshaller m = jc.createMarshaller();
m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
List<Expense> saveList = new ArrayList<>();
saveList.addAll(data);
MyWrapperForList<Expense> wrapper = new MyWrapperForList<>(saveList);
JAXBElement<MyWrapperForList> jaxbElement = new JAXBElement<>(
new QName("List"), MyWrapperForList.class, wrapper);
m.marshal(jaxbElement, xmlOut);
xmlOut.flush();
xmlOut.close();
Main-class-LOADBUTTON:
public class LoadButtonListener implements EventHandler<ActionEvent> {
#Override
public void handle(ActionEvent arg0) {
try {
Unmarshaller unmarshaller = jc.createUnmarshaller();
StreamSource xml = new StreamSource(PATH);
MyWrapperForList<Expense> unwrapper = unmarshaller.unmarshal(xml,
MyWrapperForList.class).getValue();
List<Expense> tempList = new ArrayList<>();
tempList.addAll(unwrapper.getItems());
System.out.println(tempList.get(0).getTitle());
} catch (Exception e) {
e.printStackTrace();
}
}
}
Wrapper-class:
public class MyWrapperForList {
private List<Expense> list;
public MyWrapperForList() {
list = new ArrayList<>();
}
public MyWrapperForList(List<Expense> expenses) {
this.list = expenses;
}
#XmlAnyElement(lax=true)
public List<Expense> getItems() {
return list;
}
}
Expense-class:
#XmlRootElement(name = "root")
public class Expense {
private String title;
private String category;
private String period;
private String value;
public Expense() {} //Default constructor is needed for XML-handling
public Expense(String title, String value, String period, String category) {
this.title = title;
this.value = value;
this.period = period;
this.category = category;
}
#XmlElement(name = "title")
public String getTitle() {
return this.title;
}
#XmlElement(name = "category")
public String getCategory() {
return this.category;
}
#XmlElement(name = "period")
public String getPeriod() {
return this.period;
}
#XmlElement(name = "value")
public String getValue() {
return this.value;
}
}
I used this tutorial from Blaise Doughan: http://blog.bdoughan.com/2012/11/creating-generic-list-wrapper-in-jaxb.html
MyListWrapper
If you want MyWrapperForList to unmarshal holding an instance of ObservableList then you will need to setup your class in one of the following ways.
Property of Type ObservableList
import javax.xml.bind.annotation.XmlAnyElement;
import javafx.collections.*;
public class MyWrapperForList<T> {
private ObservableList<T> list;
public MyWrapperForList() {
list = FXCollections.<T>observableArrayList();
}
public MyWrapperForList(ObservableList<T> list) {
this.list = list;
}
#XmlAnyElement(lax = true)
public ObservableList<T> getItems() {
return list;
}
}
List Property Initialized to Instance of ObservableList
import java.util.List;
import javax.xml.bind.annotation.XmlAnyElement;
import javafx.collections.*;
public class MyWrapperForList<T> {
private List<T> list = FXCollections.<T>observableArrayList();
public MyWrapperForList() {
list = FXCollections.<T>observableArrayList();
}
public MyWrapperForList(List<T> list) {
this.list = list;
}
#XmlAnyElement(lax = true)
public List<T> getItems() {
return list;
}
}
Demo Code
Input (nub.xml)
<List>
<root>
<category>[none]</category>
<period>Year</period>
<title>dfg</title>
<value>4</value>
</root>
<root>
<category>[none]</category>
<period>Year</period>
<title>ROBO</title>
<value>1234</value>
</root>
</List>
Demo
import java.util.List;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.Unmarshaller;
import javax.xml.transform.stream.StreamSource;
public class Demo {
public static void main(String[] args) throws Exception {
JAXBContext jc = JAXBContext.newInstance(MyWrapperForList.class, Expense.class);
//UNMARSHALLING
Unmarshaller unmarshaller = jc.createUnmarshaller();
StreamSource xml = new StreamSource("src/forum18594548/nub.xml");
MyWrapperForList<Expense> wrapper = (MyWrapperForList<Expense>) unmarshaller.unmarshal(xml, MyWrapperForList.class).getValue();
List<Expense> data = wrapper.getItems();
System.out.println(data.getClass());
for(Expense expense : data) {
System.out.println(expense);
}
}
}
Output
class com.sun.javafx.collections.ObservableListWrapper
forum18594548.Expense#789df61d
forum18594548.Expense#4a8927c8
UPDATE
First: Thanks for you work Blaise!! I'm really glad for what you do to
me! I tried what you wrote here (it was nearly the same as I had) and
I got a similar (same type of) output as you got. BUT the objects in
the lists are all referenced with null. If I write
System.out.println(data.get(0).getTitle()); it says null. There is the
exact amount of objects in the list, but all attributes are referenced
with null. :(
I think I got tunnel vision on the ObservableList aspect only to miss your real problem was with how you mapped the Expense class. Since you only have get methods you should map to the fields using #XmlAccessorType(XmlAccessType.FIELD) as follows.
import javax.xml.bind.annotation.*;
#XmlRootElement(name="root")
#XmlAccessorType(XmlAccessType.FIELD)
public class Expense {
private String title;
private String category;
private String period;
private String value;
public Expense() {
}
public Expense(String title, String value, String period, String category) {
this.title = title;
this.value = value;
this.period = period;
this.category = category;
}
public String getTitle() {
return this.title;
}
public String getCategory() {
return this.category;
}
public String getPeriod() {
return this.period;
}
public String getValue() {
return this.value;
}
}
I want to unmarshall the following xml into another a parent object as defined below. But it always returns NULL.
Incoming XML:
<contentFiles>
<contentFile>
<contentFileName>cwb_reg_content_IB20C0F504A9A11E281E4C8BF76F4977C.pdf</contentFileName>
<title><![CDATA[SEC No-Action Guidance Expanding the Definition of “Ready Market” for Certain Foreign Equity Securities]]></title>
<sourcePublicationDate>20121219</sourcePublicationDate>
<alternateDocNumbers>
<alternateDocNumber>12345-b</alternateDocNumber>
</alternateDocNumbers>
<citesAffected>
<cite>SEA Rule 15c3-1</cite>
</citesAffected>
</contentFile>
</contentFiles>
Parent class corresponding to <contentFiles>
#XmlRootElement(name = "contentFiles")
public class RtSuperQuickMetadata
{
private List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems;
public RtSuperQuickMetadata()
{
rtSuperQuickMetadataItems = new ArrayList<RtSuperQuickMetadataItem>();
}
public List<RtSuperQuickMetadataItem> getRtSuperQuickMetadataItems()
{
return rtSuperQuickMetadataItems;
}
public void setRtSuperQuickMetadataItems(
List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems)
{
this.rtSuperQuickMetadataItems = rtSuperQuickMetadataItems;
}
}
Parent class corresponding to <contentFile>
#XmlRootElement(name = "contentFile")
public class RtSuperQuickMetadataItem
{
private String contentFileName;
private String title;
private String sourcePublicationDate;
private List<AlternateDocNumber> alternateDocNumbers;
private List<Cite> citesAffected;
public RtSuperQuickMetadataItem()
{
alternateDocNumbers = new ArrayList<AlternateDocNumber>();
citesAffected = new ArrayList<Cite>();
}
public List<AlternateDocNumber> getAlternateDocNumbers()
{
return alternateDocNumbers;
}
public List<Cite> getCitesAffected()
{
return citesAffected;
}
public String getContentFileName()
{
return contentFileName;
}
public String getSourcePublicationDate()
{
return sourcePublicationDate;
}
public String getTitle()
{
return title;
}
public void setAlternateDocNumbers(List<AlternateDocNumber> alternateDocNumbers)
{
this.alternateDocNumbers = alternateDocNumbers;
}
public void setCitesAffected(List<Cite> citesAffected)
{
this.citesAffected = citesAffected;
}
public void setContentFileName(String contentFileName)
{
this.contentFileName = contentFileName;
}
public void setSourcePublicationDate(String sourcePublicationDate)
{
this.sourcePublicationDate = sourcePublicationDate;
}
public void setTitle(String title)
{
this.title = title;
}
}
#XmlRootElement(name = "alternateDocNumber")
class AlternateDocNumber
{
private String alternateDocNumber;
public String getAlternateDocNumber()
{
return alternateDocNumber;
}
public void setAlternateDocNumber(String alternateDocNumber)
{
this.alternateDocNumber = alternateDocNumber;
}
#Override
public String toString()
{
return "AlternateDocNumber [alternateDocNumber=" + alternateDocNumber + "]";
}
}
#XmlRootElement(name = "cite")
class Cite
{
private String cite;
public String getCite()
{
return cite;
}
public void setCite(String cite)
{
this.cite = cite;
}
#Override
public String toString()
{
return "Cite [cite=" + cite + "]";
}
}
Unmarshaller code using JAXB:
public RtSuperQuickMetadata unmarshallXml(final File metadataFile)
throws JAXBException, FileNotFoundException
{
RtSuperQuickMetadata rtSuperQuickMetadata = null;
try
{
JAXBContext jc = JAXBContext.newInstance(RtSuperQuickMetadata.class);
Unmarshaller um = jc.createUnmarshaller();
rtSuperQuickMetadata =
(RtSuperQuickMetadata) um.unmarshal(metadataFile);
}
catch (JAXBException e)
{
String msg = "Malformed XML supplied as Metadata" + " Msg " + e.getMessage();
LOG.error(msg, e);
throw new RuntimeException(msg, e);
}
return rtSuperQuickMetadata;
}
You have too many XmlRootElements, you generally want to use this with the top element only. What you want to do is label the children as XmlElement.
Remove the XmlRootElement annotation from all but your root element (i.e. RtSuperQuickMetadata), and label them with XmlElement in the class from which they will be loaded.
So, as an example, here is how your RtSuperQuickMetadata class should look:
#XmlRootElement(name = "contentFiles")
class RtSuperQuickMetadata
{
private List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems;
public RtSuperQuickMetadata()
{
rtSuperQuickMetadataItems = new ArrayList<RtSuperQuickMetadataItem>();
}
#XmlElement(name = "contentFile")
public List<RtSuperQuickMetadataItem> getRtSuperQuickMetadataItems()
{
return rtSuperQuickMetadataItems;
}
public void setRtSuperQuickMetadataItems(
List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems)
{
this.rtSuperQuickMetadataItems = rtSuperQuickMetadataItems;
}
}
Transfer this principle to alternateDocNumbers and citesAffected as well.
If you want to see an example of how the Unmarshaller thinks your XML is formatted based off your annotations, you can create your structure in code and use the Marshaller. Here is a quick and ugly example:
RtSuperQuickMetadata rtSuperQuickMetadata = new RtSuperQuickMetadata();
List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems = new ArrayList<RtSuperQuickMetadataItem>();
rtSuperQuickMetadata.setRtSuperQuickMetadataItems(rtSuperQuickMetadataItems);
RtSuperQuickMetadataItem item = new RtSuperQuickMetadataItem();
rtSuperQuickMetadataItems.add(item);
ArrayList<Cite> cites = new ArrayList<Cite>();
Cite cite = new Cite();
cite.setCiteStr("MyCite");
cites.add(cite);
item.setCitesAffected(cites);
Marshaller m = jaxbContext.createMarshaller();
m.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
m.marshal(rtSuperQuickMetadata, System.out);
This will output the result to System.out. You can put this in a file instead, whatever suits your needs.
I have added this answer to address the follow up questions you posted as comments on the answer given by cklab.
I had another question. Why doesn't jaxb automatically allocate memory
for the lists contained in the object. Why do we need to assign memory
in a constructor for it ?
You do not need to, see below.
While unmarshalling these items the following isn't being saved into
the metadata object. 12 I
need to add another element for this to be generated ??
See mapping below.
RtSuperQuickMetadata
import java.util.*;
import javax.xml.bind.annotation.*;
#XmlRootElement(name = "contentFiles")
public class RtSuperQuickMetadata {
private List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems;
#XmlElement(name="contentFile")
public List<RtSuperQuickMetadataItem> getRtSuperQuickMetadataItems() {
return rtSuperQuickMetadataItems;
}
public void setRtSuperQuickMetadataItems(
List<RtSuperQuickMetadataItem> rtSuperQuickMetadataItems) {
this.rtSuperQuickMetadataItems = rtSuperQuickMetadataItems;
}
}
RtSuperQuickMetadataItem
import java.util.List;
import javax.xml.bind.annotation.XmlType;
#XmlType(propOrder={"contentFileName", "title", "sourcePublicationDate", "alternateDocNumbers", "citesAffected"})
public class RtSuperQuickMetadataItem {
private String contentFileName;
private String title;
private String sourcePublicationDate;
private List<AlternateDocNumber> alternateDocNumbers;
private List<Cite> citesAffected;
public List<AlternateDocNumber> getAlternateDocNumbers() {
return alternateDocNumbers;
}
public List<Cite> getCitesAffected() {
return citesAffected;
}
public String getContentFileName() {
return contentFileName;
}
public String getSourcePublicationDate() {
return sourcePublicationDate;
}
public String getTitle() {
return title;
}
public void setAlternateDocNumbers(
List<AlternateDocNumber> alternateDocNumbers) {
this.alternateDocNumbers = alternateDocNumbers;
}
public void setCitesAffected(List<Cite> citesAffected) {
this.citesAffected = citesAffected;
}
public void setContentFileName(String contentFileName) {
this.contentFileName = contentFileName;
}
public void setSourcePublicationDate(String sourcePublicationDate) {
this.sourcePublicationDate = sourcePublicationDate;
}
public void setTitle(String title) {
this.title = title;
}
}
AlternateDocNumber
class AlternateDocNumber {
private String alternateDocNumber;
public String getAlternateDocNumber() {
return alternateDocNumber;
}
public void setAlternateDocNumber(String alternateDocNumber) {
this.alternateDocNumber = alternateDocNumber;
}
}
Cite
class Cite {
private String cite;
public String getCite() {
return cite;
}
public void setCite(String cite) {
this.cite = cite;
}
}
I have the following XML and I need to convert it into a java object.
<tests>
<test-data>
<title>BookTitle</title>
<book>BookName</book>
<count>64018</count>
<test-data>
<title>Book title1</title>
<book>Book Name1</book>
<count>5</count>
</test-data>
<test-data>
<title>Book title2</title>
<book>Book Name3</book>
<count>5</count>
</test-data>
<test-data>
<title>Book title3</title>
<book>Book Name3</book>
<count>4</count>
</test-data>
</test-data>
</tests>
I am not sure what will be my pojo when I use JAXB to convert it.
I created the following POJOs as per my understanding:
public class Tests {
TestData testData;
public TestData getTestData() {
return testData;
}
public void setTestData(TestData testData) {
this.testData = testData;
}
}
public class TestData {
String title;
String book;
String count;
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getBook() {
return book;
}
public void setBook(String book) {
this.book = book;
}
public String getCount() {
return count;
}
public void setCount(String count) {
this.count = count;
}
}
Tests
On the Tests class we will add an #XmlRootElement annotation. Doing this will let your JAXB implementation know that when a document starts with this element that it should instantiate this class. JAXB is configuration by exception, this means you only need to add annotations where your mapping differs from the default. Since the testData property differs from the default mapping we will use the #XmlElement annotation. You may find the following tutorial helpful: http://wiki.eclipse.org/EclipseLink/Examples/MOXy/GettingStarted
package forum11221136;
import javax.xml.bind.annotation.*;
#XmlRootElement
public class Tests {
TestData testData;
#XmlElement(name="test-data")
public TestData getTestData() {
return testData;
}
public void setTestData(TestData testData) {
this.testData = testData;
}
}
TestData
On this class I used the #XmlType annotation to specify the order in which the elements should be ordered in. I added a testData property that appeared to be missing. I also used an #XmlElement annotation for the same reason as in the Tests class.
package forum11221136;
import java.util.List;
import javax.xml.bind.annotation.*;
#XmlType(propOrder={"title", "book", "count", "testData"})
public class TestData {
String title;
String book;
String count;
List<TestData> testData;
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getBook() {
return book;
}
public void setBook(String book) {
this.book = book;
}
public String getCount() {
return count;
}
public void setCount(String count) {
this.count = count;
}
#XmlElement(name="test-data")
public List<TestData> getTestData() {
return testData;
}
public void setTestData(List<TestData> testData) {
this.testData = testData;
}
}
Demo
Below is an example of how to use the JAXB APIs to read (unmarshal) the XML and populate your domain model and then write (marshal) the result back to XML.
package forum11221136;
import java.io.File;
import javax.xml.bind.*;
public class Demo {
public static void main(String[] args) throws Exception {
JAXBContext jc = JAXBContext.newInstance(Tests.class);
Unmarshaller unmarshaller = jc.createUnmarshaller();
File xml = new File("src/forum11221136/input.xml");
Tests tests = (Tests) unmarshaller.unmarshal(xml);
Marshaller marshaller = jc.createMarshaller();
marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
marshaller.marshal(tests, System.out);
}
}