Monday, July 21, 2008

Setting Master Page For An Individual Page

Settings the master page for a SharePoint 2007 publishing website can be done out of the box using the UI or programmatically. For guidance on how to set the MasterPage programmatically, Mike Hodnick has a good post.

However, if you want to set the Master Page for an individual page or pages within a website, things get tricky.

The @Page directive exposes the MasterPageFile property, but the value is immediately overwritten in the Pre-Init event of the publishing pages base class (PublishingLayoutPage).

To resolve this, we will have to set the MasterPageFile through code. Andrew Connell provides a nice tutorial on how to create a code-behind class for a layout page.

Once you have created the code-behind class, override the OnPreInit event method and set the MasterPageFile property immediately after the base.OnPreInit(e) call.

protected override void OnPreInit(EventArgs e)
{
     base.OnPreInit(e);
     // override the MasterPageFile which is set in the Pre-Init with our own.
     MasterPageFile = "mymaster.master";
}

Friday, July 18, 2008

Content Type is still in use error

I spent an hour trying to delete a content type through the SharePoint 2007 UI with no success. I kept getting an "Content Type is still in use" exception even though I had deleted all layout pages that used that content type. I even went as far as de-activating the feature that installs the layout pages in the first place.

Finally I figured out that I have to remove the content type from any document library that contained any of the layout pages attached to the offending content type.

In my case, I had a publishing web site. So I clicked on "View All Site Content" and selected the Pages document library. From there, I went to the Settings page and, under the Content Types section, clicked on the content type I wanted to remove and deleted it.

Wednesday, July 16, 2008

Programmatically Creating a List from a ListTemplate

Adding a list to a website in SharePoint 2007 from a ListTemplate is fairly straightforward. But there is one quirk that you need to be aware of.

The templates are located in SPWeb.ListTemplates. The indexer for the ListTemplateCollection has two overloads. The first one uses the index value of the ListTemplate. Since you will probably not know that value, the second overload comes into play. This one uses the "Name" of the ListTemplate.

Here's the catch. What Microsoft really means by "Name" is "Display Name". This seems like more than just bad naming conventions, but bad practice as well. As the "Name" of the ListTemplate should be the key.

Monday, July 7, 2008

Namespaces matter

Thanks to Paul's post, I realized that SharePoint 2007 pays closer attention to namespaces than I realized. Your feature and it's feature receiver must have the same root namespace or the solution will not deploy.

I am still not sure what the difference is, because I could deploy to my local environment using WSPBuilder without issue. But when I tried to deploy to our test environment using the standard stsadm commands it failed with the following exception:

"Failed to create feature receiver object from assembly 'MyAssemblyInfo'... : System.ArgumentNullException: Value cannot be null."

Thursday, July 3, 2008

Create an Anonymous Access Survey Programmatically

Their are several good examples on how to use the UI to make a SharePoint 2007 survey work for anonymous users.  So I took what I learned from them and came up with this method for doing the same thing programmatically.

The main catch was the AnonymousPermMask64 flags.  The only ones that you see in the UI are the AddListItems and ViewListItems.  But there are several others that are set behind the scenes.

 

 
private void AddNewSurvey(SPWeb web, SPListTemplate surveyTemplate)
{
    web.Lists.Add("Survey Title", "Survey Description", surveyTemplate);
    
    // once we have created the survey, find it again so we can set the permissions
    SPList surveyList = web.Lists["Survey Title"];
    web.AllowUnsafeUpdates = true;
    // break the role inheritance so we can set our own permissons
    if (!surveyList.HasUniqueRoleAssignments)
        surveyList.BreakRoleInheritance(true);
    surveyList.ReadSecurity = 2; // can read their own
    surveyList.WriteSecurity = 2; // can edit their own
    // set the permission flags for Add and View plus some internal flags
    surveyList.AnonymousPermMask64 =
        (SPBasePermissions.Open |
        SPBasePermissions.OpenItems |
        SPBasePermissions.ViewFormPages |
        SPBasePermissions.UseClientIntegration |
        //SPBasePermissions.UseRemoteAPIs |
        SPBasePermissions.ViewListItems |
        SPBasePermissions.AddListItems);
    surveyList.Update();
}