Reputation: 998
I want to idendify the tag while parsing this XML content. we have method like isStartElement() or isEndElement(). but this is not comes under both category. pls help me. how to address this kind of tags.
Code :
import java.io.StringReader;
import java.util.Hashtable;
import java.util.Iterator;
import javax.xml.stream.Location;
import javax.xml.stream.XMLEventReader;
import javax.xml.stream.XMLInputFactory;
import javax.xml.stream.XMLStreamReader;
import javax.xml.stream.events.EndElement;
import javax.xml.stream.events.StartElement;
import javax.xml.stream.events.XMLEvent;
public class Sample {
public static void main(String[] args) {
String xPath = "HAI/ONE";
String xml = "<HAI><ONE/></HAI>";
try {
System.out.println(getValueByXPath(xml,xPath));
} catch (Exception e) {
e.printStackTrace();
}
}
public String getValueByXPath(String xmlString, String xPathString){
String value = "";
String tagName = null;
int index = 2;
int hashIndex = 1;
int tagBalance = 0;
String tagIndex = null;
String[] tagIndexArr = null;
Hashtable<Integer,String> xPathHashtable = null;
XMLInputFactory xmlInputFactory;
XMLEventReader xmlEventReader;
try{
xmlInputFactory = XMLInputFactory.newInstance();
xmlInputFactory.setProperty
(XMLInputFactory.IS_REPLACING_ENTITY_REFERENCES,Boolean.TRUE);
xmlInputFactory.setProperty
(XMLInputFactory.IS_SUPPORTING_EXTERNAL_ENTITIES,Boolean.FALSE);
xmlInputFactory.setProperty(XMLInputFactory.IS_COALESCING,
Boolean.FALSE);
xmlEventReader = xmlInputFactory.createXMLEventReader(new StringReader
(xmlString));
//Split XPath
xPathHashtable = splitXPath(xPathString);
tagIndex = xPathHashtable.get(hashIndex);
tagIndexArr = tagIndex.split("=");
tagName = tagIndexArr[0];
index = Integer.parseInt(tagIndexArr[1])+1;
while (xmlEventReader.hasNext()) {
XMLEvent e = xmlEventReader.nextEvent();
if(tagBalance < 0 ){
return "";
}
if(index==1 && e.isCharacters()){
value = e.asCharacters().getData();
hashIndex++;
tagIndex = xPathHashtable.get(hashIndex);
if(tagIndex == null)break;
tagIndexArr = tagIndex.split("=");
tagName = tagIndexArr[0];
index = Integer.parseInt(tagIndexArr[1])+1;
tagBalance = 0;
System.out.println(tagName+"tag"+index);
}
if (e.isStartElement()) {
StartElement startElement = e.asStartElement();
if(tagName.equalsIgnoreCase(startElement.getName
().getLocalPart())){
index--;
tagBalance++;
}
}
if (e.isEndElement()) {
EndElement endElement = e.asEndElement();
if(tagName.equalsIgnoreCase(endElement.getName
().getLocalPart())){
tagBalance--;
}
}
}
}catch(Exception e){
e.printStackTrace();
}
return value;
}
public Hashtable<Integer,String> splitXPath(String xPath){
Hashtable<Integer,String> xPathHashtable = null;
String[] xPathSplit = null;
int hashIndex = 0;
int index = 1;
String tag= null;
try{
xPathHashtable = new Hashtable<Integer,String>();
xPathSplit = xPath.split("[\\[\\]/]");
for(int i=0;i<xPathSplit.length;i++){
if(xPathSplit[i].isEmpty()) continue;
try{
index = Integer.parseInt(xPathSplit[i]);
}catch(Exception e){
tag = xPathSplit[i];
index = 1;
hashIndex++;
}
xPathHashtable.put(hashIndex, tag+"="+index);
}
}catch(Exception e){
e.printStackTrace();
}
return xPathHashtable;
}
}
I am simulating XPath scenario with Stax parser.
Upvotes: 3
Views: 1258
Reputation: 141
I have had the same issue as you and couldn't find a solution anywhere.
What you want to do is use
xmlEventReader.peek().isEndElement()
and handle however you'd like to. peek()
doesn't move the element like .nextEvent()
does.
Upvotes: 0