ASPX templates
Version 7.x > ASPX templates > TreeProvider.SelectNodes sorting by ClassName before OrderBy clause View modes: 
User avatar
Member
Member
shauna.gordon-fahlgren - 12/13/2012 10:24:51 AM
   
TreeProvider.SelectNodes sorting by ClassName before OrderBy clause
I found this in the 6.x forums, which shows the behavior in a CMSListMenu, but I'm also seeing it when dealing with TreeProvider.SelectNodes, directly.

It seems that when multiple document types are involved, the code is either generating more than one query, then concatenating the results, or is first ordering by ClassName.

This is my code:
protected void RenderNavigation(string section) {
NodeSelectionParameters navParams = new NodeSelectionParameters();
navParams.AliasPath = "/FPCEvents/" + section + "/%";

// Same behavior regardless of which ClassNames directive I use
//navParams.ClassNames = "CMS.MenuItem;CMS.Folder";
navParams.ClassNames = "*";

navParams.MaxRelativeLevel = 1;

// Same behavior even when "NodeLevel, NodeOrder, NodeName" is used
navParams.OrderBy = "NodeOrder";

navParams.SelectOnlyPublished = true;
navParams.Where = "DocumentMenuItemHideInNavigation = 0";

// create a TreeProvider instance
UserInfo ui = UserInfoProvider.GetUserInfo("administrator");
TreeProvider tree = new TreeProvider(ui);
TreeNodeDataSet ds = tree.SelectNodes(navParams);
foreach (TreeNode node in ds) {
string href = "/Subsite/" + section + "/" + node.NodeAlias;
navLeft.InnerHtml += "<li><a href=\"" + href + "\">" +
(node.DocumentMenuCaption == string.Empty ? node.DocumentName : node.DocumentMenuCaption) + "</a></li>";
}
}

(Yes, it does pretty much the same thing that CMSListMenu does. However, due to the structure of my site, CMSListMenu was not adequate, so I did this. It works, except for the order of the links generated.)

I have the following structure in CMSDesk:

Subsite
- Folder
- Page
- Page
- Folder
- Page
- Page

What the code generates:

- Folder
- Folder
- Page
- Page
- Page
- Page

It seems this behavior was fixed for CMSListMenu for version 7, so is there a way I can mimic the desired (CMSListMenu) behavior for ordering in my custom code?

User avatar
Member
Member
shauna.gordon-fahlgren - 12/13/2012 11:47:43 AM
   
RE:TreeProvider.SelectNodes sorting by ClassName before OrderBy clause
I am able to work around this limitation by putting the following code between filling the dataset and populating the list:
// TreeProvider doesn't order things correctly when multiple ClassNames are involved
// To make matters worse, each ClassName is a separate table
// So we need to merge the tables so we can sort them properly
for (int i = 1; i < ds.Tables.Count; i++) {
ds.Tables[0].Merge(ds.Tables[i]);
// Delete the extra tables, so they aren't used by the CMSListMenu Control
ds.Tables.Remove(ds.Tables[i]);
}
ds.Tables[0].DefaultView.Sort = "NodeOrder";

I also found that the CMSListMenu control is still usable in my case, though with some unintuitive behavior:

If the control can get data without codebehind, it will ignore any codebehind you try to add. However, if the parameters you specify in the .aspx file do not return any results, then it will fallback to your custom codebehind.

Therefore, I set up my code to bind as the datasource to the CMSListMenu, instead of creating the list items by hand. Without the table merging and sorting code, though, the custom code still "sorts" by ClassName before anything else. I suspect this is due to the query returning in separate tables.