Tag Archives: sitecore

How to configure Sitecore Blue/Green deployment on Kubernetes

With Sitecore announcing that they will no longer support Azure App Service from version 10.2, more and more Sitecore customers will need to start to think about and plan the inevitable upgrade from their current application development and hosting environment to the ways of containers and Kubernetes.

As I’ve helped more and more Sitecore solutions moving to the Kubernetes platform, I see common requests where they want to maintain the Blue/Green deployment as part of the quality assurance process.

I’d like to share with you the process of implementing Blue/Green deployment on Kubernetes and it doesn’t matter whether you’re using Azure Kubernetes Service (AKS), Amazon Elastic Kubernetes Service (EKS), or Google Kubernetes Service (GKS). You can apply the same principle to any of the Kubernetes managed service that you have.

Kubernetes Rolling-Forward deployment

The default Kubernetes deployment model is a rolling forward deployment model. In which, the new version of applications that you deployed will live side-by-side with the old versions for a short amount of time until they are ready to be swapped over and receive live traffic. This entire process is automated and when done correctly supports zero downtime.

An ilustration of the rolling forward deployment model

Let’s describe what happens in the example above:

1. Version 1 of the application are running on Kubernetes and serving live traffic.
2. A new version was deployed and the deployment instruction defined 2 replicas of version 2 to be deployed. At this point, one CD pod have been created.
3. The deployed version 2 then gets initialized, running, passed the health checks and ready to receive live traffic. Kubernetes then start to redirect live traffic to the pod. Another new version 2 pod has been created.
4. The latest version 2 pod now ready to receive traffic and Kubernetes starts to redirect live traffic to that pod. Now all live traffic are hitting version 2 pods.

As you can see above, the switch for version 2 to be made publicly available is done automatically, and some customers might have a different requirement where they want version 2 to be tested by their internal tester before giving the go-ahead for going live as part of their quality assurance process.

Kubernetes Blue/Green Deployment

Now let’s take a look at how we can implement Blue/Green deployment.

Here’s a quick ilustration.

Essentially the main difference here is the fact that we have a separate Kubernetes service for version 1 and version 2, labelled as CD-Blue and CD-Green.

Once version 2 is fully deployed, we’ll update Kubernetes Ingress which is responsible for routing the live traffic request to a service (either CD-Blue and CD-green)

An example of Kubernetes Ingress manifest pointing live traffic to cd-blue

apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: cd-ingress
  annotations:
    nginx.ingress.kubernetes.io/proxy-buffer-size: "32k"
    nginx.ingress.kubernetes.io/affinity: "cookie"
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  rules:
  - host: www.habitat-demo.com.au
    http:
      paths:
      - path: /
        backend:
          serviceName: cd-blue
          servicePort: 80
  - host: uat.habitat-demo.com.au
    http:
      paths:
      - path: /
        backend:
          serviceName: cd-green
          servicePort: 80

And that’s it. Without going into too many details that’s how you would implement a Blue/Green deployment with your Sitecore solution on Kubernetes.

Hope this helps.

Sitecore implementation strategies to mitigate production environment issues

I’ve found the following techniques proves to be very handy in ensuring a smooth website operation, especially if you’re running a mission critical site for example an online shopping site or other high traffic site.

Feature Toggles

Feature toggles is a software design pattern which enables you to modify the behavior of the software without modifying the code – https://martinfowler.com/articles/feature-toggles.html

It’s a simple technique yet ridiculously powerful if used correctly.

We’ve used feature toggles for different reasons:

Release toggles

You have a shiny new feature that you are working on in the current release that’s half finished and not yet ready to be included in the next deployment schedule but you don’t want to keep it in a long lived feature branch? – merge it in the main branch and use feature toggle to make it dormant.

Got to deploy that new header components but it’s not a 100% done yet? – use feature toggle.

Got a cool new Sitecore renderings which displays different look and feel and defined in a custom Sitecore device? – use feature toggle to control the roll out.

