i trying compare 2 xelements () below:
xelement parentitems =
<tcm:listitems xmlns:tcm="http://www.tridion.com/contentmanager/5.0"> <tcm:item title="070_page" modified="2016-01-06t18:08:36" cp1="-6185, intro" cp2="-6182, article body" cp3="-14507, article body1" cp4="-14430, article body2" cp5="-14530, article body3" cp6="-7064, article body4" cp7="-14529, article body5" cp8="-7065, article body6" cpcount="8" /> <tcm:item title="080_page" modified="2015-04-23t13:27:59" cp1="-6302, intro" cp2="-6193, article body" cpcount="2" /> <tcm:item title="release notes" modified="2016-01-07t21:25:43" cp1="-6303, release notes intro" cp2="-6196, release notes article body" cpcount="2" /> </tcm:listitems>
xelement childitems =
<tcm:listitems xmlns:tcm="http://www.tridion.com/contentmanager/5.0"> <tcm:item title="070_page" modified="2016-06-06t19:36:35" cp1="-6185, intro" cp2="-6147, media & delivery intro" cp3="-6182, article body" cp4="-14507, article body1" cp5="-14430, article body2" cp6="-14530, article body3" cp7="-7064, article body4" cp8="-14529, article body5" cp9="-7065, article body6" cpcount="9" /> <tcm:item title="080_page" modified="2016-02-09t21:03:32" cp1="-6302, intro" cp2="-6193, article body" cpcount="2" /> <tcm:item title="release notes" modified="2016-02-09t21:03:33" cp1="-6303, release notes intro" cp2="-6196, release notes article body" cpcount="2" /> <tcm:item title="release notes1" modified="2016-03-09t22:00:13" cp1="-6303, release notes intro" cp2="-6196, release notes article body" cpcount="2" /> </tcm:listitems>
i want result (first 1 has different cpcount, , second 1 new element in childitems):
xelement diff =
<tcm:listitems xmlns:tcm="http://www.tridion.com/contentmanager/5.0"> <tcm:item title="070_page" modified="2016-06-06t19:36:35" cp1="-6185, intro" cp2="-6147, media & delivery intro" cp3="-6182, article body" cp4="-14507, article body1" cp5="-14430, article body2" cp6="-14530, article body3" cp7="-7064, article body4" cp8="-14529, article body5" cp9="-7065, article body6" cpcount="9" /> <tcm:item title="release notes1" modified="2016-03-09t22:00:13" cp1="-6303, release notes intro" cp2="-6196, release notes article body" cpcount="2" /> </tcm:listitems>
i've tried xmldiff api no luck. can loop through , results, list can huge (3000+). there best way handle this?
ok, here code - in console app created using vs2015 (could non-optimal works - 2 expected elements in end - leaving refactoring homework):
class program { //this convenient storage of collected data //also avoid additional dictionary lookups , processing internal class elementattributes { public xelement element { get; set; } public dictionary<string, string> attributes; public elementattributes(xelement element) { this.element = element; this.attributes = new dictionary<string, string>(); } } static void main(string[] args) { //loading xml elements embedded resources xelement parentitems = xelement.parse(resourcexml.parentitems); xelement childitems = xelement.parse(resourcexml.childitems); xelement diff = xelement.parse(@"<tcm:listitems xmlns:tcm=""http://www.tridion.com/contentmanager/5.0"" ></tcm:listitems>"); var parentdictionary = builddictionary(parentitems); var childdictionary = builddictionary(childitems); //perform diff foreach (string key in childdictionary.keys) { elementattributes parentelementattributes; if (parentdictionary.trygetvalue(key, out parentelementattributes)) { //found title/key in parent, compare attributes foreach (var childattribute in childdictionary[key].attributes) { var attributename = childattribute.key; var childattributevalue = childattribute.value; string parentattributevalue; if (parentelementattributes.attributes.trygetvalue(attributename, out parentattributevalue)) { //found attribute in parent, compare value if(childattributevalue == parentattributevalue) { //values equal, compare other attributes continue; } } //parent not have attribute or //different value in child -> show in diff diff.add(childdictionary[key].element); //do not compare other attributes break; } //child may have missing attributes, in parent //note: example not present use case scenario foreach (var parentattribute in parentelementattributes.attributes) { string attributename = parentattribute.key; if (!childdictionary[key].attributes.containskey(attributename)) { //attribute found in parent, not in child diff.add(childdictionary[key].element); break; } } } else { //not found in parent, show in diff diff.add(childdictionary[key].element); } } } private static dictionary<string, elementattributes> builddictionary(xelement element) { xnamespace tcm = "http://www.tridion.com/contentmanager/5.0"; var resultdictionary = new dictionary<string, elementattributes>(); foreach (xelement childelement in element.elements(tcm + "item")) { var attributedictionary = new elementattributes(childelement); foreach (xattribute attribute in childelement.attributes()) { string[] excludedcolumns = {"title", "modified"}; if (excludedcolumns.contains(attribute.name.localname)) { continue; } attributedictionary.attributes.add(attribute.name.localname, attribute.value); } resultdictionary.add(childelement.attribute("title").value, attributedictionary); } return resultdictionary; } }