In SharePoint 2007 it is possible to handle events that occur on list items. These types of events come in two flavours: synchronous and asynchronous.
-
Synchronous: happens 'before' the actual event, you have the HttpContext and you can show an error message in the browser and cancel the event
-
Asynchronous: happens 'after' the actual event, there's no HttpContext and you cannot directly show an error message or cancel the event
By subclassing Microsoft.SharePoint.SPItemEventReceiver you can override the desired "event" methods.
-
Synchronous: methods ending with '-ing' (ItemAdding, ItemUpdating, ...)
-
Asynchronous: methods ending with '-ed' (ItemAdded, ItemUpdated, ...)
If you implement an override method you might want to place your code between the following lines to avoid raising other events unwantedly (and possibly causing an infinite loop).
this.DisableEventFiring();
...
this.EnableEventFiring();
Each override method has a parameter of type Microsoft.SharePoint.SPItemEventProperties that contains the item and event properties available for use. There's a bug in the SPItemEventProperties.AfterProperties dictionary that appears empty for synchronous events but it isn't. You can iterate over the dictionary to read and write to this collection ! This means that you can modify some of the inputted metadata before the actual item is stored in the list.
The thing to remember here is that the dictionary uses the field internal name as key, so field 'My custom field' could have an internal name such as 'My_x0020_custom_x0020_field'.
You can get the internal name of a field by using a tool like Stramit SharePoint 2007 Caml Viewer or as follows:
- Navigate in the browser to the 'Edit Page' of the List or Site Column
- The URL contains the internal field name
Here's a code snippet that works for synchronous events that outputs the contents of the property dictionary to the screen. It cancels the event so it's not very useable for other purposes but it could come in handy to actually see what is used for metadata.
using System;
using System.Collections;
using System.Text;
using Microsoft.SharePoint;
namespace Vandest
{
public class MyTestEventReceiver : SPItemEventReceiver
{
public override void ItemAdding(SPItemEventProperties properties)
{
StringBuilder sb = new StringBuilder();
foreach (DictionaryEntry de in properties.AfterProperties)
{
string key = de.Key.ToString();
string value = de.Value.ToString();
sb.AppendLine(key + " -- " + value);
}
properties.Cancel = true;
properties.ErrorMessage = sb.ToString();
}
}
}