Plugin to Track Marketing List Movements

   Words by CRM Consultancy

   on 16/04/2018 08:00:00

imageRecently we encountered a client requirement to track the Contacts being added or removed to a Marketing List so that a weekly report could be produced on the movements of the list.

For Contacts being added to a Marketing List, this is relatively simple as we can produce our report based from the ‘createdon’ of the Marketing List Members entity in CRM.

However to report on Contacts being removed from the Marketing List this is more tricky, as the Marketing List Member is removed from the CRM Database when the Contact is removed from the List – which means that there is no record for us to report from.

We could use the CRM Audit Trail to track the Associate and Disassociate Messages for the Marketing List, however this would require a pretty detailed report capable of reading and reporting on the CRM Audit Trail.

This would work but would push the technical complexity into the Report, whereas we have a common Email-Report framework that we were looking to use for this weekly report so the requirement could be implemented within a common framework with other Daily, Weekly or Monthly Reports we produce from Dynamics CRM.

Instead we looked at a CRM Plugin that would track when a Contact was added or removed from a Marketing List – and then save a record to a Custom Entity that would track List Movements. (a kind of a mini custom Audit Trail that we can more easily report on)

To do this, we must add a Plugin to ‘lesser spotted’ Messages in the Dynamics CRM Pipeline – AddMember and RemoveMember.

As the name suggests, these Messages trigger when an Add Member or Remove Message is processed by Dynamics and allow us to capture the event and take action as a result.

These Messages do not take in the traditional ‘TargetMessage’ Entity being passed into the Plugin Execution and instead favour two Input Parameters for the GUID Id of the List and the GUID Id of the Contact. (or other record being added to the List, such as a Lead or Account)

So our Plugin must look at handling these InputParameters and take action on the basis of these Parameters:

listId = (Guid)context.InputParameters["ListId"];

recordId = (Guid)context.InputParameters["EntityId"];

This can then be used to build a history of movements for different Marketing Lists.


Figure 1 – Adding a Contact to a Marketing List


Figure 2 – The Resulting List Movements History

This can then be used to produce regular List Movement Reports to track the quantity of Contacts being added or removed from Lists.

Online there is a wealth of resources for Plugin Development with Dynamics, but not much information on these events for AddMember and RemoveMember – and so the full source code of this Plugin can be found below as a practical example of using these Messages and Events:

/// <summary>
/// Tracks when a Contact is added to or removed from a Marketing List
/// </summary>
public class MarketingListMovement : BasePlugin
     /// <summary>
    /// Execute the plug-in
    /// </summary>
    /// <param name="serviceProvider">Service provider</param>
     /// <param name="context">Plugin exeution context</param>
    /// <param name="organizationServiceFactory">Organization service factory</param>
    protected override void ExecutePlugin(IServiceProvider serviceProvider,
                                             IPluginExecutionContext context,
                                             IOrganizationServiceFactory organizationServiceFactory)
        #region Get references to CRM Webservices

        if (context == null)
            throw new ArgumentNullException("context");

        if (organizationServiceFactory == null)
            throw new ArgumentNullException("organizationServiceFactory");

        IOrganizationService service = organizationServiceFactory.CreateOrganizationService(context.UserId);
        OrganizationServiceContext organizationServiceContext = new OrganizationServiceContext(service);


             Guid userId = Guid.Empty;
            Guid listId = Guid.Empty;
            Guid recordId = Guid.Empty;
            string action = string.Empty;

            if ( context.MessageName == "AddMember")
                userId = context.InitiatingUserId;
                listId = (Guid) context.InputParameters["ListId"];
                recordId = (Guid)context.InputParameters["EntityId"];
                action = "Add to Marketing List";
            else if (context.MessageName == "RemoveMember")
                userId = context.InitiatingUserId;
                listId = (Guid)context.InputParameters["ListId"];
                recordId = (Guid)context.InputParameters["EntityId"];
                action = "Remove from Marketing List";

            if ( action != string.Empty && listId != Guid.Empty && recordId != Guid.Empty )
                // before we do anything else, we should check
                // that the 'EntityId' is a reference to the Contact Entity
                // instead of to a Company or Lead
                QueryExpression checkContact = new QueryExpression("contact");
                checkContact.Criteria.AddCondition("contactid", ConditionOperator.Equal, recordId);

                EntityCollection resultContacts = service.RetrieveMultiple(checkContact);
                if (resultContacts.Entities.Count > 0)
                    // Contact exists in CRM that matches the RecordId, proceed
                     Entity newMovement = new Entity("crmcs_listmovement");
                     newMovement.SetValue("crmcs_name", action);
                     newMovement.SetLookupValue("crmcs_listid", "list", listId);
                    newMovement.SetLookupValue("crmcs_contactid", "contact", recordId);

                    // No Contact exists, do nothing
        catch (Exception ex)
            throw new InvalidPluginExecutionException("CRMCS.Xrm.Email.MarketingListMovement --> Execute :: ERROR " + ex.Message + "");

Further Reading

Microsoft Dynamics CRM 2013 – Plugin Messages – AddMember – deep dive

Share this Article

Search Articles

Filter Articles

CRM Tech DocMan

Recent Articles

Dynamics 365 Marketing vs ClickDimensions It’s time to pause, reflect and acknowledge a new era of inclusivity and collaboration. Part 2 - How to get the most from a Technology Expert – Asset Management Hub Property & Asset Management Hub Part 1 – Balancing CRM and Asset Management Scopes - Asset Management Hub Creating a Multi-Lingual PowerApps Portal How to Set Up a Microsoft Teams Site Using DocDrive365 Microsoft Teams - Adding a Microsoft Teams URL to a Dynamics Appointment Dynamics 365 Marketing – Customer Voice Survey Not Appearing In Emails? Using SQL Management Studio to connect to the Dynamics DB Calling a Power Platform AI Builder Model via oData How to use DocDrive365 to integrate permissions between Business Units in Dynamics with Sites in SharePoint Getting started with the Power Platform AI Builder. Power Apps Portal Information Hub DocDrive365 Security: Day One - Getting Started with Dynamics to SharePoint Permissions Part 5 - Power Apps Portals: How To Connect Azure B2C With Linked-In Part 4 – Power Apps Portals: Styling Azure B2C for Power Apps Portals The 3 Phases for Using Multi-Select Option Sets in Flow with Microsoft Forms Part 3 – PowerApps Portals: Azure B2C and Power Apps Portals – User Flow for Signup and Signin Part 2 - Power Apps Portals: New Application Registration in Azure B2C for our Power Apps Portal Part 1 – Power Apps Portals: Creating a New Azure AD B2C Tenant The Automation Bot: Launching Contextual Flow from Teams Creating a New Bot for Teams Debugging your Teams Bot using Ngrok Adding a Microsoft Teams URL to a Dynamics Appointment
Contact Us

Want expert advice or a demo?

Get in touch now and see how we can help your business grow.

  • Name
  • Email Address
  • Phone Number

Understanding Your Challenges

Our strong understanding of CRM and emerging technologies within the Microsoft environment means we deliver the right solutions for you.

Proven Real-World Solutions

As a leader in the field of Dynamics solutions, our pedigree developing and delivering real-world solutions is unsurpassed.

Long Term Support

We provide support beyond our design, implementation and 'go-live' delivery using Sprints and continual updates to our AppSource apps.

CRMCS | Design by Thinktank Marketing | Citrus-Lime Limited

To improve your experience today and in the future, this site uses cookies. Read our full Privacy Policy & Cookie information here I Understand