Akshay Sura - Partner
26 Aug 2018
In this video, I am going to walk you through how to use xConnect in a Sitecore Commerce Engine solution.
We will:
Useful links:
If you have any questions or concerns, please get in touch with me. (@akshaysura13 on twitter or on Slack).

using System ;using System . Collections . Generic ;using System . Linq ;using System . Threading . Tasks ;using Konabos . XConnect . Loyalty . Model . Facets ;using Konabos . XConnect . Loyalty . Model . Models ;using Sitecore . Commerce . Core ;using Sitecore . Commerce . Plugin . Customers ;using Sitecore . XConnect ;using Sitecore . XConnect . Client ;using Sitecore . XConnect . Client . WebApi ;using Sitecore . XConnect . Collection . Model ;using Sitecore . XConnect . Schema ;using Sitecore . Xdb . Common . Web ;using Plugin . Konabos . Loyalty . Components ;using Sitecore . Framework . Pipelines ;using Microsoft . Extensions . Logging ; namespace Konabos . Loyalty . Feature . ReconcilePoints . Pipelines . Blocks{public class UpdateCustomerInxDBBlock : PipelineBlock < Customer , Customer , CommercePipelineExecutionContext >{private readonly IPersistEntityPipeline _persistEntityPipeline ;private readonly IFindEntitiesInListPipeline _findEntitiesInListPipeline ; public UpdateCustomerInxDBBlock ( IPersistEntityPipeline persistEntityPipeline , IFindEntitiesInListPipeline findEntitiesInListPipeline ){_persistEntityPipeline = persistEntityPipeline ;_findEntitiesInListPipeline = findEntitiesInListPipeline ;} public override async Task < Customer > Run ( Customer customer , CommercePipelineExecutionContext context ){CertificateWebRequestHandlerModifierOptions options =CertificateWebRequestHandlerModifierOptions . Parse ( "StoreName=My;StoreLocation=LocalMachine;FindType=FindByThumbprint;FindValue=BC9B7186102910E8F34EE8D9F38138203F7555BA" ); var certificateModifier = new CertificateWebRequestHandlerModifier ( options ); List < IHttpClientModifier > clientModifiers = new List < IHttpClientModifier >();var timeoutClientModifier = new TimeoutHttpClientModifier ( new TimeSpan ( 0 , 0 , 20 ));clientModifiers . Add ( timeoutClientModifier ); var collectionClient = new CollectionWebApiClient ( new Uri ( "https://cateringdemo.xconnect.dev.local/odata" ), clientModifiers , new [] { certificateModifier });var searchClient = new SearchWebApiClient ( new Uri ( "https://cateringdemo.xconnect.dev.local/odata" ), clientModifiers , new [] { certificateModifier });var configurationClient = new ConfigurationWebApiClient ( new Uri ( "https://cateringdemo.xconnect.dev.local/configuration" ), clientModifiers , new [] { certificateModifier }); var cfg = new XConnectClientConfiguration (new XdbRuntimeModel ( LoyaltyModel . Model ), collectionClient , searchClient , configurationClient ); try{await cfg . InitializeAsync ();}catch ( XdbModelConflictException ce ){context . Logger . LogError ( string . Format ( "{0}-Error in UpdateCustomerInxDBBlock connecting to xDB : {1}" , ( object ) this . Name , ( object ) ce . Message ), Array . Empty < object > ());}using ( var client = new XConnectClient ( cfg )){try{IdentifiedContactReference reference = new IdentifiedContactReference ( "CommerceUser" , string . Concat ( customer . Domain , "\", customer.Email));Contact existingContact = client.Get<Contact>(reference, new ContactExpandOptions(new string[] { PersonalInformation.DefaultFacetKey, LoyaltyPointsFacet.DefaultFacetKey, LoyaltyCommerceFacet.DefaultFacetKey })); if (existingContact != null){//Add an identifier for the contact with the Commerce Customer Idstring identifierSource = " LoyaltyCustomerId ";var loyaltyCustomerIdentifier = existingContact.Identifiers.Where(i => i.Source == identifierSource).FirstOrDefault();if (loyaltyCustomerIdentifier == null){client.AddContactIdentifier(existingContact, new ContactIdentifier(identifierSource, customer.Id.ToString(), ContactIdentifierType.Known));client.Submit();} //Add or Update Loyalty Points for the customerLoyaltyPointsFacet loyaltyPointFacet = existingContact.GetFacet<LoyaltyPointsFacet>(LoyaltyPointsFacet.DefaultFacetKey);if (loyaltyPointFacet == null)loyaltyPointFacet = new LoyaltyPointsFacet(); loyaltyPointFacet.PointsEarned = customer.GetComponent<LoyaltyComponent>().PointsEarned;loyaltyPointFacet.PointsSpent = customer.GetComponent<LoyaltyComponent>().PointsSpent; client.SetFacet<LoyaltyPointsFacet>(existingContact, LoyaltyPointsFacet.DefaultFacetKey, loyaltyPointFacet);client.Submit(); //Add or Update the Commerce Customer IDLoyaltyCommerceFacet loyaltyCommerceFacet = existingContact.GetFacet<LoyaltyCommerceFacet>(LoyaltyCommerceFacet.DefaultFacetKey);if (loyaltyCommerceFacet == null)loyaltyCommerceFacet = new LoyaltyCommerceFacet(); loyaltyCommerceFacet.CommerceCustomerId = customer.Id.ToString();client.SetFacet<LoyaltyCommerceFacet>(existingContact, LoyaltyCommerceFacet.DefaultFacetKey, loyaltyCommerceFacet);client.Submit();}}catch (XdbExecutionException ex){context.Logger.LogError(string.Format(" { 0 }- Error in UpdateCustomerInxDBBlock updating customer { 2 } to xDB : { 1 } ", (object)this.Name, (object)ex.Message, customer.Id.ToString()), Array.Empty<object>());}}return customer;}}}You might get the following error while the running xConnect code:
[ Error ] [ "XdbContextLoggingPlugin" ] XdbContext Batch Execution ExceptionSystem . Net . Http . HttpRequestException : An error occurred while sending the request . ---> System . Net . WebException : The underlying connection was closed : Could not establish trust relationship for the SSL / TLS secure channel . ---> System . Security . Authentication . AuthenticationException : The remote certificate is invalid according to the validation procedure .at System . Net . TlsStream . EndWrite ( IAsyncResult asyncResult )at System . Net . ConnectStream . WriteHeadersCallback ( IAsyncResult ar )--- End of inner exception stack trace ---at System . Net . HttpWebRequest . EndGetRequestStream ( IAsyncResult asyncResult , TransportContext & context )at System . Net . Http . HttpClientHandler . GetRequestStreamCallback ( IAsyncResult ar )--- End of inner exception stack trace ---at System . Runtime . ExceptionServices . ExceptionDispatchInfo . Throw ()at System . Runtime . CompilerServices . TaskAwaiter . HandleNonSuccessAndDebuggerNotification ( Task task )at Sitecore . Xdb . Collection . Search . Solr . SolrReader .< ExecuteQuery > d__14 `1.MoveNext()--- End of stack trace from previous location where exception was thrown ---at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw()at System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(Task task)at Sitecore.Xdb.Collection.Search.Solr.SolrReader.<GetSearchResults>d__13` 2.MoveNext ()--- End of stack trace from previous location where exception was thrown ---at System . Runtime . ExceptionServices . ExceptionDispatchInfo . Throw ()at System . Runtime . CompilerServices . TaskAwaiter . HandleNonSuccessAndDebuggerNotification ( Task task )at Sitecore . Xdb . Collection . Search . Solr . SolrReader .< SearchContacts > d__10 . MoveNext ()--- End of stack trace from previous location where exception was thrown ---at System . Runtime . ExceptionServices . ExceptionDispatchInfo . Throw ()at System . Runtime . CompilerServices . TaskAwaiter . HandleNonSuccessAndDebuggerNotification ( Task task )at Sitecore . Xdb . Collection . Repository .< SearchContacts > d__11 . MoveNext ()--- End of stack trace from previous location where exception was thrown ---at System . Runtime . ExceptionServices . ExceptionDispatchInfo . Throw ()at System . Runtime . CompilerServices . TaskAwaiter . HandleNonSuccessAndDebuggerNotification ( Task task )at Sitecore . Xdb . Collection . RepositoryCountersDecorator .< SearchContacts > d__8 . MoveNext ()--- End of stack trace from previous location where exception was thrown ---at System . Runtime . ExceptionServices . ExceptionDispatchInfo . Throw ()at System . Runtime . CompilerServices . TaskAwaiter . HandleNonSuccessAndDebuggerNotification ( Task task )at Sitecore . XConnect . Service . RepositorySearchInvoker .< Execute > d__7 . MoveNext ()published
certlm
Please add your Solr cert to the Local Computer\Trusted Root Certification Authorities.
You might get the following error while the running xConnect code:
2018 - 08 - 25 15 : 01 : 10.453 - 07 : 00 [ Information ] XConnect Test Host Application Start , Machine : "DESKTOP-BCOM790" , Site : "cateringdemo.xconnect.dev.local" , AppId : "/LM/W3SVC/2/ROOT"2018 - 08 - 25 15 : 01 : 11.584 - 07 : 00 [ Information ] Certificate Validation Filter Enabled , Thumbprint : BC9B7186102910E8F34EE8D9F38138203F7555BA2018 - 08 - 25 15 : 01 : 11.585 - 07 : 00 [ Information ] SSL Validation Filter Enabled2018 - 08 - 25 15 : 01 : 12.865 - 07 : 00 [ Information ] SystemPerformanceCounters Constructor , Instance : cateringdemo . xconnect . dev . local , Path : C : inetpubwwwrootcateringdemo . xconnect . dev . localApp_DataDiagnostics , CounterFilePattern : *. json2018 - 08 - 25 15 : 01 : 12.882 - 07 : 00 [ Error ] Access to the registry key 'Global' is denied .System . UnauthorizedAccessException : Access to the registry key 'Global' is denied .at Microsoft . Win32 . RegistryKey . Win32Error ( Int32 errorCode , String str )at Microsoft . Win32 . RegistryKey . InternalGetValue ( String name , Object defaultValue , Boolean doNotExpand , Boolean checkSecurity )at Microsoft . Win32 . RegistryKey . GetValue ( String name )at System . Diagnostics . PerformanceMonitor . GetData ( String item )at System . Diagnostics . PerformanceCounterLib . GetPerformanceData ( String item )at System . Diagnostics . PerformanceCounterLib . get_CategoryTable ()at System . Diagnostics . PerformanceCounterLib . CategoryExists ( String machine , String category )at System . Diagnostics . PerformanceCounterCategory . Exists ( String categoryName , String machineName )at System . Linq . Enumerable . WhereEnumerableIterator `1.MoveNext()at System.Linq.Buffer` 1. . ctor ( IEnumerable `1 source)at System.Linq.Enumerable.ToArray[TSource](IEnumerable` 1 source )at Sitecore . XConnect . Diagnostics . PerformanceCounters . SystemPerformanceCounters . Initialize ( String counterFilePattern )2018 - 08 - 25 15 : 01 : 13.331 - 07 : 00 [ Information ] Create "XdbContextLoggingPlugin"2018 - 08 - 25 15 : 01 : 13.341 - 07 : 00 [ Information ] Register "XdbContextLoggingPlugin"
Please add your xConnect site app pool user to the Performance Monitor Users group.
Follow us on Twitter Follow us on LinkedIn Follow us on YouTube

Akshay is a nine-time Sitecore MVP and a two-time Kontent.ai. In addition to his work as a solution architect, Akshay is also one of the founders of SUGCON North America 2015, SUGCON India 2018 & 2019, Unofficial Sitecore Training, and Sitecore Slack.
Akshay founded and continues to run the Sitecore Hackathon. As one of the founding partners of Konabos Consulting, Akshay will continue to work with clients to lead projects and mentor their existing teams.