Ops toggles

Got a sudden spike in server resources grinding the server to a halt due to a sudden spike in traffic ? Ideally you should plan this out with the client to mitigate the sudden traffic increase which could come from a marketing department campaign activity – if not, turn off some of the non critical and resource intensive operation in the site using feature toggle to reduce the load.

Got a poor performing functionality in the site? I hope you’re doing some sort of performance test before deploying it in the first place so you can caught it earlier¬† ūüôā – if not, then I hope you implemented feature toggle to turn it off.

Implementation

no code example here, it’s very basic – didn’t I mention this is a very simple technique?

The core implementation that I’ve used is using Sitecore content item and item publish.

  • I have a multi site implementation
  • Each site has a feature toggles folder
  • Feature toggles folder contains different types of feature toggle Sitecore items, for example:
    • Enable new Header layout
    • Enable site notifications
    • Enable contact us email forwarding

Every feature toggles, contains the basic functionality, a single checkbox to define whether the functionality should be enabled/disabled. that’s it.

You can extend the functionality to also include IP white-listing, Country detection etc go nuts ūüėÄ

 

Sitecore Site Snippet

Another simple technique for mitigation is using Sitecore site snippet.

The site snippet I’m referring here is javascript and css hacks to modify the behavior or look and feel of the site on the browser. A sticky plaster fix if you like, it gives you the ability to fix the issue quickly without requiring file deployment and give you time to focus on doing a proper fix to be included in the next deployment schedule.

You can of course deploy a hotfix which contains js or css files which also works of course, if you have multiple Content Delivery servers make sure you have easy deployment process where you can just press a single button to get it done.. or use site snippet

Implementation

Site snippet that I’ve done is just a custom API endpoint which returns a js or css syntax

  • Define the API controller endpoints
    • /api/sitesnippet/js
    • /api/sitesnippet/css
  • I have multi site implementation
  • Each site has a Site Snippets folder
  • Site Snippets folder contains different types of snippet Sitecore items, for example
    • Hide newsletter component from footer (css)
    • Override click event from the subnav component (js)
  • Those site snippets would then be managed through a Site Snippet Configuration where admin can select which site snippet to be activated

 

CDN Cache Rules

If you’re using CDN such as CloudFlare, it can act as an Application Gateway where you can define custom rules to mitigate certain issues which occurs on your site.

Have you encountered some of these issues?

  • You have a public API endpoint which suddenly gets abused by malicious hacker
  • Certain API endpoints of your site is responding poorly and it’s affecting all the sites in the same server instance
  • etc

with CloudFlare you can block those endpoints using CF rules to prevent the issues from becoming a major disaster, providing you time to come up with proper planning to tackle the issue.

That’s all for now, let me know if you have some other techniques which you’d like to share.

Extend Sitecore Engagement Plan UI to assign contacts to an engagement plan state

The default Sitecore Engagement Plan currently supports the following option to assign users/contacts to an engagement plan state

  • Add from CSV File
  • Add a Sitecore user
  • Add all Members of a Sitecore Role
  • Add a Segment

Out off all those options only the segment option have the capability of assigning existing contacts to an engagement plan state.

However, what if we would like to import contacts from a CSV file there’s no option to do so, the Add from CSV file will import the data as Sitecore users instead of contacts.

We would need to modify the UI in order to achieve the functionality that we’re aiming for. To do so first we would need to figure which file to modify.

As the UI is using Silverlight it’s a bit difficult to figure which file we need to modify, however searching for the “Welcome to the Import Contacts Wizard” text under the /sitecore ¬†folder reveals that this file seems to be the correct one

Further inspecting the code inside that file and tinkering with it a bit confirms that this is the correct file to modify.

We will not modify the existing Sitecore file, instead we will use the Override folder in order to apply our modification to the existing XML control. To do this copy and paste the existing ImportVisitors.xml file to the override folder

