Tuesday, May 29, 2012

Using the Case Resolution in Workflows via a Custom Workflow Activity

One feature missing from CRM is the ability to use the information from the Case Resolution in a workflow. A popular application of this would be sending an email when the case is closed that includes the description field from the Case Resolution form. In the past a work around was to include a custom field on the Case itself that contained the resolution notes. These would need to be entered prior to closing the case and then manually copied and pasted into the corresponding field on the resolution. With a custom workflow activity, we can retrieve this value and use it directly in an email that is sent from a workflow.

If you haven’t already done so, download a copy of the Microsoft CRM 2011 SDK.

The Code

Start off by creating a new Class Library project in Visual Studio 2010.

Add the following references to your project:

· Microsoft.Xrm.Sdk (from the SDK)

· Microsoft.Xrm.Sdk.Workflow (from the SDK)

· System.Activities

· System.Runtime.Serialization

Add this file from the SDK sample code to use the default early bound CRM entities:

· \sdk\samplecode\cs\helpercode\myorganizationcrmsdktypes.cs

Add a strong name key file:

· Project -> Properties -> Signing -> Sign the assembly

o New – give it a name and do not protect with password

Make sure your code looks similar to this:

using System.Activities;
using System.Linq;
using Microsoft.Xrm.Sdk;
using Microsoft.Xrm.Sdk.Query;
using Microsoft.Xrm.Sdk.Workflow;

namespace MyCustomWorkflow
{
public class GetCaseResolution : CodeActivity
{
protected override void Execute(CodeActivityContext exContext)
{
IWorkflowContext context =
exContext.GetExtension<IWorkflowContext>();
IOrganizationServiceFactory sFactory =
exContext.GetExtension<IOrganizationServiceFactory>();
IOrganizationService service =
sFactory.CreateOrganizationService(context.UserId);

QueryByAttribute query = new QueryByAttribute();
query.Attributes.AddRange(new string[] { "incidentid" });
query.ColumnSet =
new ColumnSet(new string[] { "description" });
query.EntityName = IncidentResolution.EntityLogicalName;
query.Values.AddRange(new object[] {
context.PrimaryEntityId });

EntityCollection result = service.RetrieveMultiple(query);
IncidentResolution resolution =
(IncidentResolution)result.Entities.FirstOrDefault();
CaseResolution.Set(exContext, resolution.Description);
}

[OutputAttribute("CaseResolution")]
public OutArgument<string> CaseResolution { get; set; }
}
}


Make sure your class inherits from the CodeActivity class and specifies the OutputAttribute property.

Build and resolve any errors.

Deployment

You can use the Plugin Registration Tool that is included in the SDK to deploy the new Custom Workflow Activity to CRM.

Once connected:

Register -> Register New Assembly

CaseResolution1

Browse to the DLL output from your project, once selected and everything is correct with the code the assembly details should be populated automatically and already checked.

Select Register Selected Plugins

CaseResolution2

Usage

Create a new workflow for the Case entity and set the criteria when you want this to execute. In this case we’ll use when the record status changes.

Create a Check Condition step to see if the Status = Resolved

Next you should see a new step at the bottom of the list the references your Custom Workflow Activity, add it under the check condition step so that it fires if the case s resolved.

Add the next step of Send E-mail, in the properties of the email you should now have a local value that corresponds to the custom activity. It can be assigned to a field like any other form field.

Assign the value to the email body, set any other fields and then Save and Close.

CaseResolution3

CaseResolution4

Activate your workflow so you should be all set. When a Case is closed as Resolved, an email should be created that includes the description from the Case Resolution.