How to attach Event Receiver to SPList programmatically?

carruw picture carruw · May 22, 2012 · Viewed 16.1k times · Source

I'm working on a project i SharePoint 2010 where I have several under sites. each under site contain a list with news and I want to attach an Event Receiver to those lists.

The under sites and lists are created programmatically but I cannot attach the Event Receiver I have in my VS2010 Solution.

I've tried with this:

SPList list = new SPSite(siteURL).OpenWeb().Lists[listName]; 
SPEventReceiverDefinitionCollection eventReceivers = list.EventReceivers;

SPEventReceiverDefinition eventReceiver = eventReceivers.Add();
eventReceiver.Name = receiverName;
eventReceiver.Synchronization = SPEventReceiverSynchronization.Synchronous; 
eventReceiver.Type = SPEventReceiverType.ItemAdded;
eventReceiver.SequenceNumber = sequenceNumber; 
eventReceiver.Assembly = assemblyFullName;
eventReceiver.Class = assemblyClassName;
eventReceiver.Data = receiverData;

eventReceiver.Update();

But it does not work.

The error message is "Could not load file or assembly 'Projekt_Test1\, \, Version\=1.0.1777.23493\, Culture\=neutral\, PublicKeyToken\=49c7547d535382ab' or one of its dependencies. The given assembly name or codebase was invalid. (Exception from HRESULT: 0x80131047)"

Thanks for help.

Answer

Luis picture Luis · Oct 24, 2012

I end up creating a List Extension method for this:

public static void EnsureEventReceiver(this SPList list,IEnumerable<SPEventReceiverType> receiverTypes, Type eventHander, SPEventReceiverSynchronization synchronization, int sequenceNumber)
{
   foreach (SPEventReceiverType spEventReceiverType in receiverTypes)
   {
      string name = list.Title + spEventReceiverType.ToString();

      if (list.EventReceivers.Cast<SPEventReceiverDefinition>().All(i => i.Name != name))
      {
          SPEventReceiverDefinition eventReceiver = list.EventReceivers.Add();
          eventReceiver.Name = name;
          eventReceiver.Type = spEventReceiverType;
          eventReceiver.Assembly = eventHander.Assembly.FullName;
          eventReceiver.Class = eventHander.FullName;
          eventReceiver.SequenceNumber = sequenceNumber;
          eventReceiver.Synchronization = synchronization;
          eventReceiver.Update();
      }
   }    
}

Caveats, Limitations of this method:

  • Only one event per List, since this is good enough for me, if you need more then you need to pass the name as a parameter
  • Event handler methods are in the same class

You can use it like this:

list.EnsureEventReceiver(
     new[] { SPEventReceiverType.ItemAdded, SPEventReceiverType.ItemUpdated },
     typeof(NewsItemsHandler),
     SPEventReceiverSynchronization.Synchronous, 
     10000);