You can put the file directly inside the Override folder, but it’s good practice to¬†replicate the original folder paths so you know which file you’re overriding.¬†After we now know which file to modify we can start modifying the default behaviour of that XML control.

The modified ImportVisitors.xml

 

The code beside file

 

The end result

Source Code is available in GitHub

 

 

Sitecore Server Role Checker Tool

When configuring Sitecore in a distributed environment, you typically have more than 1 server in the production environment configured as a different roles (CM, CD, Processing, Reporting Service, etc).

More often than not I’ve noticed that issues are raised due to misconfiguration rather than implementation¬†itself. You then go to Sitecore documentation site and check the configuration for each of the server that you’ve setup to see if there’s anything that you miss.

In the 8.0 documentation you would need to read a long list of tables containing information which config files that you need to enable/disable.

Since the 8.1 release, these steps are simplified with Sitecore providing us an excel spreadsheet file as a guide to enable/disable the config files depending on the role(s) that you want to setup. These steps are manual though and highly likely that we will miss one or two config files and could cause some issues down the line.

With the number of projects that you need to review, this task will start eating up your time and should really be automated. Some might have already done so and create a little tool tucked away somewhere.

I’ve decided to create my own version of the tool called Sitecore Server Role Checker, can’t be more obvious than that ūüôā

How does it work?

This tool would basically uses a converted csv format from the Sitecore official spreadsheet guide and read the configuration based on your selected roles. It currently supports the following Sitecore version

  • 8.1 update 3
  • 8.2 initial release
  • 8.2 update 1
  • 8.2 update 2

Only those version is supported as those are only the spreadsheet available for now.

How do I use it?

Follow this simple steps

  1. Choose your Sitecore version
  2. Choose your search engine provider
  3. Browse to your website folder
  4. Tick your intended role(s) for this particular Sitecore instance
  5. Click the Analyze button

It would then go through each of your configuration files and report if there’s any config files that should be enabled/disabled.

Through the tool you can also quickly disable/enable those config files.

What it doesn’t do

  • Check if your config files is updated accordingly, e.q:
    • Changing robot detection handler in CM
    • Configuring remote reporting service url
    • etc
  • Check the configuration files for WFFM, EXM.. yet
  • Make you coffee

Where can I get it?

The code is available in Github

Note that this tool is not deeply tested, if you have any issues or suggestions with the tool then raise a ticket in Github or do a PR

update: 22 February 2017

The tool is now available at Sitecore Marketplace

Sitecore SOLR index update strategies in a scaled environment

Sitecore by default ships with two main search provider which is Lucene or SOLR.

I will not delve too much on which one you should use as that’s been covered in¬†https://doc.sitecore.net/sitecore_experience_platform/setting_up__maintaining/search_and_indexing/indexing/using_solr_or_lucene

I’d like to highlight some of the points mentioned in the article, where using SOLR is mandatory:

  1. You have a dedicated processing server
  2. You have multiple CM servers

The main thing here is that if sitecore_analytics_index exist in multiple servers then you would need to¬†use SOLR.¬†But¬†since all the indexes are now in a centralized server, what’s the index update strategies for SOLR would be?

Typically in this setup you would set

  • CM as the indexing server
    • will perform index rebuild
    • Set the index update strategies as you fit (except manual)
  • CD¬†only reads from index
    • Does not perform index rebuild
    • Set the index update strategies to manual

If you have multiple CM server then you can set one of the CM as the one that perform index rebuild while the other one only reads from the index.

https://doc.sitecore.net/sitecore_experience_platform/setting_up__maintaining/search_and_indexing/indexing/index_update_strategies

Rebuild sitecore_analytics_index contact data

There’s been an interesting question around how to rebuild the sitecore_analytics_index but specifically only for contact data.

As you’ve probably know that sitecore_analytics_index is not available to be indexed manually – go to the indexing manager in the control panel if you want to check. This is because the index is configured using an observer crawlers.

However there are ways to manually rebuild the sitecore_analytics_index. The example given in that seems to be specifically about rebuilding the interactions documents while what we want is to build the contacts.

