Sitecore xConnect overview – Contacts, Interactions, Facets.

When sitecore 9 got introduced I felt that xDB got replaced with xConnect in sitecore 9 and assumed xConnect is a logical collection of databases to store our website interactions, all other user specific data. After exploring came to know that xDB is different from xConnect.

What xConnect exactly is?

xConnect acts as a service layer between xDB and all other applications/clients/devices which makes use of user information, interactions stored in xDB , few of such applications are Experience Profile, EXM, List Manager, Analytics ,also few external application are also dependent. To and fro communication from applications to xDB always happens through secured https protocol and client should have a proper certificate thumbprint to access xConnect with admin permissions to certificates.

Few notable features of xConnect
  • Any application/client cant access xDB data without xConnect ,xConnect is the only way of communication to access any xDB data.
  • xConnect is capable of capturing complete user profiles, behaviors and interests, dislikes through proper client devices/store visits. With xConnect, Omni channel data from customers like Fitbit data, in store visits, beacon data, IOT and other devices can now be fully integrated through xConnect with the Sitecore Experience database (xDB), allowing us to create contextually relevant and predictive digital experiences for our customers.
  • The xConnect Client API is portable and can be used out of Sitecore project in normal .NET based applications as well without any dependency with sitecore context.
  • Sitecore instance and xConnect instance are 2 different independent instances which contains 2 separate IIS websites, 2 web roots, 2 different URL’s.


How xConnect got introduced from existing xDB architecture

Previously in Sitecore 8.x versions different applications use to store/search/read/write user interaction data to/from xDB using different providers as above screenshot depicts but in sitecore  9.x all these providers are replaced with Sitecore xConnect as you can see in below picture depicts.

xConnect Architecture

The complete xConnect cycle, operations how it behaves is captured in below image.

When you have sitecore9 installed and running, we have to make sure that analytics, xConnect, Experience profile are working proper. Where a user is being searched through xConnect API , then below are the life cycle steps followed internally by xConnect and xDB.

First step, User contact and interaction data is being saved/read by client application or devices. Below in image I mentioned Roles with numbers.


  1. Search Index : Able to read contact and interaction data from the xDB Collection database during indexing. And stores personal data in the xDB index if indexing of personal data has been enabled.
  2. Collection Database: Collection Database mainly supports data extraction. It receives contacts and interactions and allows reading of contact and interaction data by ID or identifier.
  3. Processing Pool: Once received contact and interactions information are read, Processing pool analyses and aggregates collected data to make into usable in reporting.
  4. Reporting Data: Then processed query results are retrieved  from various data sources and sent to sitecore reporting applications or device as mentioned below.
  5. Automation Data: This role is responsible for enrolling contacts in plans and activities.


Also xConnect makes use of 3 windows services in its architecture for few operations as below.

  1. Index Worker : Here Search Index and Collection database roles are being executed
  2. Processing : Here Processing pool and Reporting role is being executed.
  3. Automation Engine: The Marketing Automation Engine is a stand-alone service that is responsible for enrolling contacts in plans and activities which is executed in Automation Role.


Contacts and Common Terminologies

Contacts :

A contact represents an individual or an entity who interacts with your website or brand. Contacts are represented by Sitecore.XConnect.Contact class, and are uniquely identified by ID (GUID) within the xDB. IDs are generated by the service layer when a contact is saved and should not be saved outside the xDB. Contacts also have one or more identifiers that identifies the contact to systems outside the xDB. Identifier can be a mail id or unique username which can be decided by brand.

  1. An interaction describes any point at which a contact interfaces (contact achieves some goal as page visit, registration, download, quotation) with a brand or site, either its online or offline. Interactions are represented by Sitecore.XConnect.Interaction class and must have at least one event. In the following example, an interaction with a single goal is added to a new contact, Interactions includes
  • Purchasing a something from a physical store
  • Using an app
  • Browsing a website
  • A phone conversation



Facets are piece of information that enriches a contact or an interaction. For contacts, facet include their full name, and address, other contact details. For interactions, facets might include the geographic location of the interaction happened. Each facet may contain:

  • Few pre-defined facets are Personal Information, Email, Avatar, Addresses. In case if pre-defined facets wont serve your purpose you can go with creating your own custom facets.
  • Facet model is a class that inherits from Sitecore.XConnect.Facet.
  • Facet can be defined as, which associates a facet model with a key and assigns it to an entity  such as either contacts or interactions.
  • Facet model can be defined with the same key for contacts and interactions, or re-used with a different key.
  • Facet keys are case sensitive.


Web Tracking:

Tracker is responsible for tracking a contact’s activities on your website and submitting that interactions data to xConnect at the end of the each session. xConnect and the tracker both works together but they are separate components.

  • xConnect Client API is the only possible way to work with user experience data. No system can access the collection database or search index directly, and you should not use the ContactRepository and ContactManager classes in a non-tracking context.
  • The tracker records all the contact’s activities into session and, converts all that experience data when session ends, and submits it to xConnect using the xConnect Client API.


xConnect Client Web API

The xConnect Client API is a portable web API that allows trusted clients to create, read, update, and search contacts and interactions over HTTPS. The xConnect Client API implements the oData protocol. The xConnect Client API is different from the tracker, both have individual responsibilities. However, the tracker depends on the xConnect Client API to read and write experience data.

Working with xConnect

To start working with xConnect and to create contacts, interactions, we should get a client config into local using client certificate thumbprint. This client config gets the sitecore xconnect context into your .NET based independent application.

  public static XConnectClient GetClient()
            CertificateWebRequestHandlerModifierOptions options =

            var certificateModifier = new CertificateWebRequestHandlerModifier(options);
            List<IHttpClientModifier> clientModifiers = new List<IHttpClientModifier>();
            var timeoutClientModifier = new TimeoutHttpClientModifier(new TimeSpan(0, 0, 200));

            var collectionClient = new CollectionWebApiClient(new Uri("https://sc91.xconnect.local/odata"), clientModifiers, new[] { certificateModifier });
            var searchClient = new SearchWebApiClient(new Uri("https://sc91.xconnect.local/odata"), clientModifiers, new[] { certificateModifier });
            var configurationClient = new ConfigurationWebApiClient(new Uri("https://sc91.xconnect.local/configuration"), clientModifiers, new[] { certificateModifier });

            var cfg = new XConnectClientConfiguration(
                new XdbRuntimeModel(CollectionModel.Model), collectionClient, searchClient, configurationClient);

            ServicePointManager.Expect100Continue = true;
            ServicePointManager.DefaultConnectionLimit = 9999;
            ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls12 | SecurityProtocolType.Ssl3;
            cfg.Initialize(); // cfg.InitializeAsync();
            return new XConnectClient(cfg);


Creating Contact with interaction and basic facets.

In below code snippet you can find code for creating a contact , getting a client config into context, creating pre-defined facets such as personal information, email, profile picture of contact can also be included in facets as below.

   /// <summary>
        /// Creating contact with interaction,event and facets.
        /// </summary>
        /// <param name="registerViewModel"></param>
        /// <returns></returns>
        public static async Task<bool> CreateContactWithInteraction(RegisterViewModel registerViewModel)
                using (var client = GetClient())
                    var offlineGoal = Guid.Parse("A9948719-E6E4-46D2-909B-3680E724ECE9"); //Any offline goal which suits your requirement.
                    var channelId = Guid.Parse("3FC61BB8-0D9F-48C7-9BBD-D739DCBBE032"); // /sitecore/system/Marketing Control Panel/Taxonomies/Channel/Offline/Store/Enter store 

                    #region Identifier
                    var Identifiers = new ContactIdentifier[]{
                    new ContactIdentifier("TechAspect",registerViewModel.Email,ContactIdentifierType.Known)
                    var contact = new Contact(Identifiers);
                    #region Personal Information facet
                    var personalInfo = new PersonalInformation()
                        FirstName = registerViewModel.FirstName,
                        LastName = registerViewModel.LastName,
                        Gender = registerViewModel.Gender,
                        Birthdate = registerViewModel.DOB,
                        JobTitle = registerViewModel.JobTitle,
                        Nickname = registerViewModel.FirstName,
                        Title = registerViewModel.JobTitle,
                        PreferredLanguage = "English"
                    client.SetFacet<PersonalInformation>(contact, PersonalInformation.DefaultFacetKey, personalInfo);

                    #region Email Facet
                    var EmailAddressesFacet = new EmailAddressList(new EmailAddress(registerViewModel.Email, true), EmailAddressList.DefaultFacetKey);
                    client.SetFacet<EmailAddressList>(contact, EmailAddressesFacet);

                    #region Interaction
                    Interaction interaction = new Interaction(contact, InteractionInitiator.Contact, channelId, "");
                    // Add events - all interactions must have at least one event
                    var xConnectEvent = new Goal(offlineGoal, DateTime.UtcNow);

                    #region Avatar Facet
                    var Thumbnail = new Avatar(Avatar.DefaultFacetKey, registerViewModel.ContactImage);
                    Thumbnail.Picture = registerViewModel.ContactImage;
                    Thumbnail.MimeType = "image/jpeg";
                    client.SetFacet<Avatar>(contact, Avatar.DefaultFacetKey, Thumbnail);

                    await client.SubmitAsync();

                    var operations = client.LastBatch;
                    return true;
            catch (XdbCollectionUnavailableException ex)
            return false;


Getting Contact by a identifier
  /// <summary>
        /// Getting contact by a contact identifier
        /// </summary>
        /// <param name="identifier"></param>
        /// <returns></returns>
        public static async Task<RegisterViewModel> GetContactById(string identifier)
            using (var client = GetClient())
                // Get a known contact
                IdentifiedContactReference reference = new IdentifiedContactReference("TechAspect", identifier);
                Contact existingContact = await client.GetAsync<Contact>(reference, new ContactExpandOptions(new string[] { PersonalInformation.DefaultFacetKey, EmailAddressList.DefaultFacetKey }));
                #region Personal Information Facet
                PersonalInformation existingContactFacet = existingContact.GetFacet<PersonalInformation>(PersonalInformation.DefaultFacetKey);
                RegisterViewModel resultContact = new RegisterViewModel();
                resultContact.ContactId = Guid.Parse(existingContact.Id.ToString());
                resultContact.FirstName = existingContact.Personal().FirstName;
                resultContact.LastName = existingContact.Personal().LastName;
                resultContact.JobTitle = existingContact.Personal().JobTitle;
                resultContact.Gender = existingContact.Personal().Gender;
                resultContact.DOB = existingContact.Personal().Birthdate.Value;

                #region Email Facet
                EmailAddressList emailFacet = existingContact.GetFacet<EmailAddressList>(EmailAddressList.DefaultFacetKey);
                resultContact.Email = existingContact.Emails().PreferredEmail.SmtpAddress;

                return resultContact;


Making a contact Anonymous

Once you create a contact into xDB and if no more need a contact we cant directly delete a contact, but there is one option available , xConnect provides one method to make a list of contacts forgotten: “ExecuteRightToBeForgotten(contacts)”. we can make that particular contact as anonymous so that particular contact is in-directly deleted from xDB. To make a contact as Anonymous , below code snippets can be used.

    /// <summary>
        /// Forgetting Contacts
        /// </summary>
        /// <param name="identifier"></param>
        /// <returns></returns>
        public static async Task<bool> ForgetAllContacts(string identifier)
                using (var client = GetClient())
                    var queryable = client.Contacts.WithExpandOptions(new ContactExpandOptions("Personal", "Emails", "Avatar"));

                    var results = await queryable.ToSearchResults();
                    var contacts = await results.Results.Select(x => x.Item).Where(x=>x.Identifiers.Select(c=>c.IdentifierType == ContactIdentifierType.Known && c.Identifier==identifier).FirstOrDefault()).FirstOrDefault();
                    await client.SubmitAsync();
                    return true;
            catch (NullReferenceException ex)
                return false;

Things to take care once xConnect is up and running

  • As mentioned up make sure 3 windows services are up and running whenever you need sitecore xConnect to do your contact related activities.
  • Solr_6.6.2 (Relevant to your solr version)
  • Sitecore xConnect Search Indexer
  • Sitecore Marketing Automation Engine.
  • Installed security certificates should have proper access and permissions to installed user
  • Also make sure your firewall wont block xConnect or certificates from installation.
  • Whenever data is in-consistent or half-populated , please rebuild reporting database and do swap Solr index with rebuild_xdb.
  • User have admin permissions since xConnect try to edit Registry keys, and many system resources.


About The Author

Leave a Reply