How to send an EXM email from code

In this post I’d discuss the following

  1. How to send an EXM email from code?
  2. How to use EXM to send emails to users who are not in Sitecore, i.e.

Before I describe my approach, I should note that we’d need to solve #2, before we can send an email.

Sitecore requires that a contact in xDB exist, before sending out emails. This is needed as it enables Sitecore to track and report.

Solution

  • Setup
    • The first step is to create a new email campaign. For this task we’ll select automated email campaign (Read more about email types). Use the this guide to create a new campaign.
    • Once you have the campaign created, open Sitecore content editor to locate the new message.
    • Grab the Item ID from the item. In my case the value is “{508277E8-745D-4859-B2E7-268CC7E90A27}”
  • Code
    • First step is to, grab the message (email) from Sitecore
                  // retrive message item from Sitecore
                  var message = Factory.GetMessage(ID.Parse("{508277E8-745D-4859-B2E7-268CC7E90A27}"));
                  // for multi lingual solution use the override to get the correct language version
                  //var message = Factory.GetMessage(messageItemId,"en");
    • Then, we need to find the contact in xDB. We’ll need the contact ID
      • If the current user is logged in and is the contact we are looking for, then simply use the tracker and return the contact ID
         return new XdbContactId(Tracker.Current.Contact.ContactId);
      • If the user is not logged in get the user from xDB
         var anonymousIdFromEmail = _clientApi.GetAnonymousIdFromEmail(email);
                        if (anonymousIdFromEmail.HasValue)
                        {
                            return new XdbContactId(new ID(anonymousIdFromEmail.Value));
                        }
      • If the steps above do not work, we’ll need to create a new xDB Contact, and write the email value
         // if the contact does not exist in Xdb then create one
                        var newContactId = _gateway.CreateContact(email);
                        if (newContactId != Guid.Empty)
                        {
                            LeaseOwner leaseOwner = new LeaseOwner("GetXdbContactId-" + Guid.NewGuid(),
                                LeaseOwnerType.OutOfRequestWorker);
                            TimeSpan leaseDuration = TimeSpan.FromSeconds(15.0);
                            TimeSpan timeout = leaseDuration;
                            Contact contact;
                            string webClusterName;
                            switch (
                                _gateway.TryGetContactForUpdate(ID.Parse(newContactId), leaseOwner, leaseDuration, timeout,
                                    out contact, out webClusterName))
                            {
                                case ContactLockingStatus.InCurrentTracker:
        
                                    SaveEmail(contact, email);
                                    break;
        
                                case ContactLockingStatus.LockAcquired:
                                    try
                                    {
                                        SaveEmail(contact, email);
        
                                    }
                                    finally
                                    {
                                        _contactRepository.SaveContact(contact,
                                            new ContactSaveOptions(true, leaseOwner, new TimeSpan?(leaseDuration)));
                                    }
                                    break;
                                case ContactLockingStatus.LockedByWebCluster:
                                // we will probably never run into this as the contact is new
        
                                case ContactLockingStatus.NotFound:
                                //handle error
                                default:
                                    //handle error
                                    break;
                            }
                            return new XdbContactId(newContactId);
                        }
        
              public void SaveEmail(Contact contact, string email)
                {
                    var emailFacet = contact.GetFacet(Constants.ContactFacetNames.Emails);
                    if (!emailFacet.Entries.Contains("Work Email"))
                    {
                        var emailaddress = emailFacet.Entries.Create("Work Email");
                        emailaddress.SmtpAddress = email;
                        emailFacet.Preferred = "Work Email";
                    }
                    var contactInfo = contact.GetFacet(Constants.ContactFacetNames.Personal);
                    contactInfo.FirstName = "Created";
                    contactInfo.Surname = "ByCode";
                }
    • Finally, let’s send the email
         // retrive message item from Sitecore
                  var message = Factory.GetMessage(messageItemId);
                  // for multi lingual solution use the override to get the correct language version
                  //var message = Factory.GetMessage(messageItemId,"en");
                  Assert.IsNotNull(message, $"Could not find message with ID {messageItemId}");
                  RecipientId recipient = GetXdbContactId(email);
                  Assert.IsNotNull(recipient, $"Could not find recipient with email {email} in xDB");
      
                   // sync call
                  //var sendingManager = new SendingManager(message);
                  //sendingManager.SendStandardMessage(recipient);
                  var asyncSending = new AsyncSendingManager(message);
                  asyncSending.SendStandardMessage(recipient);

 

You can download the code from here

 

How to send an EXM email from code
Tagged on:         

2 thoughts on “How to send an EXM email from code

Leave a Reply

Your email address will not be published. Required fields are marked *