I gained some hints from the provided example though, let’s have a look at the following code.

In particular this line

I then go to the handy showconfig.aspx page to find the following

Which shows the processingPools configured for the aggregation processes. From there I can spot the contact element definition which seems to be the one that I’m looking for and start building the code for it.

result:

Depending on your needs, you might want to only reindex known contacts for example. You can take the above example and adjust it yourself.

 

Sitecore 8 – how to update contact through FXM API

This post will talk through how to setup a custom actions to be executed to update Sitecore contact through FXM API. If you don’t know about FXM you can read a brief overview about it in the Sitecore site¬†and the doc site

If you’ve played around with FXM¬†and it’s javascript API¬†then you would know that you can trigger client side call to send information back to Sitecore regarding the current visitor browsing behaviour. But¬†what does one do if we want to update the Contact information instead? say the current visitor email address if they fill out a newsletter subscription form? or their unique user id if they have logged in through the external application?

Looking at the available javascript FXM API there’s these three methods available:

  1. SCBeacon.trackEvent
  2. SCBeacon.trackGoal
  3. SCBeacon.trackOutcome

and there’s no such things as SCBeacon.updateContact which we sought after. After some investigation there’s a couple of ways to do this.

1. A custom web service call to the Sitecore server

Setup a custom web service in Sitecore server and pass in the current visitor contact id for custom processing. Doable but I’m looking for something that can be done through the same javascript API if possible as it would mean greater coverage – can be reused by other external site.¬†By doing it through FXM javascript API we don’t have to setup web service call in¬†each external sites.

2. Modify the beacon script to include our custom function 

Modify the beacon script¬†and include the custom SCBeacon.updateContact function. Figured¬†that this won’t be ideal as we would muck around with the bundled javascript and won’t be compatible in Sitecore future upgrades.

3. Hook into one of the available methods to do some custom processing

This seems like the best place to start. Out of the available methods I choose to override the trackEvent tracking implementation because the action that I want to captured falls to “system” type action, doesn’t relate to conversion (Goal) or has monetary value (Outcome). Plus if I use page events then by default the events triggered will not show in the Experience Profile which might confused the marketers.

OK, let’s do this.

This is done with the latest Sitecore version at the time of writing which is 8.1 update 3.

First let’s open the Sitecore.FXM.config in /website/app_config/include/fxm folder

I opened up Sitecore.FXM.Pipelines.Tracking.TriggerPageEvent.RunRegisterPageEventProcessor using dotPeak to find out that it will run the tracking.registerpageevent pipeline

When I take a look at Sitecore.FXM.Pipelines.Tracking.RegisterPageEvent.RegisterPageEventProcessor and what it does it seems this would be the best place to put my custom logic

We can override the TriggerPageEvent method and implement our custom processing.

The next step is for us to create our custom Processor class which extends from Sitecore’s default¬†RegisterPageEventProcessor

After that we need to register our custom processor class in the config file. For best practice use Sitecore config file patching to do.

In our custom config file we override the default processor class to process the triggered page events with our custom processor class. Put the file in /website/app_config/include/zzz.POC/ folder

Now that we have our custom processor class and have registered it through the custom config file, we need to create the actual page event items in Sitecore.

Here’s what the created page event items looks like in my setup.

registered-custom-page-events

And now to test it out, browse to the external site  and open the developer console to run these javascripts

We can check the end result in MongoDB after the session has timeout

updated-contact-through-FXM

And in the Experience Profile

updated-contact-through-FXM-xFile

That’s it folks.

 

Sitecore 8 – Create a custom personalization rule

Sitecore OOTB comes with tons of personalization rules that we can use, however there might be times where we need to create a custom rule condition that fits to the client business requirements.

Luckily with Sitecore framework that’s known easy to extend, we can easily achieve this.

Here’s the steps to create a custom personalization rule:

1.Register the tag

