I am parsing through an xml doc and I need to get the value of a Property element. As of right now I have a line of code that returns this:
<Property name="ID" value="thevalueineed"/>
Here is my line of code used.
var ID = from el in linkedinfo.DescendantsAndSelf("Property")
where (string)el.Attribute("name") == "ID"
select el.Attributes("value").ToString();
What would be the next step I am missing that would I get thevalueineed from that Element that I have in var ID?
Just change your select as
select (string)el.Attribute("value")
A working code.
var xDoc = XDocument.Parse(#"<root><Property name=""ID"" value=""thevalueineed""/></root>");
var ID = from el in xDoc.Root.DescendantsAndSelf("Property")
where (string)el.Attribute("name") == "ID"
select (string)el.Attribute("value");
var val = ID.First();
This should work
var ID = from el in linkedinfo.Descendants("Property")
where el.Attribute("name").Value == "ID"
select el.Attribute("value").Value;
I personally like this method when reading XML files but I don't know if it will work with your XML file.
// Create a DataSet
DataSet ds = new DataSet();
// Get the data from the XML file
ds.ReadXml("C:\\myXMLFile.xml");
// Get values
foreach (DataRow dr in ds.Tables[0].Rows)
{
string value = dr["ID"].ToString();
}
select el.Attributes("value")
will return an a type
System.Linq.Enumerable.WhereSelectEnumerableIterator<System.Xml.Linq.XElement,System.Collections.Generic.IEnumerable<System.Xml.Linq.XAttribute>>
try this:
var ID = element.DescendantsAndSelf("Property").Where(x => x.Attribute("name").Value == "id").Select(x => x.Attribute("value")).First();
I would personally use .Value instead of casting to string:
XElement linkedTeethInfo = XElement.Parse(#"<Property name=""ID"" value=""thevalueineed""/>");
var ID = from el in linkedTeethInfo.DescendantsAndSelf("Property")
where el.Attribute("name").Value == "ID"
select el.Attribute("value").Value;
Console.WriteLine("ID: {0}", ID.First());
Created a small fiddle here: https://dotnetfiddle.net/mrSITM
Related
I try to parse an xml file with XDocument class, with criteria that if the child node matches a given string, its parent node is selected.
<SalesQuotes xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://api.some.com/version/1">
<Pagination>
<NumberOfItems>2380</NumberOfItems>
<PageSize>200</PageSize>
<PageNumber>1</PageNumber>
<NumberOfPages>12</NumberOfPages>
</Pagination>
<SalesQuote>
<Guid>825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a</Guid>
<LastModifiedOn>2018-01-09T12:23:56.6133445</LastModifiedOn>
<Comments>Please note:
installation is not included in this quote
</Comments>
</SalesQuote>
</SalesQuotes>
I tried using
var contents = File.ReadAllText(path: "test1.xml");
var doc = XDocument.Parse(contents);
var root = doc.Root;
var sq = root.Elements("SalesQuote");//return null
var theQuote = root.Elements("SalesQuote").Where(el => el.Element("Guid").Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a");//return null
var theAlternativeQuote =
from el in doc.Descendants("SalesQuote").Elements("Guid")
where el.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
select el;//return null
I can't seem to find what's wrong.
Any help is much appreciated! Thanks.
You ignored the namespace bro.
Do remove the xmlns attribute in your XML or try this:
var contents = File.ReadAllText("XMLFile1.xml");
var doc = XDocument.Parse(contents);
var root = doc.Root;
XNamespace ns = "http://api.some.com/version/1";
var sq = root.Descendants(ns + "SalesQuotes"); //return null
var theQuote = root.Elements(ns + "SalesQuote")
.Where(el => el.Element(ns + "Guid").Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"); //return null
var theAlternativeQuote =
from el in doc.Descendants(ns + "SalesQuote").Elements(ns + "Guid")
where el.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
select el; //return null
If you are not too concerned about keeping your current implementation, you could consider using a Typed DataSet and load your XML into fully typed, structured objects.
Querying those objects with Linq will be more straight forward than what I see in your current implementation.
You might also find this useful:
SO Question: Deserialize XML Document to Objects
yap, you're missing the namespace that you can grab with document.Root.GetDefaultNamespace()
// Load
var document = XDocument.Parse(xml);
var xmlns = document.Root.GetDefaultNamespace();
// Find
var query = from element in document
.Descendants(xmlns + "SalesQuote")
.Elements(xmlns + "Guid")
where element.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
select element;
I have the following xml file
<?xml version="1.0" encoding="utf-8"?>
<Launchpad>
<Shortcuts>
<Shortcut Id="1">
<Type>Folder</Type>
<FullPath>C:\bla\bla\bla</FullPath>
<Name>Proximity</Name>
</Shortcut>
<Shortcut Id="2">
<Type>Folder</Type>
<FullPath>C:\bla</FullPath>
<Name>Visual Studio 2017</Name>
</Shortcut>
</Shortcuts>
</Launchpad>
I am trying to deserialize to an object like this: (Tried query syntax first, didn't work either)
XDocument xd = XDocument.Load(FullPath);
// query syntax
//var shortcuts = (from s in xd.Descendants("Shortcuts")
// select new Shortcut()
// {
// Id = Convert.ToInt32(s.Attribute("Id")),
// TypeOfLink = GetTypeFromString(s.Descendants("Type")
// .First()
// .Value),
// FullPathToTarget = s.Descendants("FullPath")
// .First()
// .Value,
// Name = s.Descendants("Name").First().Value,
// }).ToList();
// method syntax
List<Shortcut> shortcuts = xd.Descendants("Shortcuts")
.Select(s =>
new Shortcut()
{
//Id = Convert.ToInt32(s.Attribute("Id")),
TypeOfLink = GetTypeFromString(s.Descendants("Type")
.First().Value),
FullPathToTarget = s.Descendants("FullPath")
.First().Value,
Name = s.Descendants("Name")
.First().Value,
}).ToList();
return shortcuts;
For some reason I only get a single shortcut object in the list. Also, for some reason, the s.Attribute("Id") is null.
If anyone has any suggestions to improve the linq query or why the attribute is not working it would be a great help
You have to read .Descendants("Shortcut") instead of .Descendants("Shortcuts").
Something like this:
List<Shortcut> shortcuts = xd.Descendants("Shortcut").Select(s =>
new Shortcut()
{
Id = s.Attribute("Id").Value,
TypeOfLink = s.Descendants("Type").First().Value,
FullPathToTarget = s.Descendants("FullPath").First().Value,
Name = s.Descendants("Name").First().Value,
}).ToList();
I get the full list by selecting the Shortcut as a descendant of Shortcuts.
Also, ID is an XAttribute so you cant convert it to int.
You need to use Value to get the attributes value.
XDocument xd = XDocument.Load(ms);
XElement root = xd.Document.Root;
var list = root.Descendants("Shortcuts").Descendants("Shortcut").Select(x =>
new Shortcut()
{
Id = Convert.ToInt32(x.Attribute("Id").Value),
TypeOfLink = GetTypeFromString(x.Descendants("Type")
.First().Value),
FullPathToTarget = x.Descendants("FullPath")
.First().Value,
Name = x.Descendants("Name").First().Value
}).ToList();
I need help. I'm trying to figure out a way to read inside a bracket like this one:
<group id = "56">
<name>Counter</name>
</group>
In the code, there are mulitiple places where the same pattern comes back, and I would like to get all the group id number's and their name.
This is my code:
XDocument doc = XDocument.Parse(_XmlFile);
var results = doc.Descendants("group").Select(x => new
{
id = (int)x.Attribute("id"),
name = x.Attribute("name").Value,
}).ToList();
Console.WriteLine(results);
Thanks
Your code looks quite OK, but name is an element and not an attribute, so it should be
XDocument doc = XDocument.Parse(_XmlFile);
var results = doc.Descendants("group").Select(x => new
{
id = (int)x.Attribute("id"),
name = (string)x.Element("name"),
}).ToList();
foreach (var x in results)
Console.WriteLine("id: {0} name: {1}", x.id, x.name);
Use GetElementsByTagName method.
Here is the microsoft article explaining it with examples.
https://msdn.microsoft.com/en-us/library/dc0c9ekk(v=vs.110).aspx
"Name" is not an attribute, but a child node. The solution is something like this:
XDocument doc = XDocument.Parse(_XmlFile);
var results = doc.Descendants("group").Select(x => new
{
id = int.Parse(x.Attribute("id").Value),
name = x.Descendants("name").First().Value
}).ToList();
I have a string like this:
var str = "<University id="1396677467961079" name="Oxford"/>";
I want to get value of id, so I could do this:
var id = str.Substring(16, 16);
but it is not a good way to get it. How can I get the value in a safer way?
You can use Linq to XML like this:
var str = "<University id=\"1396677467961079\" name=\"Oxford\"/>";
var el = XElement.Parse(str);
var attr = el.Attribute("id");
var id = attr != null ? attr.Value : string.Empty;
For an overview of Linq to Xml see this link.
i just stuck in an issue when ever i parse my XML like this using Xdocument :
XDocument xmldoc = XDocument.Load(datafromxml);
var data = from query in xmldoc.Descendants("Chapter")
select new MyEntityclass
{
Sampledata = (string)query.Element("SubChapter")
};
i got only one tag inner value from this. i.e from the first tag value only. remaining are skipped.
My XML is like :
<Chapter>
<SubChapter ChapterID="1"><![CDATA["Some data here 1"]]></SubChapter>
<SubChapter ChapterID="2"><![CDATA["Some data here 2"]]></SubChapter>
<SubChapter ChapterID="3"><![CDATA["Some data here 3"]]></SubChapter>
</Chapter>
when i checked in a debug i just got the value of "chapterid : 1". please help me to sort out this. thanks
Your query now only retreives (iterates) the outer node.
You need something like (untested)
var data = from query in xmldoc.Descendants("Chapter")
from chapter in query.Elements("SubChapter") // note the 's'
select new MyEntityclass
{
Sampledata = (string)chapter
};
var data = xmlDoc.Root
.Elements("SubChapter")
.Select(x => new MyEntityclass { Sampledata = (string)x });