• No results found

Creating Workflows for SharePoint

SharePoint 2003 is a huge improvement over SharePoint 2001. This does not mean to say that everybody was happy with SharePoint 2003 at first; people who just looked at the out-of-the- box workflow capabilities in SharePoint 2003 were disappointed. They were like taking a step back, compared to SharePoint 2001. But even 2001’s workflow capabilities were not that great. The general perception was and is that the workflow capabilities of SharePoint 2003 are not satisfactory in most cases, a gap which has been filled by a range of third-party vendors.

It is possible to create your own custom workflows. SharePoint 2003 is shipped with the Event Sink API that allows you to make use of the SharePoint event model and provides custom handlers for the various events that fire because of some user action. Developers can create managed code assemblies that define handlers for these events and then bind the handlers to document libraries. The event handlers can call into the SharePoint object model to access the configuration and content databases directly. Event handlers can also be used to invoke external services; in such cases SharePoint can be used to display the information retrieved from other systems. The SharePoint Event Sink API offers an excellent opportunity to create advanced workflows using Windows Workflow Foundation.

Note You need to be aware that you can only use Windows Workflow Foundation in combination with

Windows SharePoint Services 2003 environments, not in SharePoint Portal Server 2003 environments. This is caused by the fact that Windows Workflow Foundation requires the presence of .NET Framework 2.0, which is not supported in SharePoint Portal Server 2003 environments. If you want more information about this topic, refer to Chapter 1.

In the example described in this section, we are going to build a simple workflow that starts when a document is added to a specific SharePoint document library. The workflow will then create a new task in the tasks list. When the status property of the document is set to approved, the workflow will set the task to complete. We will use Windows Workflow Foundation to create the workflow and use SharePoint document event handling to fire an event whenever a change is made to documents in the SharePoint document library.

The first thing you need to do is to create a SharePoint document library and enable it for event handling. Create a document library called RFPDocuments. This is just a test name that indicates the document library is used to contain imaginary requests for proposal documents. You will also need to enable document event handling for this specific document library. If you want to do this, you need to enable event handling for the entire SharePoint virtual server. Follow these steps to do so:

1. Click Start ➤ All Programs ➤ Administrative Tools ➤ SharePoint Central Administration.

2. Click Configure Virtual Server Settings in the Virtual Server Configuration section.

3. Click the name of the virtual server you want to configure—in our case that will be Default Web Site.

4. Click Virtual Server General Settings in the Virtual Server Management section.

C H A P T E R 4 ■ W I N D O W S W O R K F L O W F O U N D A T I O N 163

5. At the bottom of the Virtual Server General Settings page, go to the Event Handlers section and click On (see Figure 4-14). Click OK.

Figure 4-14. The Event Handlers section on the Virtual Server General Settings page

Next, create your own document event handler. Follow these steps:

1. Open Visual Studio 2005 and create a new class library by clicking File ➤ New ➤ Project. Choose to create a C# Class Library and give it the following name: MyWorkflowSolution.

2. Add a reference to the Microsoft.SharePoint assembly that can be found at [drive letter]:\ Program Files\Common Files\Microsoft Shared\web server extensions\60\ISAPI. Right-click References in the Solution Explorer and choose Add Reference. Browse to the Microsoft.SharePoint assembly and click OK.

3. Add a reference to the System.Workflow.Runtime assembly that is located at

[drive letter]:\Program Files\Reference Assemblies\Microsoft\WinFx\v3.0. Right-click References in the Solution Explorer and choose Add Reference. Browse to the

System.Workflow.Runtime assembly and click OK.

4. Right-click the class1.cs and choose Rename. Give the class the following name:

RFPEvent.cs.

The RFPEvent class has to implement the IListEventSink interface to be able to respond to events within a SharePoint document library. The IListEventSink interface contains the

OnEvent() event handler. The OnEvent() event handler contains one parameter, a Microsoft. SharePoint.SPListEvent. This method responds to one of the following changes that occur to a document in a document library:

Checked in: A document is checked in to a document library. Checked out: A document is checked out from a document library.

Check out cancelled: A check out is cancelled and changes made to the checked out docu-

ment are undone.

Copied: A document in a document library is copied. Deleted: A document is deleted from a document library.

Edited: An existing document or the value of a custom column in the library is edited. Moved: A document is moved in a document library.

Renamed: A document is renamed in a document library. Uploaded: A new document is saved to a document library.

164 C H A P T E R 4 ■ W I N D O W S W O R K F L O W F O U N D A T I O N

The following code block contains the code for your RFPEvent class. The OnEvent() event handler checks which SharePoint list event has taken place. In the case of an Update or an

Insert event, it creates an instance of the WorkflowRuntime type that represents the workflow runtime engine, and starts your custom workflow. The CreateWorkflow() method contains two arguments; the first one is the type of workflow to create, and the second argument is a

Dictionary object that can contain any parameter of any data type. You will add the SharePoint

listEvent object, containing metadata about the SharePoint list event, and the type of event that has taken place (Insert or Delete) to this dictionary, because you will use them later in your workflow code:

using System; using System.Collections.Generic; using System.Text; using Microsoft.SharePoint; using System.Workflow.Runtime; namespace LoisandClark.MyWorkflowSolution {

public class RFPEvent : IListEventSink {

public void OnEvent(SPListEvent listEvent) {

if (listEvent.Type == SPListEventType.Insert || ➥ listEvent.Type == SPListEventType.Update)

{

Dictionary<string, object> objParameters = new Dictionary<string, object>(); objParameters.Add("ListEvent", listEvent);

objParameters.Add("ListEventType", listEvent.Type); WorkflowRuntime wfRuntime = new WorkflowRuntime(); WorkflowInstance wfInstance = ➥ wfRuntime.CreateWorkflow(typeof(SPSWorkflow.RFPWorkflow), objParameters); wfInstance.Start(); } } } }

The next step is to strong name the assembly and install it in the Global Assembly Cache. You can do this by following these steps: