If you’re using ILMerge with your plugins - make sure you read this!

Ever since Microsoft CRM moved online and Plugin sandboxing became mandatory, you'll have likely come up against the challenge of using third party assemblies.

Sand-boxed Plugins cannot access any third-party assemblies and so if you use a NuGet package such as the Microsoft.SharePoint.Client libraries or Newtonsoft's Json.Net then you may have considered or even used ILMerge to embed a copy of the assembly into your compiled Plugin. You may even have used ILMerge to include your own 'common' libraries into your Plugins - even though you could have included the source code. To put it simply - don't do this!

ILMerge is *not* supported!

This is not like the managed/unmanaged solutions or JavaScript vs Business Rules debate. The simple fact is that using ILMerge with Plugins is not supported by Dynamics 365 CE/CDS for Apps.

There is a very old blog post on msdn from back in 2010 about ILMerge that contains this statement from the Dynamics team:

"This post has been edited to reflect that Dynamics CRM does not support ILMerge. It isn't blocked, but it isn't supported, as an option for referencing custom assemblies."

If you do decide to use ILMerge then be warned then you are in dangerous waters! If there is a problem with your environment that is plugin deployment related then the likely answer from Microsoft support is that you'll need to remove your use of ILMerge before your issue can be resolved.

Don't bring me problems, bring me solutions!

One of the most common reasons for using ILMerge I see is when using Newtonsoft's Json.NET. There are many code snippets out there that use this library to parse JSON it to an object graph. Consider the following code for de-serialising Json from the Nest API into a c# object graph:

var nestData = JsonConvert.DeserializeObject<NestData>(json);
public class NestData
    public Devices devices { get; set; }
    public Dictionary<string, Structure> structures { get; set; }

The good news is that since .NET 4.0 we've had pretty much the same control over deserialising JSON using the standard class libraries:

using (var stream = new MemoryStream(Encoding.UTF8.GetBytes(json)))
    DataContractJsonSerializerSettings settings = new DataContractJsonSerializerSettings()
        UseSimpleDictionaryFormat = true

    DataContractJsonSerializer ser = new DataContractJsonSerializer(typeof(NestData), settings);
    var nestResponse = (NestData)ser.ReadObject(stream);

public class NestData
    public Devices devices;
    public Dictionary<string, Structure> structures;


Other libraries that are not included in the .NET Framework (e.g. Microsoft.SharePoint.Client) shouldn't be used. If you can't include the source code in your Plugin, then consider using a loosely coupled Microservices approach to manage your integrations. This way you'll have fully supported lightweight plugins that can offload the heavy lifting outside of the sandbox worker processes.

💡 Keep those Plugins small and lightweight! 💡

Photo by Hafidh Satyanto on Unsplash

Comments (2) -

  • Hi Scott,
    couldn't agree more.
    Think about using the OOTB Azure integration, offload the event and execution context to Azure Service Bus, use Logic Apps with potential Functions extensions and off you go Smile

    • Thanks Philip. Definitely - I do like to keep loose coupling though. If there is some logic that really should stay close to CDS and deployed as part of a solution etc. then Plugins are good.
Comments are closed