Dynamics CRM 2011 – Closing all Related Activities for a Record

Roshan Mehta, 16 February 2012

The Case Management functionality in Dynamics CRM 2011 requires the need to close all related Activities for a Case before it can be resolved. To make this process easier, we decided to add a custom button to each Activity form ribbon so that when clicked, all other related open Activities would automatically be closed along with the Case. Here is how we can achieve this functionality using a plugin.

 Dynamics CRM 2011 – Closing all Related Activities for a Record

When an Activity record (Task, Phone Call, Letter, Fax etc) is saved, a plug-in fires to retrieve the associated Case based on the “regarding” field.  Once we have the Case, we can retrieve all associated open Activities for the Case using the following code snippet:        

private List<Entity> GetAssociatedActivities(EntityReference regarding)
        {
            QueryExpression query = new QueryExpression { EntityName = "activitypointer", ColumnSet = new ColumnSet(new string[] { "activitytypecode" }) };
            query.Criteria.AddCondition("regardingobjectid", ConditionOperator.Equal, regarding.Id);
            query.Criteria.AddCondition("statecode", ConditionOperator.NotEqual, 1);  //ignore completed
            EntityCollection collection = _sdk.RetrieveMultiple(query);
            return collection.Entities.ToList();
        }

The reason we query the “activitypointer” entity is so we don’t have to write separate queries for each activity type.

Next, we loop through the results so we can deactivate each of the related activities.  An important thing to note here is the data type of the activitytypecode field. Checking the database, we can see the following columns in the FilteredActivityPointer filtered view:

 Dynamics CRM 2011 – Closing all Related Activities for a Record

Notice how we have the activitytypecode and activitytypecodename fields. In order to deactivate each activity, we need to know the schema names for every specific activity type. On first glance, these two fields look like they make up an option set, when in fact the correct return type is string. We need to use the following code snippet to deactivate each activity:

string activitySchemaName = a.GetAttributeValue<string>("activitytypecode");
            _sdk.Execute(new SetStateRequest
            {
                EntityMoniker = new EntityReference(activitySchemaName, id),
                State = new OptionSetValue(stateCode),
                Status = new OptionSetValue(statusCode)
            }); 

Note that the statusCode will differ for each activity type. See the CRM 2011 SDK for more information. We can then use the SetStateRequest to deactivate the related Case record and set the status to “Resolved”.