It's a way of acting on events that happens to a Feature. These events are:
|
Method
|
|
Description
|
|
Installed
|
|
When a feature has been installed on the server / farm
|
|
Uninstalling
|
|
Before a feature is uninstalled from the server/farm
|
|
Activated
|
|
When a feature is activated for it's scope
|
|
Deactivating
|
|
Before a feature is deactivated for it's scope
|
So in the case of this example it's the activated scenario we're interested in. Every time our feature is activated we're going to hot wire all lookup-columns to point to the WebId of the root-web of the site collection
To create a Feature Receiver in Visual Studio create a class library project, add a reference to the Windows.SharePoint.Services assembly. Create new class (in this example I will call it SiteColumnFeatureReceiver) and make it inherit from SPFeatureReceiver. Now when we have the pluming done we'll override the FeatureActivated method. Then we're going to loop over all columns and find the ones that are lookup-columns and hook them up to the root-web. So, this is what it can look like:
using System;
using System.Globalization;
using System.Xml;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Administration;
namespace MyAssembly.MyFeatures
{
publicclass SiteColumnsFeatureReciver : SPFeatureReceiver
{
privateconststring CONST_LOOKUP = "Lookup";
privateconststring CONST_FIELD = "Field";
publicoverridevoid FeatureActivated(SPFeatureReceiverProperties properties)
{
SPWeb site = properties.Feature.Parent as SPWeb;
string webid;
SPElementDefinitionCollection elementDefinitionCollection =
properties.Definition.GetElementDefinitions(new CultureInfo(1033));
foreach (SPElementDefinition elementDefinition in elementDefinitionCollection)
{
if (elementDefinition.ElementType == CONST_FIELD)
{
XmlNode node = elementDefinition.XmlDefinition;
if (node.Attributes["Type"].Value == CONST_LOOKUP)
{
try
{
SPSite parent = properties.Feature.Parent as SPSite;
if (parent != null)
{
SPWeb web = parent.RootWeb;
webid = web.ID.ToString("D");
string fieldId = node.Attributes["ID"].Value;
SPFieldLookup lookup = (SPFieldLookup) web.Fields[new Guid(fieldId)];
lookup.LookupWebId = new Guid(webid);
lookup.Update(true);
}
}
catch (Exception e)
{
Console.WriteLine(e);
}
}
}
}
}
publicoverridevoid FeatureDeactivating(SPFeatureReceiverProperties properties)
{
}
publicoverridevoid FeatureInstalled(SPFeatureReceiverProperties properties)
{
}
publicoverridevoid FeatureUninstalling(SPFeatureReceiverProperties properties)
{
}
}
}
Make sure you sign the assembly then compile it and we have a Featere Receiver! Next step: Installation.
Deploy the assembly we just created to the GAC (either by copying it to C:\WINDOWS\Assembly or by using GacUtil.exe).
In our Feature.xml file that defines things like name, scope, included elements and such we have to hook up the newly created feature receiver.
<FeatureId="0916E74F-D036-40c1-8485-C8CDCEF028F2"
Title="My Fields Definition"
Description="Site columns added by Niklas"
Version="1.0.0.0"
Scope="Site"
Hidden="FALSE"
xmlns="http://schemas.microsoft.com/sharepoint/"
ReceiverAssembly="MyAssambly.MyFeatures, Version=1.0.0.0, Culture=neutral, PublicKeyToken=5534820fb2bf9b92"
ReceiverClass="MyAssambly.MyFeatures.SiteColumnsFeatureReciver">
<ElementManifests>
<ElementManifestLocation="fields.xml"/>
ElementManifests>
Feature>
The properties of importance in this regard is ofcource ReceiverAssebmly and ReceiverClass.
Now, copy we need to copy all our feature xml-files to C:\Program Files\Common Files\Microsoft Shared\web server extensions\12\TEMPLATE\FEATURES\SiteColumns. And let's install the feature.
stsadm -o insatllfeature -name SiteColumns
Now, every time someone hits the Activate button for our feature (or runs the stsadm -o activatefeature command) our code will be executed. Now in this example I only set the WebId of the lookup columns but you could ofcource do anything within the limits of the object model. For example create a few document library's with a certain structure...