When dealing with live websites, it is desired to have lower environments that mirror production as closely as possible. Why? Because this improves your quality assurance and user acceptance processes on pretty much anything that you build, change or configure in the site. With a similar environment it’s easier to find things that will not work in production well before it reaches the live site. This is a good practice and we use this approach frequently with our clients at Brainjocks.
Recently we had an interesting experience where we created a lower environment that mirrored production in all aspects and we decided to write this post to share some of the issues we saw and how we fixed them. In our scenario we had 2 content delivery servers, 1 content management and 1 dedicated server for Commerce Engine. Each of the servers had Commerce Server installed but the engine would run only in the dedicated server. Each server was a VM so we had Azure IaaS. SQL server ran in Azure Cloud. This was a Sitecore 8.2 version running commerce 8.2.1. But these steps should be valid for Sitecore 9 running with commerce. Here are the steps we took to get it done.
1- Clone the VMs
There are a few ways one can approach this, but the ultimate goal is you want to have the same number of virtual machines running the same roles. In our case that meant 2 content deliveries, 1 content management and 1 commerce engine so we cloned them and copied the disks over to the new environment(let’s call it staging) so when that process was finished we had in all servers the same setup as production in it’s own staging Azure resource group.
2- Backup and restore SQL databases
Backup all your production databases. These must include Sitecore’s standard core, master, web, reporting, etc as well as commerce databases such as catalogs, profiles, administration database, global and shared. Restore them into SQL staging resource group.
3- Create DNS entries
Let’s say you have a domian yoursite.com running in production, cm.yoursite.com in CM and yourcommerceaddress.com:5000 (assuming the engine runs on port 5000) for the commerce engine, you will want something similar for a lower environment so you will need a DNS entry that maps to the new servers resolving staging.yoursite.com for CDs, cm.staging.yoursite.com for CM and staging.yourcommerceaddress.com:5000. So you need DNS entries to a lower environment each one for each role essentially.
4- Update source code with Staging configurations
In our case, we use continuous integration and automated deployments so all environments need to be supported appropriately so we created build profiles for each staging server(StagingCM, StagingCD1, StagingCD2, StagingCommerce) so we could generate the packages to be deployed automatically. We also use configuration transformation so the hostnames for each environment need to be properly set, i.e. production CD hostname is yoursite.com we need to set hostname for staging as well in this case staging.yoursite.com. This is valid for all configurations that are custom for the environments CM and CDs.
5- Update connection strings
Make sure the connection strings are updated to the new staging SQL instance. In the Sitecore servers(CM and CDs) update the App_Config/Include/ConnectionString.config file. In the commerce server there are a few areas where changes need to be made but first stop IIS in the server where commerce engine runs. Within your commerce engine path(under wwwroot) update the global.json as well as the commerce engine roles that you have(for example Habitat.CommerceAuthoring.json) and make sure all of them now point to the new sql staging. For more info please read this article.
6- Update connection to administration database
When you have commerce server running it needs an administration database which stores connection strings for catalogs, profiles among other resources. You need to make sure that your commerce server administration database points to the new staging sql as well as update all the connections within the database.
To update the connection with the administration database you need to unconfigure commerce server and reconfigure it(otherwise the registry key will still point to production administration database). To do so run C:Program Files (x86)Commerce Server 11CSConfig.exe /u. This will unconfigure commerce server in the virtual machine. Now run C:Program Files (x86)Commerce Server 11CSConfig.exe /f command and provide Azure SQL connection information in the Administration Database screen. This needs to be done on each server(cm, cds and commerce engine server).
After the connection to the administration database is updated open the Commerce Server application and update each site resource with the proper connection string. For example the product catalog connection string below needs to point to the new staging databases:
Do that for all applications within your Site(in example above all site resources under CFSolutionStorefrontSite).
After these steps are done reboot your server and open commerce server one more time and confirm that all applications are pointing to the right place and the administration database points to the new staging sql. To do that go into Commerce Server Manager and click “Administration Database”(see below) and confirm that the connection string matches to the proper server:
This is all good but what if I open my commerce server application and get an error? How can I update that in this case?
If you have an error while opening the commerce server that means the administration database is probably still pointing to the wrong server so you need to unconfigure and reconfigure as shown above. Another way to update the site resources is run a SQL script which pretty much does the same as if you had to update each resource within commerce server. There are two scripts that you need to run if you want to update them like that:
<pre>DECLARE @OldMachineName nvarchar(255) DECLARE @NewMachineName nvarchar(255) DECLARE @OldServerName nvarchar(255) DECLARE @NewServerName nvarchar(255) SET @OldMachineName = 'Set here the production VM name' SET @NewMachineName = 'Set here the staging VM name' SET @OldServerName = 'set here the production sql instance' SET @NewServerName = 'set here the staging sql instance' IF @OldMachineName is not null AND @NewMachineName is not null BEGIN UPDATE Resources SET s_DisplayName = REPLACE(s_DisplayName,@OldServerName,@NewServerName ) , s_Computer = REPLACE(s_Computer,@OldMachineName,@NewMachineName) UPDATE ResourceProps SET s_value=REPLACE(CONVERT(nvarchar(4000),s_value),@OldMachineName,@NewMachineName ) UPDATE ResourceProps SET s_value=REPLACE(CONVERT(nvarchar(4000),s_value),@OldServerName,@NewServerName ) END </pre>
Second script to update the database Mysite_profiles in table SourceDef:
<pre>DECLARE @OldServerName nvarchar(255) DECLARE @NewServerName nvarchar(255) SET @OldServerName = 'set here the production sql instance' SET @NewServerName = 'set here the staging sql instance' IF @OldServerName is not null AND @NewServerName is not null BEGIN Update SourceDef SET ConnStr = REPLACE(ConnStr,@OldServerName,@NewServerName) END </pre>
7- Bootstrap commerce engine
Now that all your configurations are properly set you need to bootstrap commerce engine to apply the configurations in the staging environment.
That’s it folks. Hopefully this step-by-step will be helpful for anyone with a similar scenario.