以下内容是对SPEventReceiver的一点总结
一、概述
五种事件处理器基类:
1、SPItemEventReceiver
2、SPListEventReceiver
3、SPEmailEventReceiver
4、SPWebEventReceiver
5、SPWorkflowEventReceiver
SPItemEventReceiver包含如下方法:
Name |
Description |
This member is reserved for internal use and is not intended to be used directly from your code. |
|
Obsolete. Prevents events from being raised. (Inherited from SPEventReceiverBase.) |
|
Obsolete. Enables events to be raised. (Inherited from SPEventReceiverBase.) |
|
(Inherited from Object.) |
|
(Inherited from Object.) |
|
(Inherited from Object.) |
|
(Inherited from Object.) |
|
Handles the asynchronous event that occurs after an item is added. |
|
Handles the synchronous event that occurs before an item is added. |
|
Handles the asynchronous event that occurs after an attachment is added to an item. |
|
Handles the synchronous event that occurs before an attachment is added to an item. |
|
Handles the asynchronous event that occurs after an attachment is removed from an item. |
|
Handles the synchronous event that occurs before an attachment is removed from an item. |
|
Handles the asynchronous event that occurs after an item is checked in. |
|
Handles the asynchronous event that occurs after an item is checked out. |
|
Handles the synchronous event that occurs before an item is checked in. |
|
Handles the synchronous event that occurs before an item is checked out. |
|
Handles the asynchronous event that occurs after an item is deleted. |
|
Handles the synchronous event that occurs before an item is deleted. |
|
Handles the asynchronous event that occurs after a file in a document library is converted from one type to another. |
|
Handles the asynchronous event that occurs after a file is moved. |
|
Handles the synchronous event that occurs before a file is moved. |
|
Handles the asynchronous event that occurs after an item is unchecked out. |
|
Handles the synchronous event that occurs before an item checkout is discarded. |
|
Handles the asynchronous event that occurs after an item is changed. |
|
Handles the synchronous event that occurs before an item is changed. |
|
Occurs after an item or file version is deleted. |
|
Occurs when an item or file version is being deleted. |
|
(Inherited from Object.) |
|
(Inherited from Object.) |
每个方法都有一个SPItemEventProperties参数,包含很多关于提交记录的相关信息。
具体信息请参考MSDN文档 http://msdn.microsoft.com/en-us/library/microsoft.sharepoint.spitemeventproperties_members.aspx
二、结构分析(以SPItemEventReceiver为例):
namespace CustomEventReceiver.EventReceiver1 { /// <summary> /// 列表项事件 /// </summary> public class EventReceiver1 : SPItemEventReceiver { /// <summary> /// 正在添加项. /// </summary> public override void ItemAdding(SPItemEventProperties properties) { base.ItemAdding(properties); } } }
生成的事件处理代码,继承自SPItemEventReceiver,重写ItemAdding(添加Item前的事件)代码。
<Elements xmlns="http://schemas.microsoft.com/sharepoint/"> <Receivers ListTemplateId="100"> <Receiver> <Name>EventReceiver1ItemAdding</Name> <Type>ItemAdding</Type> <Assembly>$SharePoint.Project.AssemblyFullName$</Assembly> <Class>CustomEventReceiver.EventReceiver1.EventReceiver1</Class> <SequenceNumber>10000</SequenceNumber> </Receiver> </Receivers> </Elements>
Receiver通常包含五个子节点:
1、Name:定义唯一名字信息;
2、Type:定义一个事件类型,如果添加新的事件类型,需要再添加一个Receiver子节点;
3、Assembly:定义sharepoint程序集清单;Sharepoint Assembly
4、Class:包含带命名空间的事件处理器类的类名;
5、SequenceNumber:如果有多个事件处理器绑定到同一个列表的时候通过此节点值判断执行顺序
如果希望值绑定在某个特定的列表,可以通过修改以下内容:
<Receivers ListUrl="Lists/列表名">
通过添加data标签,可以像事件处理器传递少量数据信息:
<Elements xmlns="http://schemas.microsoft.com/sharepoint/"> <Receivers ListTemplateId="100"> <Receiver> <Name>EventReceiver1ItemAdding</Name> <Type>ItemAdding</Type> <Assembly>$SharePoint.Project.AssemblyFullName$</Assembly> <Class>CustomEventReceiver.EventReceiver1.EventReceiver1</Class> <SequenceNumber>10000</SequenceNumber> <Data> Data information<Data> </Receiver> </Receivers> </Elements>
读取方法:
String data=properties.ReceiverData;
三、事件绑定
方法一:Feature绑定
在Element.xml文件中定义内容,部署。
缺陷:通过XML配置,无法将内容类型和事件处理器进行绑定,而通过对象模型的方式可以。
方法二:用sharepoint对象模型进行绑定
参考代码:
Type receiverType = typeof(事件查看器类); //typeof取得系统对类的描述 using (SPSite site = new SPSite("http://localhost/sites")) { SPWeb web = site.RootWeb; SPList list = web.Lists.TryGetList("列名"); SPEventReceiverDefinitionCollection receiverCol = list.EventReceivers; SPEventReceiverDefinition recevierDef = receiverCol.Add(); recevierDef.Assembly = receiverType.Assembly.FullName; recevierDef.Class = "CustomEventReceiver.EventReceiver1.EventReceiver1"; recevierDef.Type = SPEventReceiverType.ItemAdding; recevierDef.SequenceNumber = 10000; recevierDef.Update(); }
在绑定前要做个判断,确保同一个事件处理器没有和相应的列表绑定,加入如下代码:
SPEventReceiverDefinitionCollection receiverCol = list.EventReceivers; foreach (SPEventReceiverDefinition def in receiverCol) { if (def.Assembly == receiverType.Assembly.FullName) { def.Delete(); break; } }
四、其他应用
After事件:注册同步After事件的方法(默认为异步):
1、XML绑定
<Elements xmlns="http://schemas.microsoft.com/sharepoint/"> <Receivers ListTemplateId="100"> <Receiver> <Name>EventReceiver1ItemAdding</Name> <Type>ItemAdding</Type> <Assembly>$SharePoint.Project.AssemblyFullName$</Assembly> <Class>CustomEventReceiver.EventReceiver1.EventReceiver1</Class> <SequenceNumber>10000</SequenceNumber> <Synchronization>Synchronous</Synchronization> </Receiver> </Receivers> </Elements>
2、SharePoint对象模型
Type receiverType = typeof(事件查看器类); //typeof取得系统对类的描述 using (SPSite site = new SPSite("http://localhost/sites")) { SPWeb web = site.RootWeb; SPList list = web.Lists.TryGetList("列名"); SPEventReceiverDefinitionCollection receiverCol = list.EventReceivers; foreach (SPEventReceiverDefinition def in receiverCol) { if (def.Assembly == receiverType.Assembly.FullName) { def.Delete(); break; //删除后需要加上break,否则foreach会在删除后报错 } } SPEventReceiverDefinition recevierDef = receiverCol.Add(); recevierDef.Assembly = receiverType.Assembly.FullName; recevierDef.Class = "CustomEventReceiver.EventReceiver1.EventReceiver1"; recevierDef.Type = SPEventReceiverType.ItemAdding; recevierDef.SequenceNumber = 10000; recevierDef.Synchronization=SPEventReceiverSynchronization.Synchronous; recevierDef.Update(); }
避免二次触发引起的无限循环调用(如调用Update方法修改数据后继续调用Update方法,一直到资源超限),使用EventFiringEnabled属性:
public override void ItemUpdated(SPItemEventProperties properties) { this.EventFiringEnabled = false; properties.ListItem["Title"] = "Title"; properties.ListItem.Update(); this.EventFiringEnabled = true; }
如果在更新有版本控制的列表项时不希望更新版本,则调用SPListItem的另一个Update方法:
properties.ListItem.UpdateOverwriteVersion();
SPListItem还有另外一种更新方式SystemUpdate(),可以再更新数据时不触发其他关联字段。
MSDN解释:
Updates the database with changes that are made to the list item without changing the Modified or Modified By fields.
SystemUpdate方法有两个重载,带有bool参数的重载可以指定是否生成新的版本。
public override void ItemUpdated(SPItemEventProperties properties) { this.EventFiringEnabled = false; properties.ListItem["Title"] = "Title"; properties.ListItem.SystemUpdate(); this.EventFiringEnabled = true; }