XElement parsing from XDocument, far below, repeated - c#

I would like to make my result like this;
// Boo1
// Boo2
// Boo3
// ....
// ..
// .
Frome here..
//<xliff xmlns:sdl="http://sdl.com/FileTypes/SdlXliff/1.0" xmlns="urn:oasis:names:tc:xliff:document:1.2" version="1.2" sdl: version="1.0">
// <sdl:seg-defs>
// <sdl:seg id="1" conf="Translated">
// <sdl:prev-origin origin="source">
// <sdl:prev-origin origin="source">
// <sdl:prev-origin origin="tm" percent="99">
// <sdl:prev-origin/>
// <sdl:value key="Hash">Foo1</sdl:value>
// <sdl:value key="Created">Boo1</sdl:value>
//...
//..
//.
I've tried like this but, it failed.
string myResult = "";
XDocument myDoc = XDocument.Load(myPath);
XNamespace myNS = "http://sdl.com/FileTypes/SdlXliff/1.0";
foreach (var x in myDoc.Descendants(myNS + "seg-defs"))
myResult += x.Value.ToString() + "\n";
MessageBox.Show(myResult);
Following are not what I wanted..
// Foo1Boo1
// Foo2Boo2
// ....
// ..
// .
Help, please.
Thanks

Try following :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
List<XElement> segments = doc.Descendants().Where(x => x.Name.LocalName == "seg").ToList();
List<XElement> created = segments.Descendants().Where(x => (x.Name.LocalName == "value") && ((string)x.Attribute("key") == "Created")).ToList();
string results = string.Join("\n", created.Select(x => (string)x));
}
}
}

Related

How to get the node value by passing type in XDocument C#

I have below XML.
<subscription>
<subscription_add_ons type="array">
<subscription_add_on>
<add_on_code>premium_support</add_on_code>
<name>Premium Support</name>
<quantity type="integer">1</quantity>
<unit_amount_in_cents type="integer">15000</unit_amount_in_cents>
<add_on_type>fixed</add_on_type>
<usage_percentage nil="true"></usage_percentage>
<measured_unit_id nil="true"></measured_unit_id>
</subscription_add_on>
</subscription_add_ons>
My XMLParse function
public XNode GetXmlNodes(XElement xml, string elementName)
{
List<string> addOnCodes= new List<string>();
//elementName = "subscription_add_ons ";
var addOns = xml.DescendantNodes().Where(x => x.Parent.Name == elementName).FirstOrDefault();
foreach (XNode addOn in addOns)
{
//Needed to do something like this
/*var len = "add_on_code".Length + 2;
var sIndex = addOn.ToString().IndexOf("<add_on_code>") + len;
var eIndex = addOn.ToString().IndexOf("</add_on_code>");
var addOnCode = addOn.ToString().Substring(sIndex, (eIndex - sIndex)).Trim().ToLower();
addOnCodes.Add(addOnCode);*/
}
As mentioned in comments by #JonSkeet, I updated my snippet as below.
var addOns = xml.Descendants(elementName).Single().Elements();
foreach (XNode addOn in addOns)
{
/*addon = {<subscription_add_on>
<add_on_code>premium_support</add_on_code>
<name>Premium Support</name>
<quantity type="integer">1</quantity>
<unit_amount_in_cents type="integer">15000</unit_amount_in_cents>
<add_on_type>fixed</add_on_type>
<usage_percentage nil="true"></usage_percentage>
<measured_unit_id nil="true"></measured_unit_id>
</subscription_add_on>} */
//how to get the addOnCode node value ?
var addOnCode = string.Empty;
addOnCodes.Add(addOnCode);
}
But what I need is from the passed XML, get all the nodes of type subscription_add_on then get the value contained in add_on_code & add it to string collection.
Or in general get the value of node by passing type ? Tried with the available methods coming from VS Intellisense but not getting the exact method that can do this?
Thanks!
Here is solution with Xml Linq (XDOCUMENT) :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication107
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
var results = doc.Descendants("subscription_add_on").Select(x => new
{
add_on_code = (string)x.Element("add_on_code"),
name = (string)x.Element("name"),
quantity = (int)x.Element("quantity"),
amount = (int)x.Element("unit_amount_in_cents"),
add_on_type = (string)x.Element("add_on_type")
}).ToList();
}
}
}

Get the content of a child node from the parent selected by the listbox

