Scenario: I have a custom list definition based on which I want to create some lists and associate OOB approval workflow with them for content approval.
In the schema.xml file for my custom list definition (based documents library i.e., basetype=1), I set ModeratedList=“True” attribute among others (see in the code snippet below)
<List xmlns:ows="Microsoft SharePoint" Title="TestList" Direction="$Resources:Direction;" Url="TestList" BaseType="1"
xmlns="http://schemas.microsoft.com/sharepoint/" EnableContentTypes="TRUE" EnableMinorVersions="TRUE" VersioningEnabled="TRUE" DraftVersionVisibility="2" ModeratedList="TRUE”>
Now, I added a ListAdded event receiver that listens to my custom list definition,so whenever any list is created based on my custom list definition, the OOB approval workflow should be associated with the list.
Here is the code snippet that associates the OOB approval workflow with the list
///
/// Associate OOB Approval workflow with the list
///
///
public static void AssociateApprovalWorklowWithList(SPList list)
{
//variables
Guid listId = list.ID;
Guid webId = list.ParentWeb.ID;
Guid siteId = list.ParentWeb.Site.ID;
SPSite site = null;
SPWeb web = null;
try
{
site = new SPSite(siteId);
web = site.OpenWeb(webId);
bool allowUnsafeCurrent = web.AllowUnsafeUpdates;
web.AllowUnsafeUpdates = true;
list = web.Lists[listId];
//Get Approval Workflow Template Base Id
Guid workflowBaseId = new Guid("8ad4d8f0-93a7-4941-9657-cf3706f00"+ web.Language.ToString("X"));
//If workflow is already associated, don't re-associate
if (list.WorkflowAssociations.GetAssociationByBaseID(workflowBaseId) != null)
return;
//check if workflows feature is activated, if not activate the feature
SPFeature workflowsFeature = web.Site.Features[WorkflowId];
if (workflowsFeature == null)
web.Site.Features.Add(WorkflowId);
// Get workflow history and task list
SPList historyList = EnsureHistoryList(web);
SPList taskList = EnsureTasksList(web);
string workflowAssociationName = string.Format("{0} - Approval", list.Title);
SPWorkflowTemplate workflowTemplate = web.WorkflowTemplates.GetTemplateByBaseID(workflowBaseId);
if (workflowTemplate == null)
{
//Log exception
return;
}
workflowTemplate.AllowManual = false;
// Create workflow association
SPWorkflowAssociation workflowAssociation = SPWorkflowAssociation.CreateListAssociation(workflowTemplate,
workflowAssociationName, taskList, historyList);
var associationDataXml = XElement.Parse(workflowAssociation.AssociationData);
// Add workflow association to my list
list.WorkflowAssociations.Add(workflowAssociation);
//Set workflow association data
workflowAssociation.AssociationData = Add_Association_Data(web, associationDataXml);
// Enable workflow
if (!workflowAssociation.Enabled)
workflowAssociation.Enabled = true;
if (list.DraftVersionVisibility != DraftVisibilityType.Approver)
list.DraftVersionVisibility = DraftVisibilityType.Approver;
list.WorkflowAssociations.Update(workflowAssociation);
list.DefaultContentApprovalWorkflowId = workflowAssociation.Id;
list.Update();
web.AllowUnsafeUpdates = allowUnsafeCurrent;
}
catch (Exception ex)
{
//Log Exception
}
finally
{
//Dispose the objects
if (web != null)
web.Dispose();
if (site != null)
site.Dispose();
}
}
For the explanation of retrieving the workflow template id (line#23), please refer to my previous post here Associating OOB Approval workflow with custom list for different Locale (LCIDs)
Problem: Once I have deployed the solution and everything is hooked up, I create the list based on my custom list definition and the process ends with the following exception:
But when I go to the site, the list is created and workflow is associated properly.
Solution: After narrowing down the problem, I removed the ModeratedList attribute from List element in schema.xml file for custom list definition (shown in the first code snippet), enabled the content approval for the list in the code and redeployed the solution and everything worked !
Here is the code for enabling content approval through code (add this in the function defined above after setting DraftVersionVisibility property)
if(!list.EnableModeration)
list.EnableModeration = true;
Cheers
comments powered by Disqus