Xml parsing using xmlstream Reader and writing into a new xml file

1.1k Views Asked by At
 <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:aop="http://www.springframework.org/schema/aop"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xsi:schemaLocation="
           http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
           http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-2.5.xsd">

        <aop:aspectj-autoproxy />  

        <bean   id="A" class="A" scope="singleton">
                <constructor-arg index='0'><ref bean='B'/></constructor-arg>        
        </bean>



      <bean id="B" class="B" scope="singleton">
                <aop:scoped-proxy proxy-target-class="true"/>
            <constructor-arg index="0"><ref bean="B" /></constructor-arg>

       </bean>

        <bean id="C" class="C" scope="singleton">
                <aop:scoped-proxy proxy-target-class="true"/>
            <constructor-arg index="0"><ref bean="C" /></constructor-arg>

       </bean>

      </beans>

I have a xml similar to this . I am trying to parse this xml and find if there is an element called scoped-proxy , if there is i want to remove the whole bean tag. I want to do for all the instances.

for example :

For bean id :"B" , it has this element so i want to remove the whole

  <bean id="B" class="B" scope="singleton">
            <aop:scoped-proxy proxy-target-class="true"/>
        <constructor-arg index="0"><ref bean="B" /></constructor-arg>

   </bean>

and after removing i want to write in a new xml file.

Sample code:

    import java.util.HashSet;
    import javax.xml.stream.XMLInputFactory;
    import javax.xml.stream.XMLOutputFactory;
    import javax.xml.stream.XMLStreamReader;
    import javax.xml.transform.stream.StreamSource;
    import org.w3c.dom.Node;


    public class XMLParser {

        public static void main(String[] args) throws Exception {
            XMLInputFactory xif = XMLInputFactory.newFactory();
            StreamSource xml = new StreamSource("src/a.xml");
            XMLStreamReader xsr = xif.createXMLStreamReader(xml);


            HashSet<String> idSet = new HashSet<>();

            while(xsr.hasNext()) {
                if(xsr.isStartElement() && "bean".equals(xsr.getLocalName())) {
                    String value=xsr.getAttributeValue(1);
                    xsr.nextTag();
                    if("scoped-proxy".equals(xsr.getLocalName())){
                        idSet.add(value);
                        System.out.println(value);
                    }     
                }
                xsr.next();
             }


        }

    }

Since i am new to parsing xml using java please let me know on how to remove the complete element when found and write into a new file

2

There are 2 best solutions below

2
teppic On

A fairly straight-forward solution is to read the whole source document in to memory and then manipulate the DOM manually:

public class DomFilter {
    public static void main(String[] args) throws Exception {
        DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        factory.setNamespaceAware(true);
        DocumentBuilder parser = factory.newDocumentBuilder();

        try (InputStream in = new FileInputStream("src/a.xml")) {
            // Parse the source
            Document doc = parser.parse(in);

            // Find all "bean" elements
            NodeList beans = doc.getElementsByTagNameNS("http://www.springframework.org/schema/beans", "bean");
            List<Element> toRemove = new ArrayList<>();
            for (int i = 0; i < beans.getLength(); i++) {
                Element bean = (Element) beans.item(i);
                // Does the bean element have a "scoped-proxy" child element?
                if (bean.getElementsByTagNameNS("http://www.springframework.org/schema/aop", "scoped-proxy").getLength() > 0) {
                    // Yes... add it to the remove list
                    toRemove.add(bean);
                }
            }

            // Remove the elements we found
            toRemove.forEach(e -> e.getParentNode().removeChild(e));

            // Write the tree out using an identity transformer
            Transformer writer = TransformerFactory.newInstance().newTransformer();
            writer.transform(new DOMSource(doc), new StreamResult(System.out));
        }
    }
}
1
Gautham On
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;

public class DomFilter {
    public static void main(String[] args) throws Exception {
        DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        factory.setNamespaceAware(true);
        DocumentBuilder parser = factory.newDocumentBuilder();

        try (InputStream in = new FileInputStream("src/a.xml"))
        {
            // Parse the source
            Document doc = parser.parse(in);

            String filepath = "src/filtered.xml";
            StreamResult result = new StreamResult(new File(filepath));

            // Find all "bean" elements
            NodeList beans = doc.getElementsByTagNameNS("http://www.springframework.org/schema/beans", "bean");
            List<Element> toRemove = new ArrayList<>();
            for (int i = 0; i < beans.getLength(); i++) {
                Element bean = (Element) beans.item(i);
                // Does the bean element have a "scoped-proxy" child element?
                if (bean.getElementsByTagNameNS("http://www.springframework.org/schema/aop", "scoped-proxy").getLength() > 0) {
                    // Yes... add it to the remove list
                    toRemove.add(bean);
                }
            }

            // Remove the elements we found
            toRemove.forEach(e -> e.getParentNode().removeChild(e));

            // Write the tree out using an identity transformer
            Transformer writer = TransformerFactory.newInstance().newTransformer();
            writer.setOutputProperty(OutputKeys.ENCODING, "UTF-8");
            //writer.setOutputProperty(OutputKeys.INDENT, "yes");
            writer.transform(new DOMSource(doc), result);
        }
    }
}