tags:

views:

220

answers:

4

Hi, I'm trying to figure out how best to translate this:

<Source><properties>
  ....
  <name>wer</name>
  <delay>
    <type>Deterministic</type>
    <parameters length="1">
      <param value="78" type="Time"/>
    </parameters>
  </delay>
  <batchSize>
    <type>Cauchy</type>
    <parameters length="2">
      <param value="23" type="Alpha"/>
  <param value="7878" type="Beta"/>
    </parameters>
  </batchSize>
 ...
</properties></Source>

Into:

<Source><properties>
  ....
  <name>wer</name>
  <delay>
    <Deterministic Time="78"/>
  </delay>
  <batchSize>
      <Cauchy Alpha="23" Beta="7878"/>
  </batchSize>
 ........
</properties></Source>

I've tried using DocumentBuilderFactory, but I while I can access the value of the name tag, I cannot access the values in the delay/batch section. This is code I used

Element prop = (Element)propertyNode;

NodeList nodeIDProperties = prop.getElementsByTagName("name");
Element nameElement = (Element)nodeIDProperties.item(0);

NodeList textFNList = nameElement.getChildNodes();
String nodeNameValue = ((org.w3c.dom.Node)textFNList.item(0)).getNodeValue().trim();

//--------
NodeList delayNode = prop.getElementsByTagName("delay");

Calling getElementByName("type") or "parameters" doesn't seem to return anything I can work with. Am I missing something, or is there a cleaner way to process the exisiting xml.

The need to be in the defined format to allow for marshalling and unmarshalling by Castor.

Any help would be much appreciated.

+1  A: 

This looks like a job for XPATH or some other XML transformation API.

Check out: http://www.ibm.com/developerworks/library/x-javaxpathapi.html

Software Monkey
+5  A: 

There are a variety of ways to convert the XML.

1) You can use XSLT (XSL Transformations) to transform the XML. It is a XML based language used to transform XML documents in other XML documents, text, or HTML. The syntax is hard to learn. However it is a powerful tool for XML conversion. Here is a tutorial. For using XSLT with Java I would recommend Saxon which also comes with a nice documentation. The big plus using XSLT is that the conversion can be externalized in a seperate template. So your Java code is not obfuscated by the translation stuff. However, as mentioned the learning curve is definitly steeper.

2) You can use XPath to select the nodes easily. XPath is a query language for selecting nodes in a XML document. XPath is also used in XSLT by the way. E.g. the XPath query

//delay[type = 'Deterministic']/parameters/param/@value

selects all parameters value which are contained in a node param which are a child of delay containing a node type with the value "Deterministic". Here is a nice web application for testing XPath queries. Here is a tutorial how to use XPath in Java and here about XPath in general. You can use XPath expressions to select the right nodes in your Java code. IMHO this is far more readable and maintainable than using the DOM object model directly (which is also from time to time ackward as you have already learned).

3) You can use Smooks for doing XML transformations. This is especially useful if the transformation gets rather complex. Smooks populates a object model from the input XML and outputs the result XML via a templating mechanism either using Freemarker or XSL templates. Smooks has a very high througput and is used in high performance environments like ESBs (e.g. JBoss ESB, Apache ServiceMix). Might be overpowered for yur scenario though.

4) You could use Freemarker to do the transformation. I have no experience in this, but as I heared it can be used fairly simple. See the "Declarative XML processing" section of the documentation (also take a look at "Exposing XML documents" to learn how to read the source XML). Seems fairly simple to me. If you try your luck with this approach, I would love to hear about it.

spa
You summarised what the rest of guys above have said. Thanks. I'll look into XSLT and if the curve is too steep (on a bit of time crunch) then I'll use the XPath query.Thanks.
I saw that. So I have added some more resources. Freemarker seems to be really useful in your scenario...
spa
XSLT is not bad if you are familiar with LISP-y languages.
Thorbjørn Ravn Andersen
A: 

Although probably XSLT is the best way to do this, if you want to use a JVM programming language and you want to learn a different approach, you can try scala's xml transformation library.

Some blog posts:

http://scala.sygneca.com/code/xml-pattern-matching

http://debasishg.blogspot.com/2006/08/xml-integration-in-java-and-scala.html

volothamp
A: 

XSLT was the way forward in the end. Its actually pretty easy to use and the w3schools example is a good place to start.