Wednesday, December 5, 2007

Add a new Site Column to a Custom Site Content Type for existing sites

After modifying and redeploying your custom content type feature, run the following code to update your current site with the change.

SPWeb web = new SPSite("http://myCompany/sites/CompanyStuff/").OpenWeb();
//Content type to update
SPContentTypeId cTypeID = new SPContentTypeId("0x010100054553FEE9554f4182A551FC55544EEC");
//set the new field
SPField field = web.Fields["myCompanyNewField"];
//create a fieldLink to the new field
SPFieldLink fieldLink = new SPFieldLink(field);
//set the content type to update
SPContentType cType = web.ContentTypes[cTypeID];
//create a var to hold sealed value
bool bIsSealed = false;
//create a field collection for the currnet ctype
SPFieldCollection fieldCollection = cType.Fields;

//if the new field does not exist in this ctype, add it
if (!fieldCollection.ContainsField(field.Title))
{
//test for sealed cType, if so un-seal before making changes to the ctype
if (cType.Sealed)
{
bIsSealed = true;
cType.Sealed = false;
}

cType.FieldLinks.Add(fieldLink);

//if the ctype was sealed, we need to re-seal it
if (bIsSealed)
{
cType.Sealed = true;
}

cType.Update(true);

web.Close();
web.Dispose();



In the example, I know the content type exists in my site, if I was going to loop through many sites, I would test to see if the content type exists before proceeding.  Another thing to keep in mind is that, the new field being added must be added as a Site Column first.  To update existing sites with the new site column, see this



If the content type you are updating is Sealed or ReadOnly you must set Sealed and/or ReadOnly to false before trying to make any changes to the content type, just make sure to set them back to their original state before calling cType.Update().  In the above code I have only tested for Sealed.

No comments: