CRM-Sharepoint integration with Sharepoint REST API using Custom Workflow – C#

Working for a client last week where in we got a requirement to create a Sharepoint list item when a new Lead is created in CRM.

Being a CRM Resource, I have first checked the options (OOB/configurable) available for me and the first thing that came in to my mind is Microsoft FLOW. A quick POC proved that it is very easy to configure CRM & Sharepoint integration with FLOW. However, the first hit for us using the Flow is the additional licence (and surprised to see a max of 15000 runs are allowed with “premium” kind of license, happy to be proved wrong on this).

With a No-go to FLOW then we started our thought process towards REST Apis, initially I found the sharepoint rest apis are a bit confusing (not as straight-forward as CRM’s webapi) but it didn’t took much time to realize that it is just my lack of knowledge on sharepoint made me feel like so. The MSDN Documentation on the Sharepoint rest api is good enough for any one with some basic knowledge on REST to go ahead and do programming with SP.

The first question is how do we authenticate the SP Api ? And a quick googling resulted in to this wonderful blog of Scott TheCRMGuru Durow (MVP) on SP integration with CRM Online. It has every thing one needs to know on how to connect to Sharepoint, the HTTP Helper class to pass the web request. However, the example source code provided by Scott actually creates the Folders in to Sharepoint and so, we had to write our code to create the List item instead of Creating folder.

So, that is what I’m going to explain in this blog – How to Create/Update sharepoint list item from CRM. I have just tried to put some error handling on top of the Scott’s “open source, free to use” library and have published in to Github. I don’t think I can explain all the bits of SP integration over here, rather I’m going to concentrate only on the bits that every one needs to know to further customize it according to their entity/list item.

I have created 2 custom workflow activities (one for Create and another for Update) and here is the quick view of Create Workflow source.


 public override void ExecuteCRMWorkFlowActivity(CodeActivityContext context, LocalWorkflowContext crmWorkflowContext)
{
// You might want to work on configuring these 3 settings - URL, User Name, Password !!
ISharePointService spService = new SPService("https://xyz.sharepoint.com", "user@xyz.onmicrosoft.com", "password");

// These are the are part of Sharepoint List Item. Think of better way to handle
// the field changes.. !!
Dictionary<string, string> fields = new Dictionary<string, string>();
fields.Add("Title", Title.Get(context));

// This is the list name what we see in the Sharepoint.
// You might want to keep it as configurable value !!
var result = spService.CreateListItem("Leads from CRM", fields);

Success.Set(context, result.Success);
if (result.Success)
{
ListItemId.Set(context, result.ListItemId);
}
else
{
ExceptionDetails.Set(context, result.Exception.ToString());
}
}

The first line of the code, provides an established connection to the given Sharepoint site. Note that, I have hard coded the Sharepoint URL, User Id & password in this source code. You might want to store them as part of some “configuration” entity in your organization and retrieve it. (You might want to give some thought process further on how do you secure your Password).

The second line is where I’m creating a list of key value pairs to hold all the fields and values of sharepoint record that we are going to create. This dictionary in later stages will be converted in to JSON string to pass as Data parameter to Sharepoint rest api. If you can see, I have only one field to create the list item record (ie Title). You might want to place all your other fields of list item record over here and think on how do you grab these fields from CRM. If there are too many no.of fields, then I would suggest to retrieve the record and map it accordingly instead of placing all the fields as InputArguments.

The next line is the “Go” command to create sharepoint list item with the given information. There is one change you have to do in this line is, The list name. Notice, I have hard coded the list name as “Leads from CRM”, this could be any thing in your case. so I would highly recommend you to place it as a configurable option or as a InputArgument.

The result object provides the Success status of the REST Api call as True/False. You might want to use this in your workflow and take necessary actions in the workflow before taking any other actions.

Here is a quick view of my work flow in CRM.

1
CRM Workflow to create Sharepoint List Item

Notice, How I’m checking the Workflow Successfully Executed status to update the lead !! A quite common question at this point is, why do we need to update the Sharepoint ID in CRM ? This is required particularly in my case as I also have to ensure that the record is in sync going forward i.e. If any one updates the record in CRM then I have to update in SP as well (thank god it is not vice versa, else I think I should look for a SP Resource :))

For the purpose of Updating SP list item record, I have created another CodeActivity with almost the same piece of code except this time it is a MERGE request to SP Api. This is how my Update Code activity looks like.


public override void ExecuteCRMWorkFlowActivity(CodeActivityContext context, LocalWorkflowContext crmWorkflowContext)
{
// You might want to work on configuring these 3 settings - URL, User Name, Password !!
ISharePointService spService = new SPService("https://xyz.sharepoint.com", "user@xyz.onmicrosoft.com", "password");

// These are the are part of Sharepoint List Item. Think of better way to handle
// the field changes.. !!
Dictionary<string, string> fields = new Dictionary<string, string>();
fields.Add("Title", Title.Get(context));

// This is the list name what we see in the Sharepoint.
// You might want to keep it as configurable value !!
var result = spService.UpdateList("Leads from Flow", ListItemId.Get(context), fields);

Success.Set(context, result.Success);
if (!result.Success)
{
ExceptionDetails.Set(context, result.Exception.ToString());
}
}

No much difference to the previous code. I don’t think I need to go through this code again.  And the Update workflow is

2
Update Sharepoint list item from CRM Workflow

Isn’t that simple ? 😛

So, What you have to do now to get it done further ? Nothing much, Download the source code from here or from my GitHub, Build it and register it as custom workflow activity (after doing required URL, user/password changes and the list name changes). Create a workflow (Realtime/Asynchronous) as shown. That’s it, you are good to go.

Check it and let me know how it is working for you !!

Happy Coding !!

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s