Thursday, October 01, 2009

Custom workflow action, team members and 'to' field of email record for Microsoft Dynamics CRM 4.0

There was interesting question and I decided to help author of question and create such functionality.



Here's the code of this custom workflow action:

using System;
using System.Collections.Generic;
using System.Text;
using System.Workflow.Activities;
using Microsoft.Crm.Workflow;
using System.Workflow.ComponentModel;
using Microsoft.Crm.Sdk;
using Microsoft.Crm.Sdk.Query;
using Microsoft.Crm.SdkTypeProxy;

namespace FillEmailWithTeamMembers
{
[CrmWorkflowActivity("Fill email with team members")]
public class EmailToFiller : SequenceActivity
{
protected override ActivityExecutionStatus Execute(ActivityExecutionContext executionContext)
{
if (Team != null && Email != null)
{
IContextService contextService = (IContextService)executionContext.GetService(typeof(IContextService));
IWorkflowContext workflowContext = contextService.Context;
ICrmService crmservice = workflowContext.CreateCrmService();

//Retrieve System Users based on Team

QueryExpression query = new QueryExpression(EntityName.systemuser.ToString());
query.ColumnSet = new ColumnSet(new string[] { "systemuserid" });
LinkEntity link = query.AddLink("teammembership", "systemuserid", "systemuserid");
link.LinkCriteria.AddCondition(new ConditionExpression("teamid", ConditionOperator.Equal, Team.Value));

List<BusinessEntity> users = crmservice.RetrieveMultiple(query).BusinessEntities;

email emailInstance = new email();
emailInstance.activityid = new Key(Email.Value);

List<activityparty> receivers = new List<activityparty>();

foreach (systemuser user in users)
{
activityparty toparty = new activityparty();
toparty.partyid = new Lookup();
toparty.partyid.type = EntityName.systemuser.ToString();
toparty.partyid.Value = user.systemuserid.Value;

receivers.Add(toparty);
}

emailInstance.to = receivers.ToArray();

crmservice.Update(emailInstance);

SendEmailRequest request = new SendEmailRequest();
request.EmailId = Email.Value;
request.IssueSend = true;
request.TrackingToken = "";
crmservice.Execute(request);
}

return ActivityExecutionStatus.Closed;
}

public static DependencyProperty TeamProperty = DependencyProperty.Register("Team", typeof(Lookup), typeof(EmailToFiller));

[CrmInput("Team")]
[CrmReferenceTarget("team")]
public Lookup Team
{
get
{
return (Lookup)base.GetValue(TeamProperty);
}
set
{
base.SetValue(TeamProperty, value);
}
}

public static DependencyProperty EmailProperty = DependencyProperty.Register("Email", typeof(Lookup), typeof(EmailToFiller));

[CrmInput("Email")]
[CrmReferenceTarget("email")]
public Lookup Email
{
get
{
return (Lookup)base.GetValue(EmailProperty);
}
set
{
base.SetValue(EmailProperty, value);
}
}

}
}


I've tested this code and it works.