I am trying to parse a package xml and make it as json string using DOM Parser in salesforce.But I am not getting result of JSON string.Below is my code:
VF Page:
<apex:page applyHtmlTag="true" controller="Doccox">
<apex:form >
<apex:inputFile value="{!fil}" id="xmlfile"/>
<div>XML TO JSON PARSE TOOL FOR PACKAGE.XML</div>
<apex:actionFunction name="ctrlRead" action="{!parse}"/>
<apex:commandButton onclick="ctrlRead();" value="Parse" id="theButton"/>
</apex:form>
</apex:page>
Apex class:
public class Doccox{
public Blob fil {get;set;}
public string st {get;set;}
public String jsonstring {get;set;}
Map<string,string> listmap = new Map<string,string>();
List<PackagedMembers> pm = new List<PackagedMembers>();
public class wrapxml
{
public decimal version;
public List<PackagedMembers> types;
}
public class PackagedMembers
{
public string members;
public string name;
}
public void parse() {
string st=fil.toString();
system.debug('@@@@access_string@@'+st);
Dom.Document doc = new Dom.Document();
doc.load(st);
Dom.XMLNode add =doc.getRootElement();
system.debug('++++rootnodename+++'+add.getname());
walkThrough(add);
}
public String walkThrough(DOM.XMLNode node) {
String result = '\n';
if (node.getNodeType() == DOM.XMLNodeType.ELEMENT) {
for(Dom.XMLNode ch : node.getChildElements())
{
if(ch.getName()=='member')
{
map<string,string> memstr = new Map<string,string>();
memstr.put(string.valueOf(ch.getParent()),ch.getText());
system.debug('++++memstr+++'+memstr);
if(ch.getName()=='name')
{
map<string,string> memstrx = new Map<string,string>();
memstrx.put(string.valueOf(ch.getParent()),ch.getText());
system.debug('++++memstrx+++'+memstrx);
if(memstr.keySet()==memstrx.keySet())
{
listmap.put(memstr.get(string.valueOf(ch.getParent())),memstrx.get(string.valueOf(ch.getParent())));
system.debug('++++listmap+++'+listmap);
}
}
}
result += walkThrough(ch);
}
}
for(string sy :listmap.keyset())
{
PackagedMembers pmo = new PackagedMembers();
pmo.members=sy;
pmo.name=listmap.get(sy);
pm.add(pmo);
system.debug('++++pm+++'+pm);
}
wrapxml wp = new wrapxml();
wp.version =37.0;
wp.types=pm;
String jsonstring = JSON.serialize(wp);
system.debug('++++jsonstring+++'+jsonstring);
return jsonstring;
}
}
Best Answer
Your parsing code has a number of issues related to parsing the XML.
First, the inner members are called "members", not "member", so this line needs to be fixed:
Next, if ch.getName() is equal to 'members', it won't be equal to 'name', because that'll be in a later pass; you can't nest your if statements like that.
Your next problem is then going to be here:
because it's just building really big, useless keys for you.
Also, you never actually assigned the value back to jsonString, so the results are getting lost.
I get where you're trying to go with this, but XML parsing is non-trivial to get right.
Also, "members" may be an array once converted, which is why it's pluralized.
I'm not sure exactly how to fix your code, but I happen to have some public code that I'll share with you: XmlToJSON.
Since we can't readily determine if we'll need the array syntax, and because my class automatically generates arrays, we can start with the automatic untyped JSON parsing:
There's some additional processing you need to do if you want something other than a JSON string. To get it into a wrapper, you have to be aware that
types
will be either an Object or an Array, depending on if it has one or more elements. Similarly, members will either be an Object or an Array.As a minor optimization in this case, we can alter XmlToJson to assume that elements ending with S will always be an array:
The only change here is to swap out the automatic list aggregation with automatic list assumption. This works out well for the package.xml, because the naming convention happens to work out that way.
Here's an XML file I use by default:
And here's the resulting output:
There's also a corresponding unit test in the original link, above, but you'll have to modify it in order to maintain 100% coverage.