Reputation: 3854
I am not getting an idea how to get an element by its attribute. I tried something as below but getting error as the item(1) might change as the loop goes on. some field tags may be stripped off. so position might change. I want to get:
<field name="Test/Content/Modified">Thu Jun 01 13:11:43 2014</field>
Xml:
<assets>
<document path="some/path/1">
<metadata>
<field name="Test/Content/Date">2013-12-20</field>
<field name="Test/Content/Modified">Thu Jun 01 13:11:43 2014</field>
<field name="Test/Locale">en_US</field>
<field name="Test/Content/SubSolution"></field>
</metadata>
</document>
<document path="some/path/2">
<metadata>
<field name="Test/Content/Date">2013-12-20</field>
<field name="Test/Locale">en_US</field>
<field name="Test/Content/Modified">Thu Jun 01 13:11:43 2014</field>
<field name="Test/Content/SubSolution"></field>
</metadata>
</document>
<assets>
java partial code:
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
Document doc = dBuilder.parse("E:\\example.xml");
List<String> list = new ArrayList<>();
NodeList nList = doc.getElementsByTagName("document");
for (int i = 0; i < nList.getLength(); i++) {
Node nNode = nList.item(i);
if (nNode.getNodeType() == Node.ELEMENT_NODE) {
Element eElement = (Element) nNode;
Date date = new Date(eElement.getElementsByTagName("field").item(1).getTextContent());
System.out.println(date);
Date date1 = new Date(2014 - 1900, 06 - 1, 04);
if (date.compareTo(date1) == 1) {
list.add(eElement.getAttribute("path").trim());
}
}
}
Upvotes: 4
Views: 12400
Reputation: 23627
Here is an XPath solution which doesn't use deprecated Date()
constructors:
String xml = "<assets> ... </assets>";
DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
Document doc = dBuilder.parse(new InputSource(new StringReader(xml)));
XPath xPath = XPathFactory.newInstance().newXPath();
String expression = "//document/metadata/field[@name='Test/Content/Modified']/text()";
NodeList dates = (NodeList) xPath.compile(expression).evaluate(doc, XPathConstants.NODESET);
for(int i = 0; i < dates.getLength(); i++) {
String dateString = dates.item(i).getNodeValue();
System.out.println(dateString); // the original string
SimpleDateFormat dateFormat = new SimpleDateFormat("EEE MMM dd HH:mm:ss yyyy");
Date date = dateFormat.parse(dateString);
System.out.println(date); // the date string of the parsed date
}
This prints (in my time zone):
Thu Jun 01 13:11:43 2014
Sun Jun 01 13:11:43 BRT 2014
Thu Jun 01 13:11:43 2014
Sun Jun 01 13:11:43 BRT 2014
The original string date has an incorrect day of the week value for the month/year.
Upvotes: 3
Reputation: 72884
You need to loop over the field
nodes and check the matching attribute value:
NodeList nList = doc.getElementsByTagName("document");
for (int i = 0; i < nList.getLength(); i++) {
Node nNode = nList.item(i);
if (nNode.getNodeType() == Node.ELEMENT_NODE) {
Element eElement = (Element) nNode;
NodeList fieldNodes = eElement.getElementsByTagName("field");
for(int j = 0; j < fieldNodes.getLength(); j++) {
Node fieldNode = fieldNodes.item(j);
NamedNodeMap attributes = fieldNode.getAttributes();
Node attr = attributes.getNamedItem("name");
if(attr != null) {
if(attr.getTextContent().equals("Test/Content/Modified")) {
Date date = new Date(fieldNode.getTextContent());
System.out.println(date);
Date date1 = new Date(2014 - 1900, 06 - 1, 04);
if (date.compareTo(date1) == 1) {
list.add(eElement.getAttribute("path").trim());
}
}
}
}
}
}
Upvotes: 4