First of all we need to create a new tag item under /sitecore/system/Settings/Rules/Definitions/Tags

create-custom-personalization-rule-create-tag

2. Register a new rule element

Create a new element folder in /sitecore/system/Settings/Rules/Definitions/Elements

create-custom-personalization-rule-create-element-folder

3. Create a new personalization condition rule

create-custom-personalization-rule-create-personalization-rule

Here I’m creating a new rule and calling it¬†“Specific Template Name” which will do what exactly that, checking if the current¬†context item is based on a specific template name – not really useful in real world scenario but this post is about how to setup a custom personalization rule ūüôā

In the newly created rule we need to set the Text and Type fields

Text field contains the text that we’re going to present to the content author, here’s the following text that I use

the [TemplateName, StringOperator,,compares to] represents the format of input that we want to get from the content author. It follows the following format

  • OperatorId,¬†defines the public property of the class where we want to assign the value coming from the content author input
  • StringOperator, the built-in macro that we want to use to get the input from the user. In this case this will be a string¬†comparation operation
  • blank, this parameter will depend on the type of macro that we use, this could be a default text value if we are using the default macro,¬†¬†it could be a default start path if we’re using the Tree macro ¬†– think of it like setting a field source when we’re building a template in Sitecore. A full list of macros can be found in¬†/sitecore/system/Settings/Rules/Definitions/Macros
  • compares to, the last parameter is the text representation¬†that we want to show to the content author, this value is clickable and when clicked Sitecore will display the appropriate input control based on the macro that we set on the second parameter

The Type field is the full assembly name of the custom class that we want to use to perform the logic behind this personalization rule

4. Assign our custom element default tag definition to our custom tag

create-custom-personalization-rule-assign-element-tag-definition-to-tag

Of course we  can assign our custom element tag definition to one of the existing tag under /sitecore/system/Settings/Rules/Definitions/Tags so that it will automatically appear on the content author personalization rule window however if you want to make it obvious which one is your custom ones then I recommend creating your own custom tag and assign it to that

5. Assign the tag to Conditional Rendering

The last step to make the rule visible for the content author to choose from is to assign our custom tag to one of default Rules Context folder

create-custom-personalization-rule-assign-tag

From the picture we’re setting the tag to the Conditional Rendering rules context which will appear when the user want to personalize a certain component, but you can also some other Rules Context folders such as FXM ones.

After we assign the tag, we can verify that the custom personalization rule is available for the content author to choose from

create-custom-personalization-rule-verifying-the-custom-rule-appears

Here’s the class that’s responsible to evaluate the custom rule condition

The class logic is simple and not doing much for the purposes of the tutorial. In a real world scenario you can make a rule that reads from a custom database, read a configuration file, call an external API (be careful with this as it will increase page load time).

This may sound like a lot of work at first compared to just creating a custom code in the rendering or similar approach.¬†But when we consider that we’re enabling the content author/marketers to do it by themselves and removing/minimizing the dependency towards IT, it would lessen time to market and open up more possibilities for the marketers¬†of what they can do using the platform.

 

Sitecore 8 – set facebook profile picture in Experience Profile

This post will talk about how to retrieve the Facebook profile picture using Sitecore Social Connect module which it seems Sitecore 8.1 update 2 does not do it on default. Of course however we can hook into the Sitecore Social User LoggedIn event or similar to perform this.

First thing first, if you don’t¬†know how to setup a Facebook application with Sitecore then have a read through this article. Make sure that before going through the rest of the article you are able to sign-in using Facebook and verify that the user is created (check the Sitecore User Manager) and the contact is also created in MongoDB.

The first thing you would notice after the user is created is that the Facebook profile picture is not set by default in the Experience Profile after the user registered. This is what we’re going to address.

Reading through the Sitecore documentation on logging in using a Social Network credential¬†it seems that the process is quite straightforward. Looking at the /App_config/include/social/Sitecore.Social.config, I found that there’s a couple of events that we can hook into to add additional logic

