Link to home
Start Free TrialLog in
Avatar of Tolgar
Tolgar

asked on

How to create an XML file in the given format in Java?

Hi,
I try to create an XML file from the data that I have in a List.

So far, I have the following incomplete code to create the XML:

        public static void saveResults() throws ParserConfigurationException{
            DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
            DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
            Document doc = docBuilder.newDocument();
         
            // root elements
            Element rootElement = doc.createElement("Results");
            doc.appendChild(rootElement);
            
            for (CheckDetail checkDetail : checkDetails) {
                
                checkDetail.getFileName(); //Filename
                checkDetail.getName(); //Check
                checkDetail.getStatus(); //Status
                checkDetail.getExistingLineNumbers(); //Existing Line Numbers
                checkDetail.getNewLineNumbers(); //New Line Numbers
                
            }
            
        }

Open in new window


I would like to  create the XML in the following form. For each "for loop" in the code above, there will be one group of <Detail>. And the information is already given in the code above. (i.e file name will be gathered from checkDetail.getFileName())

<Results>
  <Date>Tuesday, October 01, 2013  16:46:47</Date>
  <Detail>
    <name>FILE NAME IN HERE</name>
    <check> CHECK NAME IN HERE </check>
    <status> STATUS NAME IN HERE </status>
   <existingLineNumbers>EXISTING LINE NUMBERS IN HERE</existingLineNumbers>             
   <newLineNumbers>EXISTING LINE NUMBERS IN HERE</newLineNumbers>
  </Detail>
  <Detail>
    <name>FILE NAME IN HERE</name>
    <check> CHECK NAME IN HERE </check>
    <status> STATUS NAME IN HERE </status>
   <existingLineNumbers>EXISTING LINE NUMBERS IN HERE</existingLineNumbers>             
   <newLineNumbers>EXISTING LINE NUMBERS IN HERE</newLineNumbers>
  </Detail>
</Results>

Open in new window


Can you please show me how I can modify my code to generate this XML?
Avatar of CEHJ
CEHJ
Flag of United Kingdom of Great Britain and Northern Ireland image

there will be one group of <Detail>.
You show two ...
Avatar of Tolgar
Tolgar

ASKER

@CEHJ: Because, in the example XML that I posted, the "for loop" loops for twice therefor we see two <Detail> groups.

 So, the core xml will look like this with only one loop of the "for loop":

<Results>
  <Date>Tuesday, October 01, 2013  16:46:47</Date>
  <Detail>
    <name>FILE NAME IN HERE</name>
    <check> CHECK NAME IN HERE </check>
    <status> STATUS NAME IN HERE </status>
   <existingLineNumbers>EXISTING LINE NUMBERS IN HERE</existingLineNumbers>             
   <newLineNumbers>EXISTING LINE NUMBERS IN HERE</newLineNumbers>
  </Detail>
<Results>

Open in new window

It's easier to write XML as a text file rather than using the xml DocumentBuilder library -- that's more for reading XML.  It doesn't help as much to write it.

Since you're starting with data, not an XML doc, I suggest you read the data, loop through it, and write the XML syntax in the format you want.  It's usually easier to create the full String (or StringBuilder) in the program, and write it all to a file at the end, when you're done.

But, if it's going to be a huge file, you could consider appending the lines to the output file as you read through your data.  Either way works.
Avatar of Tolgar

ASKER

I understand your point. But, due to the code review purposes it is hard for me to convince the reviewers. So I need to write it with the documentbuilder library.

I would appreciate if you could help me with it.

Thanks,
You are pretty close already and so I am not going to just give you the code, I think it would be beneficial for you to get this yourself. (Obviously I will help further if you need more than this, but see how you go).

Ok, so you are already creating your 'rootElement' called Results and have appended it to the document. The rest of what you need to do is just very similar to this, and so you will pretty much just need to copy those two lines and paste a few times making some minor changes...

So, you need to create another element called Date (note that you always use "doc" to create elements, regardless of where they go in the resulting document, think or doc as an "Element Factory" as well as the representation of the document) and then you can "appendChild" it to your already created rootElement (because that is where it goes in the XML, Date is a child of Results). The only extra thing here is that you need to set the value of the Date element, which you do by calling .setTextContent() on the Date element and pass it the String that you want to be inside your Date element in the XML. These 3 lines of code go outside your for loop, since you only want 1 Date element in the XML.

Then, inside the for loop, you need to paste those 2 lines again, but now you are creating the Detail element, and again you will want to "appendChild" that new element to the rootElement.

And then, for each of your checkDetail.getXXXX lines, you will need to create the correct element, "appendChild" that element to the Detail element that you created at the top of the loop, and then .setTextContent on this element with the value from checkDetail.


All should be straightforward, the final point that is a bit tricky, is to serialize the "document" object, either to a String so you can print it to the console or directly to a File. You can use the following code to achieve this (it goes after the for loop) ...
        Transformer transformer = TransformerFactory.newInstance().newTransformer();
        transformer.setOutputProperty(OutputKeys.INDENT, "yes");
        transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4");

        // Use this to serialize to a String
        StringWriter stringWriter = new StringWriter();
        transformer.transform(new DOMSource(doc), new StreamResult(stringWriter));
        System.out.println(stringWriter.toString());

        // Or use this to serialize to a File
        FileWriter fileWriter = new FileWriter("TestMessage.xml");
        transformer.transform(new DOMSource(doc), new StreamResult(fileWriter));
        fileWriter.close();

Open in new window

Avatar of Tolgar

ASKER

@mccarl: Thank you for your reply. I understand that you want me to learn rather than just typing the code but I am in a very critical time pressure and I also need to fix some other problems in my code.

So, I would really appreciate, if you can give me the code to do these at this point.
ASKER CERTIFIED SOLUTION
Avatar of mccarl
mccarl
Flag of Australia image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
I understand your point. But, due to the code review purposes it is hard for me to convince the reviewers. So I need to write it with the documentbuilder library.
That's correct and is how you should do it - that's what it's designed for. There are libraries that make things a little easier, such as JDOM, but the JRE will do all you need
Avatar of Tolgar

ASKER

Thanks a lot! You really  helped me to save time.
You're welcome! As long as you learnt something out of that too which you could apply later if you have similar needs.