Hi all,
What I am publishing here is some undocumented issuesinvolving navigation items in publishing enabled sites.
When you have publishing feature enabled in MOSS sites publishing
pages from “pages” library automatically set to be displayed in navigation. So far
– nothing is new.
What you didn’t know is that when you try to access these
items in the site’s navigation in order to perform a simple task such as hiding
a page from navigation, changing a page’s display order and other tasks
you are in to a nasty surprise!
What you want to do is to:
A: Get an instance of the current web site (SPWeb web = SPControl.GetContextWeb(Context) from within a web part.
B: Get the left navigation nodes collection (using web.Navigation.QuickLaunch)
C: Loop over navigation items and move/hide/rename etc… (foreach(SPNavigationNode node in web.Navigation.QuickLaunch))
But wait –
If you just created the site and added some pages to it you
are in to a nasty surprise as I promised. You will notice that none of your
pages that are displayed in the navigation are in that collection!
Actually the collection should be empty unless you added
some other items to it manually.
You will also notice a very weird behavior of
SharePoint that as soon as you open the “Navigation” page in the UI of
that site and make any change and save it – since that change all items suddenly
appear in the navigation collection as you expected them to from the
beginning!
My customer and I had to create pages and sites by code and
change their ordering by the same code. Of course we didn’t plan on browsing
each site and making a change manually – so we had to find a solution for that
issue.
The following code fixes that “problem”. It goes over a publishing
site pages library and make sure that all pages navigation nodes were created
and available for change using your code.
This took me quite a lot of time to investigate and find
this solution since it is not documented anywhere!!! So enjoy…
SPWeb curWeb = GetWeb();
PublishingWeb pWeb = PublishingWeb.GetPublishingWeb(curWeb);
//Get existing links in navigation
//(so we know if to create new or move existing link)
List<string> existing = new List<string>();
foreach(SPNavigationNode node in curWeb.Navigation.QuickLaunch)
existing.Add(node.Url.ToLower());
//Loop for each page in pages library
foreach(SPListItem item in pWeb.PagesList.Items)
{
//Get a fresh copy of web – curWeb =
//new SPSite(curWeb.Site.ID).OpenWeb(curWeb.ID);...
curWeb = Utilities.Refresh(curWeb);
PublishingPage pp = PublishingPage.GetPublishingPage(item);
SPNavigationNode nn = null;
string ppUrl = pp.Uri.AbsolutePath.ToLower();
//check if exists in navigation
if (existing.Contains(ppUrl))
{
continue;
}
else//add a new navigation item
{
//not? add it.
nn = new SPNavigationNode(pp.Title, ppUrl);
nn = curWeb.Navigation.QuickLaunch.AddAsFirst(nn);
//here is the trick –
//We mark the navigation item as type “Page”.
nn.Properties["NodeType"] = "Page";
nn.Update();
}
curWeb.Update();
}