Looks like the perfect place to put the additional logic to get the Facebook profile picture. Which I did btw

note: This is by no means production ready code.

The class above will update the current contact profile picture which is coming from their Facebook account and also a couple of other information such as name, email address, gender.

That’s it.

A couple of tips that might be useful when you want to try this on your own:

  • Set¬†Social.Logging.TraceToLog value to true to help debugging
  • You need to disable the interest field on the user’s profile as that field has been deprecated by Facebook – this is throwing an exception which I can see in the log file. You can do this by going to¬†Sitecore.Social.ProfileMapping.Facebook.config and disable the fb_interests field.
  • If you’re trying to¬†test the synchronization of user profile fields from Facebook or other social network then set¬†Social.ProfileUpdating.DaysBeforeExpiration to 0. See Sitecore documentation¬†for reference

Issues encountered with Sitecore Azure Module

I was playing around with Sitecore Azure Module last week and would like to share my experience to get the site up and running.

I am using Sitecore 8.0 version, WFFM and EXM modules. Obviously you would need the Sitecore Azure module to help you setup the content editing and content deliry farm.

  • Sitecore 8.0 rev. 160115 (8.0 Update-7)
  • Sitecore WFFM rev.¬†151127 (Update-6)
  • Sitecore EXM¬† 3.1 rev. 151213 (3.1 Update-2)
  • Sitecore Azure 8.0 rev. 150522

The target Azure setup would be

  • 1CM and 1CD server in the same data center, in my case I create the farms in the Singapore data center as it’s the closest one for me
  • Sharing the same databases for CM and CD; core, master, web, reporting. In the case of CD it will not have a reference to master and reporting
  • xDB cloud will not be used, instead MongoDB databases will be created using the free 500MB databases from¬†http://mongolab.com

Before proceeding you would need an Azure Subscription in order to be able to create the necessary VM/Cloud Service, if you’re like me and just want to try out the Sitecore Azure Module you can sign up for a free trial for one month.

Installation

In the installing Sitecore Azure Module article above, it also explain about how to deploy to Azure to setup a Editing Farm and Delivery Farm which seems to be easy and straightforward. However I encountered some issues while trying to deploy to Azure.

Issues when deploying

Error saying that the storage account already exist in Azure

Solution:

 

The storage account service name must be unique in Azure across subscriptions, meaning that it has to be unique not only for you and for other subscriptions in the Azure as well. To fix this you can go to /sitecore/system/Modules/Azure/[project_name]/[region_name]/Editing01/Storages/Default and update the Service Name field.

 

Error saying that the database server already exist

Solution:

In the¬†/sitecore/system/Modules/Azure/CampaignManagement-Evaluation/Southeast Asia/Editing01/Sql01 “Server Name” field¬†empty the value. And then clean the unused Azure SQL database server.

 

Error saying that the vmsize does not exist

Solution:

This is because the vm tier name has been changed by Microsoft, which originally was D3 is now has been updated to Standard_D3. To fix this you would need to update the /App_Config/AzureVendors/Microsoft.xml

 

With the free trial subscription you might encounter an issue when the Sitecore Azure Module tries to create the database in SQL Database S2 tier

Solution:

To fix this you can temporarily change the¬†/sitecore/system/Modules/Azure/[project-Name]/[region_name]/Editing01/Sql01/Set01/[database_name] Tier field and change it to “Basic – Basic”. This could also be caused by the database size Sitecore Azure Module requested to be created is not supported by the free trial subscription, I haven’t tested this however if you would like to try it yourself then update the /App_Config/AzureVendors/Microsoft.xml change the

to something smaller, say 100GB or 10GB

 

Another issue when trying to create the Cloud Service

Solution:

This issue seems to be related to the siteStorageSize configuration in /App_Config/AzureVendors/Microsoft.xml. I was trying to create a D3 instance which has the default size of 180GB, reducing the value to 10GB or more seems to do the trick

 

Some reference links that might helps: