问题
I'm trying to create a sitemap for my MOSS publishing site, i've got two approaches but seem to be stuck with both.
My first approach is to use the PortalSiteMapProvider, which is already created and nicely cached...
PublishingWeb rootWeb = PublishingWeb.GetPublishingWeb(SPContext.Current.Site.RootWeb);
//Get the URL of the default page in the web
string defaultPageUrl = rootWeb.DefaultPage.ServerRelativeUrl;
PortalListItemSiteMapNode webNode = (PortalListItemSiteMapNode)PortalSiteMapProvider.CurrentNavSiteMapProviderNoEncode.FindSiteMapNode(defaultPageUrl);
HttpContext.Current.Response.Output.WriteLine("Top Level: " + webNode.Title.ToString() + "<br />");
//iterate through each one of the pages and subsites
foreach (SiteMapNode smnTopLevelItem in webNode.ParentNode.ChildNodes)
{
HttpContext.Current.Response.Output.WriteLine(smnTopLevelItem.Title.ToString() + "<br />");
//if the current sitemap has children, create a submenu for it
if (smnTopLevelItem.HasChildNodes)
{
foreach (SiteMapNode smnChildItem in smnTopLevelItem.ChildNodes)
{
HttpContext.Current.Response.Output.WriteLine(smnChildItem.Title.ToString() + "<br />");
}
}
}
HttpContext.Current.Response.End();
but this seems to return everything in the site collection (e.g. lists, surverys). I only want to show the Sharepoint webs.
My other approach was to use this piece of code..
SPSite siteCollection = new SPSite("http://example.org");
SPWebCollection sites = siteCollection.AllWebs;
foreach (SPWeb site in sites)
{
Console.WriteLine(site.Title.ToString() + " " + site.ServerRelativeUrl.ToString());
}
Which is perfect, apart from the problem of returning all the webs in a flat list.
Ideally I want to be able to add indentation to show child webs.
回答1:
Generally it's a bad idea to use the object model for recursion. It's extremely slow and resource-intensive to do this. PortalSiteMapProvider
is pre-cached for you and can tear through an entire site structure in milliseconds.
Regarding your question about SPSite.AllWebs
, that property does return a flat list of all webs. That's what it's for. If you want a list of only the immediate child webs, use the SPSite.RootWeb.Webs
property. Recurse over each SPWeb
in the .Webs
property, and call their .Webs
property in turn to get a tree-view.
Also, when dealing with the object model, make sure to DISPOSE EVERY WEB AND SITE. This will cause epic bad problems if you don't. This includes disposing every web in the .Webs
collection, even if you haven't touched it.
Edit:
To get the PortalSiteMapProvider to return only webs, set its IncludePages
property to false
.
回答2:
Have you tried checking the type of every node in the foreach loop using the PortalSiteMapNode.Type property and displaying only nodes of type NodeTypes.Area?
回答3:
thanks for the replys everyone, this is what I came up with
public ListSiteMap()
{
PortalSiteMapProvider portalProvider1 = PortalSiteMapProvider.WebSiteMapProvider;
portalProvider1.DynamicChildLimit = 0;
portalProvider1.EncodeOutput = true;
SPWeb web = SPContext.Current.Site.RootWeb;
PortalSiteMapNode webNode = (PortalSiteMapNode)portalProvider1.FindSiteMapNode(web.ServerRelativeUrl);
if (webNode == null || webNode.Type != NodeTypes.Area) return;
Console.WriteLine(webNode.Title.ToString() + " - " + webNode.Description.ToString());
// get the child nodes (sub sites)
ProcessSubWeb(webNode);
}
private void ProcessSubWeb(PortalSiteMapNode webNode)
{
foreach (PortalSiteMapNode childNode in webNode.ChildNodes)
{
Console.WriteLine(childNode.Title.ToString() + " - " + childNode.Description.ToString());
//if the current web has children, call method again
if (childNode.HasChildNodes)
{
ProcessSubWeb(childNode);
}
}
}
I found these articles helped
http://blogs.msdn.com/ecm/archive/2007/05/23/increased-performance-for-moss-apps-using-the-portalsitemapprovider.aspx
http://blogs.mosshosting.com/archive/tags/SharePoint%20Object%20Model/default.aspx
http://www.hezser.de/blog/archive/tags/SPQuery/default.aspx
回答4:
You could use this tool:
http://realworldsa.blogspot.com/2010/12/new-tool-for-sharepoint-2007-and-2010.html
来源:https://stackoverflow.com/questions/1039448/creating-sharepoint-moss-sitemap