Java object for XML elements?

I am working on a webservices client application, and I mainly work. I can get and read data from a third-party web service. Now I need to submit some data, and I'm stuck.

The classes for the objects I receive / send were generated from XSD files using the xjc tool. The part I'm stuck on turns one of these objects into an XML tree to send to a web service.

When I receive / send a request from / to ws, it contains a payload object. This is defined in java code as (partial list):

@XmlAccessorType(XmlAccessType.FIELD) @XmlType(name = "PayloadType", propOrder = { "compressed", "document", "any", "format" }) public class PayloadType { @XmlElement(name = "Compressed") protected String compressed; @XmlElement(name = "Document") protected List<String> document; @XmlAnyElement protected List<Element> any; protected String format; public List<Element> getAny() { if (any == null) { any = new ArrayList<Element>(); } return this.any; } } 

The only field I'm associated with is the "any" field, which contains an XML tree. When I retrieve data from ws, I read this field with something like this: ("root" is of type org.w3c.dom.Element and is the result of calling getAny (). Get (0) on the payload object)

 NodeList nl = root.getElementsByTagName("ns1:Process"); // "ns1:Process" is an XML node to do something with if (nl != null && nl.getLength() > 0) { for (int i = 0; i < nl.getLength(); i++) { Element proc = (Element) nl.item(i); try { // do something with the 'proc' Element here... } catch (Exception ex) { // handle problems here... } } } 

Sending data is where I got stuck. How to take a java object created from one of the classes generated from XSD and turn it into an Element object, which I can add to the β€œany” list of the payload object? For example, if I have a DailyData class, and I create and populate it with data:

 DailyData dData = new DailyData(); dData.setID = 34; dData.setValues = "3,5,76,23"; 

How to add this dData object to the "any" list of the payload object? It must be an Element. Am I doing something with the JAXBContext marshaller? I used this to dump the dData object on the screen to check the XML structure.

I'm sure the answer is looking in my face, but I just don't see it!

Dave

UPDATE: working with the code snippet below:

 DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance(); Document doc = dbf.newDocumentBuilder().newDocument(); JAXBContext context = JAXBContext.newInstance(DailyData.class); Marshaller marshaller = context.createMarshaller(); marshaller.marshal(dData, doc); PayloadType payload = new PayloadType(); payload.getAny().add((Element)doc.getFirstChild()); 
+4
source share
2 answers

The type of the List<Element> field is usually generated by XJC if there is something like this in the schema:

 <xs:any processContents="skip" maxOccurs="unbounded" minOccurs="0" /> 

The key here is processContents="skip" , which means "everything goes" - any well-formed XML can be here. Since it is free for everyone, all that the XJC can do is present it as a DOM, and you take responsibility for this payload.

If you remove processContents="skip" , then JAXB will try to associate the payload with the object model if it can map the payload XML to the class in JAXBContext . In this case, XJC will generate this field of type List<Object> .

This may not seem like an improvement, but this List may contain an Element (if the JAXBContext does not recognize the payload as something to which it can be attached) or a JAXBElement (if it recognizes It). The latter contains a linked version of the payload, and it is much easier to handle.

All of this is described below here .

If you cannot change the circuit and are stuck with processContents="skip" , you will have to jump through the hoops. You can create another JAXBContext that knows about your payload classes and use it to marshal Element (using something like marshaller.marshal(payload, new DOMResult()) . Then you can unload this element into the payload.

+1
source

Firstly, any element can contain any XML inside it. Thus, schema validation should work fine even if you add an XML representation of the DailyData class to this.

Now for your other question about DailyData class marshaling. If this class was generated using the xjc compiler itself, this class (or some other generated class) would already know how to convert this object to XML.

I have not used this directly, but the following link should help you

http://publib.boulder.ibm.com/infocenter/wasinfo/v7r0/index.jsp?topic=/com.ibm.websphere.express.doc/info/exp/ae/rwbs_xjc.html

0
source

Source: https://habr.com/ru/post/1308777/


All Articles