18 May 2011

Starting a workflow for the current InfoPath form item in code behind

If you have the requirement to be able to programmatically start a workflow from the code behind an InfoPath form template, then the following code might do the trick (which can be called say from a button click event).

You'll need to have a promoted field in your form template which stores a unique ID for the current form item. You can use the core ID field value provided by SharePoint or perhaps you generate your own unique reference number for the form, whichever you use it needs to uniquely identify the form in the library so we can get the current form item from code using SPQeury and can then spark off the workflow.




private bool StartWorkflow(SPContext ctx)
{
    bool restarted = false;
    string output = "";
    try
    {
        SPList myForms = ctx.Web.Lists["My Forms Library"];
        if (myForms != null)
        {

            ctx.Web.AllowUnsafeUpdates = true;
            SPListItem thisForm = GetCurrentListItem(myForms);
            if (thisForm != null)
            {
                // Get the workflow association template using the workflow name as displayed on the workflow setting page
                SPWorkflowAssociation associationTemplate = prForms.WorkflowAssociations.GetAssociationByName("My Workflow", System.Globalization.CultureInfo.CurrentCulture);
                if (associationTemplate != null)
                {
                    // Now try and start the workflow
                    SPWorkflow newWorkflow = ctx.Site.WorkflowManager.StartWorkflow(thisForm, associationTemplate, associationTemplate.AssociationData);
                    if (newWorkflow != null)
                    {
                        // Success
                        restarted = true;
                    }
                }
            }
        }
    }
    catch (Exception) { }

    return restarted;
}

private SPListItem GetCurrentListItem(SPList myForms)
{
    SPListItem currentItem = null;
    // Get unique ID of current form from a field in form template
    // This ID field must be promoted to the SharePoint list
    string itemId = GetFormFieldValue("/my:myFields/my:MyFormID");
    if (itemId != null && !itemId.Equals(""))
    {
        if (myForms != null)
        {
            SPQuery oQuery = new SPQuery();
            // Query the forms library to get the item where the unique form ID field equals itemId
            // Use the internal field name in the where clause!
            oQuery.Query = string.Format(
                    "{0}"
                    , itemId);
            oQuery.ViewFields = "";
            SPListItemCollection collListItems = prForms.GetItems(oQuery);
            if (collListItems != null && collListItems.Count > 0)
            {
                foreach (SPListItem oListItem in collListItems)
                {
                    // Should only be one result
                    currentItem = oListItem;
                    break;
                }
            }
        }
    }

    return currentItem;
}

private string GetFormFieldValue(string xPath)
{
    XPathNavigator xnDoc = this.MainDataSource.CreateNavigator();
    XPathNavigator xnMyField = xnDoc.SelectSingleNode(xPath, this.NamespaceManager);
    if (xnMyField != null)
    {
        return xnMyField.Value;
    }
    else
    {
        return string.Empty;
    }
}
   

No comments:

Post a Comment