xmldom
xmldom copied to clipboard
Need example to traverse and modify XML file using XMLDOM
I am new to Node.js and am trying to parse, traverse and modify a XML (KML) file using Node.js. Can someone please provide an example on how to use the XMLDOM library to do this? Thanks in advance.
VJ
Open the file as a string using fs.readFile
: http://nodejs.org/api/fs.html#fs_fs_readfile_filename_options_callback
Then use xmldom to parse the XML into a DOM object using DOMParser.parseFromString
: https://github.com/jindw/xmldom#api-reference
When you do that you'll have a DOM object you can traverse with common DOM methods like getElementsByTagName
and the like.
You can use those to find elements and make whatever changes you like to them. Once you're done, you can convert the document back into a string using xmldom's XMLSerializer.serializeToString
and then write the file back to disk using fs.writeFile
: http://nodejs.org/api/fs.html#fs_fs_writefile_filename_data_options_callback
Thanks Kethinov!
I am trying to read multiple xml files from a dir and traverse and parse them. I have it working with a single file, can someone suggest the some options to read multiple files from a dir in Node.js?
Thanks in advance. VJ
Loop through the directory and open each file like in the example above.
As mentioned above. I am trying to read modify write and XML tag element value. fs.readFile('./test.xml','utf8', function (err, data) { if (err) { return console.log(err); } else { var doc = new dom().parseFromString(data); doc.getElementsByTagName("status")[0].childNodes[0].nodeValue = '100'; console.log(doc.getElementsByTagName("status")[0].childNodes[0].nodeValue); //Return correct value 100
var serializer = new xmldom.XMLSerializer();
var writetofile = serializer.serializeToString(doc);
console.log(writetofile); //Returns WRONG old value.
}
Am I missing something ?
Thanks in advance.
Here's a full working example:
first I went to https://msdn.microsoft.com/en-us/library/ms762271%28v=vs.85%29.aspx and saved that xml as books.xml
then I wrote this simple node program using fs
and xmldom
:
var xmldom = require('xmldom').DOMParser,
fs = require('fs');
fs.readFile('books.xml', 'utf-8', function (err, data) {
if (err) {
throw err;
}
var genreno,
thisgenreobject,
thisgenre,
doc,
genres;
doc = new xmldom().parseFromString(data, 'application/xml');
genres = doc.getElementsByTagName('genre');
for (genreno in genres) {
thisgenreobject = genres[genreno];
if (thisgenreobject.firstChild) {
thisgenre = thisgenreobject.firstChild.nodeValue;
if (thisgenre === 'Computer') {
console.log(thisgenreobject.parentNode.getElementsByTagName('title')[0].firstChild.nodeValue);
}
}
}
});
This returns the names of all the computer books from the sample data set.
I'm seeing the same effect as youemailmee, where i can modify the nodes, the value appears to have changed, but when using XMLSerializer().serializeToString(doc)
the output string contains the old value.
Anyone know what I am missing?
Same here! This code returns the exact same XML that went in, without the modification
var DOMParser = require('xmldom').DOMParser;
var XMLSerializer = require('xmldom').XMLSerializer;
var serializer = new XMLSerializer();
var doc = new DOMParser().parseFromString(
'<xml xmlns="a" xmlns:c="./lite">\n'+
'\t<child>test</child>\n'+
'\t<child></child>\n'+
'\t<child/>\n'+
'</xml>'
,'text/xml');
var xpath = require('xpath');
var select = xpath.useNamespaces({a: 'a'});
var node;
node = select('//a:child', doc, true);
console.info('selected node', node.toString());
node.firstChild.text = 'changed';
node.firstChild.nodeValue = 'changed';
node.text = 'changed';
node.nodeValue = 'changed';
console.info('new node', node.firstChild.nodeValue);
console.info('doc after change', serializer.serializeToString(doc))
Got it to change text! Used the node.textContent attribute
var DOMParser = require('xmldom').DOMParser;
var XMLSerializer = require('xmldom').XMLSerializer;
var serializer = new XMLSerializer();
var doc = new DOMParser().parseFromString(
'<xml xmlns="a" xmlns:c="./lite">\n'+
'\t<child>test</child>\n'+
'\t<child></child>\n'+
'\t<child/>\n'+
'</xml>'
,'text/xml');
var xpath = require('xpath');
var select = xpath.useNamespaces({a: 'a'});
var node;
node = select('//a:child', doc, true);
console.info('selected node', node.toString());
//node.firstChild.text = 'changed';
//node.firstChild.nodeValue = 'changed';
//node.text = 'changed';
//node.nodeValue = 'changed';
node.textContent = 'changed';
console.info('new node', node.firstChild.nodeValue);
console.info('doc after change', serializer.serializeToString(doc))
HI friends.... i have solved the issue ....cheers....... you can check my code
parseXML : function () { try { var xml = fs.readFileSync(process.env.PWD+"/upload/tmp/filtered.xml").toString();// fetch xml and convert to string var DOMParser = require('xmldom').DOMParser; var dom = new DOMParser().parseFromString(xml); var XMLSerializer = require('xmldom').XMLSerializer; var serializer = new XMLSerializer();
dom.documentElement.firstChild.nextSibling.attributes[0].nodeValue = "kissing" console.log(dom.documentElement.firstChild.nextSibling.attributes[0].nodeValue);
var newString =
'
} catch (error) { console.log("error in catch ---"); console.log(error); } }
I am not able to modify my xml using XMLSerializer... My code is var xml= request.responseText; var DOMParser = require('xmldom').DOMParser; var parser = new DOMParser(); var document = parser.parseFromString(xml, 'text/xml'); document.getElementsByTagName("a:Value").nodeValue=12345; var XMLSerializer = require('xmldom').XMLSerializer; var serializer = new XMLSerializer(); var writetofile = serializer.serializeToString(document); console.log("writetofile"+writetofile);
I am getting XML with same old value not 12345.
Please let me know how to resolve this..tried all above options..still not working.:(
Hi, everyone, how can i get the raw data:
<a> <result>true</result> </a>
I want the the raw data: <result>true</result>.
how should i do?
i can not modify XML file,what is wrong? please help me
var fs = require("fs"); var DOMParser = require('xmldom').DOMParser; var XMLSerializer = require('xmldom').XMLSerializer; var serializer = new XMLSerializer(); fs.readFile('./noauth-config.xml','utf8', function (err, data) { if (err) { return console.log(err); } else{ var doc = new DOMParser().parseFromString(data,'application/xml') var genres = doc.getElementsByTagName('config')[0]; // 克隆一个节点 newNode=genres.cloneNode(true); // 将克隆的节点追加到最后 doc.documentElement.appendChild(newNode); console.log("&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&"); // 获取待修改的目标属性的值 console.log(doc.documentElement.lastChild.childNodes[1].attributes[1].nodeValue); console.log(doc.documentElement.lastChild.attributes[0].nodeValue); // 修改目标属性的值 doc.documentElement.lastChild.childNodes[1].attributes[1].nodeValue = "1.1.1.1"; doc.documentElement.lastChild.attributes[0].nodeValue = "ttttttttttttttttttt"; console.log(doc.documentElement.lastChild.childNodes[1].attributes[1].nodeValue); console.log(doc.documentElement.lastChild.attributes[0].nodeValue); console.log(serializer.serializeToString(doc)); });
For anyone else struggling with this, you need to change the .data
value on the child node and not .nodeValue
. see: https://stackoverflow.com/a/32854062