I have an XML File resembling the following:
<root>
<parent label="parent1">
<child label="child1">
<element1>data</element1>
<element2>data</element2>
...
<grandchildren>
<grandchild label="grandchild1">
<elementa>data</elementa>
<elementb>data</elementb>
</grandchild>
</grandchildren>
</child>
<child label="child2">
<element1>data</element1>
<element2>data</element2>
...
<grandchildren>
<grandchild label="grandchild2">
<elementa>data</elementa>
<elementb>data</elementb>
</grandchild>
</grandchildren>
</child>
</parent>
</root>
The XML serves as data source for a treeview. Users can select a parent there, and the properties of the parent will be displayed in a listview (which uses a LINQdataview as data source). I’m pulling the data out using a linq query. However, I would like to display the GrandChildren in a seperate control (a Telerik grid).
I created a new XMLDataSource in the listview cell, which will pull its data from the child’s xPAth (something I add in the code, see below), as well as the intended grid. The grid is set to have the XMLDataSource as its DataSourceID.
Here’s the code I use to pull the data in the Selecting event:
protected void listsSource_Selecting(object sender, LinqDataSourceSelectEventArgs e) {
XElement rootElement = XElement.Load(MapPath(TreeSource.DataFile));
parentElement = rootElement.XPathSelectElement("//parent[@label='" + tvw.SelectedNode.Text + "']");
var query = from element in parentElement.DescendantsAndSelf("child")
select new {
element1 = element.Element("element1").Value,
element2 = element.Element("element1").Value,
xPathAddress = "//parent[@label='" + tvw.SelectedNode.Text + "']",
grandchildrenXPath = "//parent[@label='" + tvwMaterials.SelectedNode.Text + "']" + "/grandchildren"
};
e.Result = query;
}
Here’s the code from the ASPX:
<td rowspan="7" style="border-style: solid; border-width: thin" align="center">
<telerik:RadGrid ID="gridRelatives" runat="server" DataSourceID="XmlRelatives" >
</telerik:RadGrid>
<asp:XmlDataSource ID="XmlRelatives" runat="server"
DataFile="~/XML/Data/relatives.xml" xPath='<%# Eval("grandchildrenPath") %>'></asp:XmlDataSource>
</td>
However, this leads to a “Cannot find any bindable properties in an item from the datasource” error, and I am guessing that this is because of attempting to load the XML dynamically, causing it not to trigger when the ListSource selecting event fires.
Should I instead load the data in a seperate query statement, or am I overlooking something fairly simple?
Any help would be greatly appreciated, as this has had me stumped for a while now 🙂
Thanks.
Update:
Tried adding a second linq query to the selecting code, in an attempt to set the XPath part of a second XMLDataSource, but this gives me another error. Code:
var query2 = from element in parentElement.DescendantsAndSelf("child")
select new {
grandchildrenXPath = "//parent[@label='" + tvw.SelectedNode.Text + "']" + "/grandchildren"
};
myThickness.XPath = query2.ToString();
myThickness.DataBind();
Error:
‘System.Linq.Enumerable+WhereSelectEnumerableIterator2[System.Xml.Linq.XElement,<>f__AnonymousType31[System.String]]’ has an invalid token.
Commenting the new lines has things working again.
I’m still hoping to find a solution for this. I imagined that building the xPath dynamically would be a great way to accomplish this, but obviously that is a no-go. What am I not seeing here?
I ended up figuring out a workaround by adding a new XMLDataSource and loading that within the listsSource_Selecting event.
I tried doing this before, but placed the code above the LINQ query that feeds the ListView this time. That does not throw any errors anymore.