﻿#### Sitecore 9: Marketing Automation API - enrolling contacts

In the [previous posts](https://www.brimit.com/blog/sitecore-9-custom-marketing-automation-action "Sitecore 9 marketing automation action") we learned how to create custom action types. We created custom activity type and deployed it to Marketing Automation engine and Sitecore Marketing Automation UI. In order to use Marketing Automation Engine developers and marketers need to understand how contacts are enrolled in automation plans and get familiar with the corresponding API. In this post, we will learn how to enroll contact to automation plan programmatically using Operations API and how to use Marketing Automation Reporting API.

[Sitecore documentation](https://doc.sitecore.net/developers/xp/marketing-automation/automation-engine/enrollment/index.html "Sitecore 9 marketing automation enrollment") provides a great starting point to understand a number of scenarios when contact is enrolled in Automation plan. 

**Option 1: XdbContactEventWatcher** xConnect service plugin detects contacts and interactions submitted to xConnect and creates a work item for Automation Pool. A number of pool workers are waiting to process each work item according to priority. Any interaction or change to the contact and its facets submitted using **XConnectClient** will be processed to marketing automation this way.

**Option 2**: A live event is registered using Marketing Automation Operations API. Both marketers and developers can make use of this feature. Developers can use Marketing Operations API to register a live event and set a higher priority for an individual event to be processed. Marketers can use Sitecore 9 newly introduced **Is Live Event** property of the event, goal and outcome definition item.

![Is Live Event ](https://www.brimit.com/-/media/images/blog/sitecore9marketingautomationapicontacts1.png?la=en&amp;hash=B634AC9CE69784D4D6C5576FAB36E20E)

This feature is used by the Sitecore tracker to submit events to the Marketing Automation Engine before the session has ended and event data has been submitted to the Collection database. This way marketers can ensure events are evaluated in Marketing Automation plans immediately during the ongoing interaction. 

**Option 3**: Finally contact can be enrolled in Automation plan programmatically again using Marketing Automation Operations API. Let's take a closer look at how developers can make use of it.

Let’s create a simple marketing automation plan where we will want to enroll contact directly to the **Custom listener** action bypassing the plan entry condition.

![Custom listener action](https://www.brimit.com/-/media/images/blog/sitecore9marketingautomationapicontacts2.png?la=en&amp;hash=5590B532413E292EC6407B195C2F1BCB)

The following code snippet illustrates how to enroll contact to the specific activity. 

```
   
private static void AddContactToPlan()
{
    AutomationOperationsClient operationsClient = GetAutomationOperationsClient();

    var contactXconnectId = Guid.Parse("{7861dfd4-b578-0000-0000-052854642e00}");
    var planId = Guid.Parse("{4a85ddac-cc2f-47b1-a9d5-8972b3409b24}");
    var request = new EnrollmentRequest(contactXconnectId, planId); // Contact ID, Plan ID

    request.Priority = 1; // Optional
    request.ActivityId = Guid.Parse("{c01b8533-f524-b384-5614-346f0b6a7544}"); // Optional
    request.CustomValues.Add("test", "test"); // Optional

    BatchEnrollmentRequestResult result = operationsClient.EnrollInPlanDirect(new[] { request });
} 
```

So, what exactly **ActivityId** is? An automation plan contains a collection of activities. Activities are saved as a JSON on the plan definition item. Each activity in a plan defines legal paths from itself to the next activity. 

Given that we know Custom Listener **ActivityTypeID** we can quickly find corresponding **ActivityID** that makes use of Custom Listener **ActivityTypeID**.

![Custom Listener ActivityTypeID](https://www.brimit.com/-/media/images/blog/sitecore9marketingautomationapicontacts3.png)

Alternatively, you can inspect Marketing Automation UI to find the underlying ActivityId. 

In the above code snippet, we use **AutomationOperationsClient**.

If you run your code in the Sitecore context you can use the following code snippet to get its instance.

```
   
var operationsClient = 
ServiceLocator.ServiceProvider.GetService<IAutomationOperationsClient>(();
 
```

However, if you are accessing Operations API outside of Sitecore you will need to instantiate operations client in a different way.

```
   
string XconnectUrl = ConfigurationManager.AppSettings["xconnect.url"];
 
ILogger<AutomationOperationsClient>( logger = LoggerFactory.CreateLogger<AutomationOperationsClient>();
 
var result = new AutomationOperationsClient(new Uri(XconnectUrl), null, null, logger); 
 
```

Be sure to set web request certificate modifier in production environment.

We can immediately see enrollment request results in the Marketing Automation plan report and can even view contacts in the selected activity.

![Marketing Automation plan activity](https://www.brimit.com/-/media/images/blog/sitecore9marketingautomationapicontacts4.png)

If you decide to enroll the same contact to another activity, such request will be registered OK, but enrollment processing will not work, and you will find the following error in AutomationEngine log: Failed to create activity enrollment Status code: "EnrollmentAlreadyExists".

When enrollment request is received by xConnect a new record will be created in **AutomationPool** table of the **MarketingAutomation** database, Automation Engine background worker will attempt to process new work item and update **ActivityEnrollments** table to save enrollment state. Statistics tables will also be updated to include information about such enrollment for reporting purposes.

Contact **AutomationPlanEnrollmentCache** facet will also be updated to include the information about activity and plan contact is enrolled. The following image illustrates the value of the **FacetData** field for the corresponding FacetKey in the **ContactFacet** table of the Collection database. 

![ContactFacet Collection database](https://www.brimit.com/-/media/images/blog/sitecore9marketingautomationapicontacts5.png)

Note that custom values submitted along with enrollment request are saved here and you can make use of it in automation conditions, and any further business logic.

You can [enroll contact in multiple automation plans](https://doc.sitecore.net/developers/xp/marketing-automation/operations-api/index.html#enrolling-a-contact-in-multiple-plans "Sitecore 9 marketing automation enrollment") and also remove the contact from automation plans using [purge request](https://doc.sitecore.net/developers/xp/marketing-automation/operations-api/index.html#purge-contact-from-specific-plan "Sitecore 9 marketing automation purge request").

In a similar way, you can instantiate Automation Reporting client and make use of Reporting API. All code snippets are available in the [GitHub repository](https://github.com/avershalovich/Demo9.Features "Sitecore 9 marketing automation enrollment").

Fly high with Sitecore 9.

#### Read more on marketing automation and Sitecore 9:

- [Creating Activity Type backend logic and definition item](https://www.brimit.com/blog/sitecore-marketing-automation-creating-activity-definition "Sitecore Activity Type")
- [Deploying Activity Type to Sitecore UI and Marketing Automation engine](https://www.brimit.com/blog/sitecore-marketing-automation-deploying-activity-type-automation-engine "Marketing Automation engine")
- [Creating Activity Type UI and Editor](https://www.brimit.com/blog/sitecore-marketing-automation-creating-activity-editor "Creating Activity Type")
- [Custom Marketing Automation Action - Introduction](https://www.brimit.com/blog/sitecore-9-custom-marketing-automation-action "Custom Marketing Automation Action")
- [Marketing Automation - Repeated and concurrent contact enrollments](https://www.brimit.com/blog/sitecore-9-marketing-automation-multiple-enrollments "Repeated and concurrent contact enrollments")

##### Do you need help with your Sitecore project?

      ![](~/media/CD37043DFD1F491D8E92958A11959F75.ashx?la=en&amp;hash=D08B252DD3B41C09B588007541E5D22F)

   [VIEW SITECORE SERVICES](https://www.brimit.com/expertise/sitecore-cms)

###### Author

[!\[Alexei Vershalovich\](https://www.brimit.com/-/jssmedia/feature/blogs/authors/alexei-vershalovich-brimit---500.png?h=1098&amp;iar=0&amp;w=1042&amp;hash=7551A887E43E4DDE95E9C95102DBDF1B)
Alexei Vershalovich
Principal Consultant, digital experience and e-commerce](https://www.brimit.com/blog/author?authors=Alexei%20Vershalovich)

#### More on Sitecore

[!\[How Vercel Will Help You Save Effort When Deploying Sophisticated Sitecore Projects\](https://www.brimit.com/-/jssmedia/project/brimit/blog/2024/vercel_cover-image.png)
#Guides#How-toDXPE-commerce
##### How Vercel Will Help You Save Effort When Deploying Sophisticated Sitecore Projects
Optimize and accelerate the development and deployment of complex multisite Sitecore projects.
Alexei Vershalovich on July 17, 2024](https://www.brimit.com/blog/how-vercel-will-help-you-save-effort-when-deploying-sophisticated-sitecore-projects)

[!\[Training Up Tomorrow's Sitecore MVPs: a Mentoring Success Story\](https://www.brimit.com/-/jssmedia/project/brimit/blog/2023/sitecore-mentoring---cover-image.png)
#How-toDXP
##### Training Up Tomorrow's Sitecore MVPs: a Mentoring Success Story
How to participate in the Sitecore Mentor program and help younger colleagues jump-start a career in Sitecore development.
Sergey Baranov on October 2, 2023](https://www.brimit.com/blog/training-up-tomorrows-sitecore-mvps)

[!\[Going Headless. Part 2: When a Headless CMS Is Your Best Bet (if you have Sitecore)\](https://www.brimit.com/-/jssmedia/project/brimit/blog/2022/headless/adobestock_456986731.jpg)
#How-toDXPE-commerce
##### Going Headless. Part 2: When a Headless CMS Is Your Best Bet (if you have Sitecore)
Discover how a headless CMS can benefit organizations that use Sitecore.
Daniil Raschupkin, Palina Trokhautsava on September 15, 2022](https://www.brimit.com/blog/going-headless-part-2-when-a-headless-cms-is-your-best-bet-if-you-have-sitecore)

![](https://bat.bing.net/action/0?ti=187017043&amp;tm=gtm002&amp;Ver=2&amp;mid=a768eb07-1fc3-4d82-b9a4-5b1f8b76a8cb&amp;bo=2&amp;gtm_tag_source=1&amp;pi=0&amp;lg=en-US&amp;sw=800&amp;sh=600&amp;sc=24&amp;nwd=1&amp;tl=Sitecore%209%3A%20Marketing%20Automation%20API%20-%20enrolling%20contacts&amp;kw=Sitecore,%209,%20Custom,%20Deploying,%20Activity,%20Type%20,Marketing,%20Automation,%20engine%20&amp;p=https%3A%2F%2Fwww.brimit.com%2Fblog%2Fsitecore-marketing-automation-api-enrolling-contacts&amp;r=&amp;lt=272&amp;evt=pageLoad&amp;sv=2&amp;asc=D&amp;cdb=AQAY&amp;rn=256330)