Developing an Offline Plug-in

Chapter 5, gave some examples of creating and deploying plug-ins for Microsoft Dynamics CRM. In this section we expand on this by creating a simple plug-in that functions while running Microsoft Dynamics CRM for Outlook in offline mode.

Programming the Plug-in

We’ll develop the offline-capable plug-in in a similar manner as the other plug-ins we have developed, but we need to add logic to determine when the client computer is in offline mode. Our plug-in will update the subject of a Lead record when it is created. We will update the subject to the Lead’s last name followed by its first name and the current date. When you create plug-ins, you want to be careful that Microsoft Dynamics CRM doesn’t execute them twice (once offline and once online). In a situation where the user is offline and creates a lead and then returns online at a later date, our plug-in would be run both when the lead was created offline and when the user returned online. As you will see later in this section, we add a condition to the plug-in to prevent this from happening. Example 10-3 shows the entire source code for the LeadTopicUpdater plug-in. Before we start coding, let’s talk briefly about the Microsoft Dynamics CRM customizations that we need for this example to function properly. Because the plug-in automatically updates the subject attribute on the Lead entity, we disabled this attribute on the Lead form and set its requirement level to No Constraint. This allows the user to create a new lead without entering a subject.

Adding the LeadTopicUpdater.cs file

  1. Open the ProgrammingWithDynamicsCrm4 solution with Microsoft Visual Studio 2008.

  2. Right-click the ProgrammingWithDynamicsCrm4.Plugins project we created in Chapter 5 and select Add New Item.

  3. Select the Class template and type LeadTopicUpdater in the Name box.

  4. Click Add.

Example 10-3. LeadTopicUpdater.cs source code

using System;
using System.Collections.Generic;
using System.Text;
using ProgrammingWithDynamicsCrm4.Plugins.Attributes;
using Microsoft.Crm.Sdk;
using System.Xml;
using Microsoft.Crm.SdkTypeProxy;

namespace ProgrammingWithDynamicsCrm4.Plugins
{
    [PluginStep("Create",
                PluginStepStage.PostEvent,
                Description = "Updates the lead's topic",
                StepId = "LeadPostCreate",
                PrimaryEntityName = "lead",
                Mode = PluginStepMode.Synchronous,
                SupportedDeployment = PluginStepSupportedDeployment.Both)]