i would ask you if it's possible to do the following task:
this is my xml file:
<SETTING_LIST>
<setting>
<name>first</name>
<enable>the command...</enable>
<disable>the command...</disable>
<check>the command...</check>
<word>first</word>
<ifchecktrue>true</ifchecktrue>
<usegrep>true</usegrep>
</setting>
<setting>
<name>second</name>
<enable>the command...</enable>
<disable>the command...</disable>
<check>the command...</check>
<word>first</word>
<ifchecktrue>true</ifchecktrue>
<usegrep>true</usegrep>
</setting>
</SETTING_LIST>
so the user will select from a listbox the name of the parent node like "first" or "second", than i'd need something that give me back the content as string of the child node . I tried something like this but it doesen't work.
private void checkbtn_Click(object sender, EventArgs e)
{
string selectednode = Convert.ToString(listBox1.SelectedItem);
string prompt;
XmlDocument doc = new XmlDocument();
doc.Load("dati.txt");
XmlNode node = doc.SelectSingleNode("setting/" + selectednode + "/check");
prompt = node.InnerText;
MessageBox.Show(prompt);
}
Thank you for your help!!
Use xml linq :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq ;
namespace ConsoleApplication1
{
public class Program
{
const string FILENAME = #"c:\temp\test.xml";
public static void Main()
{
XDocument doc = XDocument.Load(FILENAME);
string name = "first";
Dictionary<string, string> dict = doc.Descendants("setting")
.Where(x => (string)x.Element("name") == name).FirstOrDefault()
.Elements().GroupBy(x => x.Name.LocalName, y => (string)y)
.ToDictionary(x => x.Key, y => y.FirstOrDefault());
}
}
}

How to take value based on previous node from the given xml file

I have an xml file shown below which is small part of big xml file
<?xml version="1.0" encoding="utf-8" ?>
<xn:VsDataContainer id=test">
<xn:attributes>
<xn:vsDataType>vsDataEUtranCellFDD</xn:vsDataType>
<es:crsGain>0</es:crsGain>
<es:pciConflictCell>
<es:enbId>66111</es:enbId>
<es:cellId>3</es:cellId>
</es:pciConflictCell>
<es:pdcchLaGinrMargin>100</es:pdcchLaGinrMargin>
<es:lbEUtranAcceptOffloadThreshold>50</es:lbEUtranAcceptOffloadThreshold>
<es:pdcchCfiMode>5</es:pdcchCfiMode>
<es:cellId>0</es:cellId>
<es:zzzTemporary21>-2000000000</es:zzzTemporary21>
</xn:attributes>
</xn:VsDataContainer>
I am using following code to get values of crsGain and cellId.But cellIdiam not getting the desired one.. ie i need cellId if the previous node is pdcchCfiMode .so here i should get value as 0 ,but i am getting 3 which is the first in the sequence .How to solve this issue.Snippet Code i am using is
if (vsDataEUtranCellFDD.Any()) {
List<CellName> cells = vsDataEUtranCellFDD.Select(x => new CellName() {
cellId= (int)x.Descendants().Where(a => a.Name.LocalName == "cellId").FirstOrDefault(),
crsGain = (int)x.Descendants().Where(a => a.Name.LocalName == "crsGain").FirstOrDefault(),
EDIT
this cellid can happen in middle also ,only differentiation is previous node which is pdcchCfiMode
You can skip the elements while they are not equal to pdcchCfiMode then take the first element. Something like this:
cellId = (int)x.Descendants().SkipWhile(a => a.Name.LocalName != "pdcchCfiMode")
.Skip(1).Take(1).FirstOrDefault(),
Try code below
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
List<XElement> attributes = doc.Descendants().Where(x => x.Name.LocalName == "attributes").ToList();
XNamespace esNs = attributes.FirstOrDefault().GetNamespaceOfPrefix("es");
List<CellName> cells = attributes.Select(x => new CellName() {
cellId = (int)x.Element(esNs + "cellId"),
crsGain = (int)x.Element(esNs + "crsGain")
}).ToList();
}
}
public class CellName
{
public int cellId { get; set; }
public int crsGain { get; set; }
}
}

xml, xmlreader read only specific part using c#

I'm using c# to get a parameters from xml file. My problem is I want to read only for the current program parameters. (v1.0, v1.1, v1.2... )
<?xml version="1.0" encoding="utf-8" ?>
<ApplicationPool>
<Resource Version="V1.0">
<Input>2000</Input>
<Input>210</Input>
<Input>65000</Input>
</Resource>
<Resource Version="V1.1">
<Input>2500</Input>
<Input>400</Input>
<Input>130000</Input>
</Resource>
</ApplicationPool>
using (XmlReader reader = XmlReader.Create("testXml.xml"))
{
while (reader.Read())
{
if (reader.IsStartElement())
{
if (reader["Version"] == actualVersion)
{
//??
}
}
}
}
XDocument doc = XDocument.Load("testXml.xml")
var result = doc.Root.Descendants("Resource")
.Where(x => x.Attribute("Version")!= null
&& x.Attribute("Version").Value == actualVersion);
This will return you all Resource nodes in which the Attribute Version == actualVersion. After that you can do whatever you want with the node.
if (reader["Version"] == actualVersion)
{
while (reader.ReadToFollowing("Input"))
{
string value = reader.ReadElementContentAsString();
// or
int value = reader.ReadElementContentAsInt();
}
}
You can use the Xml Linq Approach like:
var xmlFile= XElement.Load(xmlString);
var actualVersion = "V1.1";
var requiredXmlData = xmlFile.Elements("Resource").Where(c=>c.Attribute("Version").Value==actualVersion );
using System.Xml;
...
string actualVersion="V1.1";
XmlDocument rssDoc = new XmlDocument();
rssDoc.Load("testXML.xml");
XmlNodeList _ngroups = rssDoc.GetElementsByTagName("Resource");
for(int i=0;i<=_ngroups.Count-1;i++)
{
if(_ngroups[i].Attributes[0].InnerText.ToString()==actualVersion)
{
for(int j=0;j<=_ngroups[i].ChildNodes.Count-1;j++)
Console.WriteLine(_ngroups[i].ChildNodes[j].InnerText);
}
}
...
Using combination of XmlReader and xml linq
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Linq;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XmlReader reader = XmlReader.Create(FILENAME);
while (!reader.EOF)
{
if (reader.Name != "Resource")
{
reader.ReadToFollowing("Resource");
}
if (!reader.EOF)
{
XElement resource = (XElement)XElement.ReadFrom(reader);
string version = (string)resource.Attribute("Version");
}
}
}
}
}

Scrub data from xml using c# and xpath

I am trying to delete/Scrub few elements from the xml using c# with the help of xpaths. I am trying to replace the value of social_security_number with "Scrubbed" in both the child tags named "Customers". But my program is landing in many errors. Please correct me.
xml :
<?xml version="1.0" encoding="utf-16"?>
<LoanApplications xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" id="12345" bundle_id="12225" version="1.0">
<LoanApplication payment_call="False" version="1.0" app_status="I" perform_dupe_check="1" bundle_id="12225" UpdateReviewed="True">
<Customers id = "12" name = "krish" ssn = "123456789">
</LoanApplication>
<LoanApplication deal_type="RESPONSE" payment_call="True" version="1.0" app_status="I" perform_dupe_check="1" bundle_id="12225" UpdateReviewed="True">
<Customers id = "12" name = "krish" ssn = "123456789">
</LoanApplication>
</LoanApplications>
Program :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml;
namespace ConsoleApplication2
{
class Program
{
static void Main(string[] args)
{
XmlDocument doc = new XmlDocument();
doc.Load("mytestfile.xml");
doc.SelectSingleNode("/LoanApplications/LoanApplication[#deal_type="%DealTypeALL%"]/LoanApplicationStates/LoanApplicationState/Customers/Customer[#customer_id="%CustIDALL%"]/").Attributes["social_security_number"].InnerText = "Scrubbed";
doc.Save("mytestfile.xml");
}
}
}
var doc = XDocument.Parse(System.IO.File.ReadAllText("C:\\Users\\jason\\Desktop\\Input\\2015\\09\\03\\mytestfile.xml"));
foreach (var customer in doc.Descendants("Customer"))
{
var ssn = customer.Attribute("social_security_number");
if (ssn != null)
{
ssn.Value = "scrubbed";
}
}
doc.Save("file.xml");
You have few needed nodes instead of one. Thus, you should use SelectNodes instead of SelectSingleNode method.
var doc = new XmlDocument();
doc.Load("mytestfile.xml");
var ssns = doc.SelectNodes("LoanApplications/LoanApplication/LoanApplicationStates/LoanApplicationState/Customers/Customer/#social_security_number");
foreach (XmlAttribute ssn in ssns)
ssn.InnerText = "Scrubbed";
doc.Save("mytestfile.xml");
You can use shorter XPath with descendants. But it has less performance.
var ssns = doc.SelectNodes("//Customer/#social_security_number");
This is real easy with xml linq
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XDocument doc = XDocument.Load(FILENAME);
List<XElement> ss = doc.Descendants().Where(x => x.Attribute("social_security_number") != null).ToList();
foreach (XElement s in ss)
{
s.Attribute("social_security_number").Value = "Scrubbed";
}
}
}
}

Categories