OK, I have an XML/XSLT pairing (inserted into my HTML via Javascript from 2 external files) that creates a button on the page with the nodeValue taken from a tag called 'JobID' (a generated GUID).
<button id="5f8294ca-fe5a-4da9-847b-da99df999000" onclick="markFinished(this.id)" type="button">Finished</button>
Thus returning the id of the button to a function...
function markFinished(clicked_id)
{
cid = clicked_id;
document.write(cid)
}
The XML look like this...
<?xml version="1.0" encoding="utf-8"?>
<CurrentJobs>
<Job>
<JobID>25657287-cc52-415b-8781-be37d5098656</JobID>
<Status>a-current</Status>
</Job>
<Job>
<JobID>5f8294ca-fe5a-4da9-847b-da99df999000</JobID>
<Status>a-current</Status>
</Job>
<Job>
<JobID>05a84779-5801-4645-a7f9-74529ea5298b</JobID>
<Status>a-current</Status>
</Job>
<Job>
<JobID>07df3deb-4935-4504-8822-a73ccea038ae</JobID>
<Status>b-complete</Status>
</Job>
<Job>
<JobID>078c496d-ac60-48e7-b9fe-a0e1f78ff2c5</JobID>
<Status>c-upcoming</Status>
</Job>
<Job>
<JobID>07ec868e-d294-4bb3-807d-00df66f5bab2</JobID>
<Status>c-upcoming</Status>
</Job>
<Job>
<JobID>8bdeee5f-2bf6-4e44-8af8-69f600048dfe</JobID>
<Status>a-current</Status>
</Job>
</CurrentJobs>
I need a way for my function to match the clicked_id to the JobID and replace the nextSibling (Status) with 'b-finished'. Any help here would be greatly appreciated.
You'd do that by parsing the XML and traversing it nodes.
As the value you're looking for is the text, you have to iterate and check each element until a match is found, then get the next element and replace the text content of that
var parser = new DOMParser();
var doc = parser.parseFromString(xml, "application/xml");
function markFinished(clicked_id) {
var cid = clicked_id;
var nodes = doc.getElementsByTagName('JobID'),
match = null;
for (var i=nodes.length; i--;) {
if ( nodes[i].textContent.trim() === clicked_id ) {
match = nodes[i];
break;
}
}
if (match) {
match.nextSibling.textContent = 'b-finished'
}
}
FIDDLE
Related
I have one sample XML & XSL resource. I am getting XML as a string from API call in javascript. While XSLT is present as a static resource on the server. My goal is to display XML content along with stylesheet in HTML document element.
I do not want to use XSLTProcessor for now. I would like to try the browser way. And yes both the XML and XSLT would be coming from the same server.
Code:
import XSL from '#salesforce/resourceUrl/Roles';
export default class DisplayReport extends LightningElement {
renderedCallback(){
var xml = '<root> <node>one</node> <nodes> <node>1</node> <node>2</node> </nodes> <node>two</node> </root>';
var output = '<?xml version="1.0" encoding="UTF-8"?><?xml-stylesheet type="text/xsl" href="'+XSL+'" ?>'+xml;
console.log(output); //output on below line
//<?xml version="1.0" encoding="UTF-8"?><?xml-stylesheet type="text/xsl" href="/assets/project/b481ca5a6f/staticresources/Roles" ?><root> <node>one</node> <nodes> <node>1</node> <node>2</node> </nodes> <node>two</node> </root>
var xmlNode = this.parseXml(output);
console.log(xmlNode);
const element = this.template.querySelector('div.dms');
element.appendChild(xmlNode.documentElement);
}
parseXml(xmlStr){
if (window.DOMParser) {
return ( new window.DOMParser() ).parseFromString(xmlStr, "text/xml");
}
}
}
Markup:
<template>
<div class="dms" lwc:dom="manual">
</div>
</template>
Output: (no style sheet getting applied)
one 1 2 two
Any idea what is missing here?
I am parsing XML via libxmljs2 and then trying to add an extra element, see example below.
var x = require('libxmljs2');
var xmlDoc = x.parseXmlString(`<?xml version="1.0" encoding="UTF-8"?>
<ns:FOO xmlns:ns=“example ns" xmlns:ns2="example ns 2”>
<ns:A>
<ns2:X>TEXT</ns2:X>
</ns:A>
<ns:B>
<ns2:Y>TEXT</ns2:Y>
<ns2:Z>TEXT</ns2:Z>
<ns2:P>TEXT</ns2:P>
</ns:B>
</ns:FOO>`)
What i want is to make it like:
<?xml version="1.0" encoding="UTF-8"?>
<ns:FOO xmlns:ns=“example ns" xmlns:ns2="example ns 2">
<NEW-ELEMENT>
<NEW-SUB-ELEMENT>
<ANOTHER-NEW-SUB-ELEMENT>TEXT</ANOTHER-NEW-SUB-ELEMENT>
<NEW-SUB-ELEMENT>
</NEW-ELEMENT>
<ns:A>
<ns2:X>TEXT</ns2:X>
</ns:A>
<ns:B>
<ns2:Y>TEXT</ns2:Y>
<ns2:Z>TEXT</ns2:Z>
<ns2:P>TEXT</ns2:P>
</ns:B>
</ns:FOO>
This is what I am trying to do:
const reqNode = xmlDoc.get('//ns:FOO', { FOO: 'example'})
const doc = new x.Document();
doc
.node('NEW-ELEMENT')
.node('Service', "TI")
.parent()
.node('NEW-SUB-ELEMENT')
.node('ANOTHER-NEW-SUB-ELEMENT', 'TEXT')
.parent()
.parent().toString()
reqNode.addChild(doc)
However it seems to make it like:
<?xml version="1.0" encoding="UTF-8"?>
<ns:FOO xmlns:ns=“example ns" xmlns:ns2="example ns 2">
<ns:A>
<ns2:X>TEXT</ns2:X>
</ns:A>
<ns:B>
<ns2:Y>TEXT</ns2:Y>
<ns2:Z>TEXT</ns2:Z>
<ns2:P>TEXT</ns2:P>
</ns:B>
<NEW-ELEMENT>
<NEW-SUB-ELEMENT>
<ANOTHER-NEW-SUB-ELEMENT>TEXT</ANOTHER-NEW-SUB-ELEMENT>
<NEW-SUB-ELEMENT>
</NEW-ELEMENT>
</ns:FOO>
Any ideas, where I'm doing wrong?
Much appreciated
node(...) always adds the node at the end. If you want to insert an element elsewhere you can use addPrevSibling(siblingNode) to insert a node before the Element that was called on. So here you would first find the ns:A Element and then call that function on it (you probably have to construct the child element explicitly so it can be passed as an argument).
Have a XML string like below:
<stages>
<params/>
<test description=""/>
</stages>
I want to add the following XML string after <test desc.../> tag OR before the end of stages i.e. </stages>
<stage id="myId" level="1">
and all subsequent stages.
Post-addition it should like
<stages>
<params/>
<test description=""/>
<stage id="myId" level="1"/>
<stage id=.../>
...
</stages>
I am trying to do something like this:
var stageNode = document.createTextNode(
"<stage id=\"myId\" level=\"1\">")
);
var root = document.getElementsByTagName("test").parentNode;
console.log(document.getElementsByTagName("test")); //<-- giving [] in console log and root is undefined; though the element is there
var stages = root.getElementsByTagName("stage");
root.insertBefore(stageNode,stages.nextSibling);
How can I do this in JavaScript or JQuery?
Using DocumentBuilder or DocumentBuilderFactory is giving me "Unexpected identifier" error. Is there an easier way to do the above using document builder in Javascript (as in Java)?
With jQuery it might look like so:
function addStage(xmlDocument, stageElement){
var parent = $(xmlDocument).find("test").parent(); //picks <test>'s parent
parent.append(stageElement); //appends stageElement to parent
}
var xmlString = '<stages><params/><test description=""/></stages>'; //your XML string
var xmlDocument = $.parseXML(xmlString); //parses your XML string and returns XML document
$("#addStage").click(function(){
var id = $("#stageId").val();
var stageElement = $("<stage id=\"" + id + "\"></stage>"); //creates new element
addStage(xmlDocument, stageElement);
console.log(xmlDocument);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.3/jquery.min.js"></script>
Stage ID: <input type="text" id="stageId" /> <input type="button" id="addStage" value="Add stage" />
Open browser's console to see the results.
Using Plain Old JavaScript:
var text = "<stages><params/><test description=\"\"/></stages>";
var parser = new DOMParser();
var xmlDoc = parser.parseFromString(text,"text/xml");
var newNode = xmlDoc.createElement("stage");
newNode.setAttribute("id", "myId");
newNode.setAttribute("level", "1");
xmlDoc.documentElement.appendChild(newNode);
newNode = xmlDoc.createElement("stage");
newNode.setAttribute("id", "myId2");
newNode.setAttribute("level", "2");
xmlDoc.documentElement.appendChild(newNode);
console.log(new XMLSerializer().serializeToString(xmlDoc.documentElement));
For reference on adding node at a particular position, refer XML DOM Add Nodes
Ive been following the examples from w3 schools on using a xpath to navigate through my xml document however all i get back from iterateNext() is null. Below is my blog.xml file.
<blog
xmlns ="http://www.w3schools.com"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="blogschema.xsd">
<Title>My blog</Title>
<Entry>
<Heading id="101">week1</Heading>
<body>
<text>enter text right here</text>
<pictures>pictures in the body</pictures>
</body>
<labels>Seperate labels with commas</labels>
<date> 20121119</date>
</Entry>
</blog>
This is my html script, the while statement is never reached as result always returns null, this maybe something that im overlooking, but i assumed that if it was on w3 schools it should really work.
xmlDoc=loadXMLDoc("blog.xml");//loads xml file
//loadXmlContent(xmlDoc); using xml dom
path="/blog/Title"
if(document.implementation && document.implementation.createDocument)
{
var nodes = xmlDoc.evaluate(path, xmlDoc, null, 5, null);
alert(nodes);
var result = nodes.iterateNext();
while (result)
{document.write(result.childNodes[0].nodeValue);}
}
</script>
There is a default namespace declaration xmlns="http://www.w3schools.com" in the input that you need to take into account with e.g.
var nodes = xmlDoc.evaluate("df:blog/df:Title", xmlDoc, function(prefix) { if (prefix === "df") return "http://www.w3schools.com"; }, 5, null);
var result;
while ((result = nodes.iterateNext()) != null)
{
document.write(result.textContent);
}
This is my exact xml file:
<?xml version="1.0" ?>
<blah_de_blah>
<unblocker_details table_color="#F2F0FF" type="zip" alt_link="http://g.org/288"
link_for_deletion="3-QQ5DJoa-AWFT7a9" comment="zippy" />
<unblocker_details table_color="#FFFFFF" type="Webpage" alt_link="http://www.gg.com"
link_for_deletion="4-rOX2brr-2qQeGY3" comment="test" />
</blah_de_blah>
I have successfully gotten it via an ajax request, then did this:
var xmlDoc=null;
var parser = new DOMParser();
xmlDoc = parser.parseFromString(data, "text/xml");
and now I need to get each of those values from unblocker_details into a variable:
for example:
the_table_color=table_color;
the_type =type;
etc
Please also check if I declared the xml properly as I am very new to this.
Thanks!
Something like this:
var nodes = xmlDoc.getElementsByTagName("unblocker_details");
for(i=0; i< nodes.length; i++) {
the_table_color = nodes[i].getAttribute("table_color");
// get other attributes the same way
}
You can use this http://www.w3schools.com/ajax/ajax_xmlfile.asp