    public class LeadTopicUpdater : IPlugin
    {
        public void Execute(IPluginExecutionContext context)
        {
            DynamicEntity target =
                      (DynamicEntity)context.InputParameters[ParameterName.Target];


            if (!target.Properties.Contains("subject") ||
                string.IsNullOrEmpty(target.Properties["subject"].ToString()))
            {
                ICrmService crmService = context.CreateCrmService(true);

                lead crmLead = new lead();
                crmLead.leadid = new Key();
                crmLead.leadid.Value =
                    new Guid(context.OutputParameters[ParameterName.Id].ToString());
                // we will create a new topic with the format:
                // Last Name, First Name - Created Date
                string firstName = String.Empty;
                string lastName = String.Empty;
                string date = String.Empty;

                if (target.Properties.Contains("firstname"))
                    firstName = target.Properties["firstname"].ToString();
                if (target.Properties.Contains("lastname"))
                    lastName = target.Properties["lastname"].ToString();


                // get the user's date format
                string fetch = String.Format(@"<fetch mapping='logical'>
                                            <entity name='usersettings'>
                                               <attribute name='dateformatstring' />
                                               <filter type='and'>
                                                    <condition
                                                       attribute='systemuserid'
                                                       operator='eq'
                                                       value='{0}' />
                                                </filter>
                                            </entity>
                                           </fetch>", context.UserId.ToString());

                string fetchResults = crmService.Fetch(fetch);

                XmlDocument resultDoc = new XmlDocument();
                resultDoc.LoadXml(fetchResults);

                string dateFormat =
resultDoc.DocumentElement.FirstChild.SelectSingleNode("dateformatstring").InnerText;

                date = DateTime.Now.ToString(dateFormat);

                crmLead.subject = String.Format("{0}, {1} - {2}",
                                                  lastName,
                                                  firstName,
                                                  date);

                crmService.Update(crmLead);
            }
        }
    }
}

We want to register the plug-in for both the Web and Outlook clients, so note that we set the SupportedDeployment of the PluginStep attribute to Both. You can find the PluginStepSupportedDeployment enum in the ProgrammingWithDynamicsCrm4.Plugins.Attributes project we created in Chapter 5. Table 10-6 lists the fields of the PluginStepSupportedDeployment enum along with a description. Another thing to note is that the Mode is set to Synchronous. Asynchronous plug-ins do not run in offline mode.

Note

Note

The PluginStep attribute is discussed in detail in Chapter 5.

Table 10-6. SupportedDeployment Members

Field

Value

Description

Both

2

Registers the plug-in for both the Web server and the Outlook Client

OutlookClientOnly

1

Registers the plug-in for only the Outlook Client

ServerOnly

0

Registers the plug-in for only the Web server

The logic in our plug-in is pretty simple. We first check to see whether the lead currently has the subject field populated. If it doesn’t have a subject, we then create an instance of the lead object, update its subject to our specified format, and call the Update method of the CrmService. Because we are checking to see whether a subject already exists, we are safe if the Plug-in is run more than once. This prevents the date from being incorrectly updated if the user created the lead offline. If the check is not in place, the next time the user goes online, the subject is updated with the current date instead of keeping the actual date the lead was created.

Another way to prevent a plug-in from running twice is to check the CallerOrigin property of the IPluginExecutionContext argument that is passed into the plug-in’s Execute method. If the origin is of the type offlineOrigin, the plug-in was fired when the offline client went into online mode. This concept is demonstrated in the following code snippet:

using System;
using Microsoft.Crm.Sdk;
using Microsoft.Crm.SdkTypeProxy;

public class OnlinePlugin : IPlugin
{
   public void Execute(IPluginExecutionContext context)
   {
      // Check to see if the plug-in was executed when going back online.
      CallerOrigin callerOrigin = context.CallerOrigin;
      if (callerOrigin is OfflineOrigin)
      {
         // The plug-in was excuted when the user clicked the go online button
         return;
      }
      else
      {
         // add the plug-in logic here
      }
   }
}

Tip

Tip

If you want a piece of code to only run online or offline, you can check the value of the IsExecutingInOfflineMode property on the IPluginExecutionContext argument that is passed into your plug-in’s Execute method.

Deploying the Plug-in

The "Deployment" section of Chapter 5 has all of the necessary steps for deploying the plug-in. You should deploy the plug-in to the database instead of the file system so that Microsoft Dynamics CRM automatically registers the plug-in on the client’s computer the next time the client goes offline.

After we register the plug-in, we have one more step before it can run in offline mode. Microsoft Dynamics CRM for Outlook with Offline Access has another layer of security for offline plug-ins. When Microsoft Dynamics CRM for Outlook with Offline Access is installed it creates a registry key called AllowList. We need to add the public token key guid of our plug-in assembly as a new key under the AllowList key.

Note

Note

See the "Offline Applications" section of Chapter 9 for detailed instructions on adding the Plug-in assembly’s public token key guid to the AllowList registry key.

Testing the Plug-in

To test our lead plug-in, open your instance of Microsoft Outlook that has Microsoft Dynamics CRM for Outlook with Offline Access installed and configured. Click the Go Offline button. When the synchronization process is complete and the Go Offline button has been replaced with a Go Online button, navigate to the Leads grid. Click New, and fill out the new Lead form. Click the Save button or the Save And Close button. Our plug-in should have executed and you can now see the subject updated with the Lead’s name followed by the current date (Figure 10-5).

Updated lead topic

Figure 10-5. Updated lead topic

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset