PowerShell Script for Sitecore Hotfix Installation

Note: This blog article is more applicable for Sitecore versions below 10.2.0 since they don't have an Update parameter in the SIF script. Just for reference, here is a screen shot of the SIF 10.3 PS script with Update param as well as cumulative packages copied over to the same location as the script:



Actual Article

There are situations when a co-developer runs into an issue and we tend to offer a very superficial solution. Then, the developer would comeback stating the fix didn't work when we would actually jump-in to solve the problem and realize it is not as easy as our superficial solution! Such situations always keeps us grounded!

Recently, someone had to run a hotfix on a Sitecore 10.1.0 instance. Based on Sitecore documentation, I thought it to be as easy as following the given instructions but it wasn't so easy since although I added the Update parameter all across the json files, nothing worked as expected. 

So, I decided to do a step-by-step about a couple of ways hotfixes can be applied and decide for yourself which one is better:

1. Visual Studio Approach

2. PowerShell Script Approach

Prerequisites:

1. The correct instance of Sitecore where the hotfix must be applied

2. The xConnect services of the instance must be stopped



1. Visual Studio Approach:


Create Empty ASP.NET Framework project and add projects like these:


Note: I have used separate VS projects each for Identity, xConnect and site root, set separate publish profiles each pointing to the respective web root folder:

xConnect project example:


Also note in this approach, I manually copied over files from the hotfix onto respective project. 

Although this approach is what a C# developer would follow, I felt this is intrusive and was mixing up installation/deployment and the code structure. I also was inconvenient about maintaining separate publish profiles and then the associated project dll / rosyln folder that would get published. You also have to ensure anything extra doesn't get deployed by ensuring files are set to "do not copy". Then, don't forget the dll hell and ysod in case if one wrong version dll gets into the bin folder. In case if you need to use any of the hotfix dlls for development, that is a whole different problem to address. So, let us keep other aspects out of this equation since this blog post is just focused on deploying the hotfix dlls to your local setup or any other higher environments. 

Also, the above approach would be cumbersome when you have to deploy the hotfix to higher environments. You might have to re-think or find some other way to automate the deployment pipeline process.

2. PowerShell Script Approach


In this approach, all you have to do is copy the correct hotfix file for the topology to a folder and place the following PowerShell Script and run the PowerShell script supplying the environment prefix. No other mess-up with project code involved.

The script is fairly self-explanatory:

##############################################

[CmdletBinding()]

Param ( 


[Parameter(Mandatory = $true)]

    [string]

    [ValidateNotNullOrEmpty()]

$SitePrefix = "sc103instance", 

# The root folder with the WDP files.

    [string]    

    $SCInstallRoot = ".",

# The root folder with the WDP files.

    [string]    

    $PatchType = "cumulative",

# Root folder where the site is installd. If left on the default [systemdrive]:\inetpub\wwwroot will be used

    [string]

    $SitePhysicalRoot = "c:\inetpub\wwwroot\" ,

# Site suffix matches what is used by SIA

    [string]

    $SiteSuffix = ".dev.local" 

    

)


$ErrorActionPreference = "Stop";

$SitecoreSiteName =$SitePrefix.Trim() + "sc" + $SiteSuffix

$XConnectSiteName=$SitePrefix.Trim() + "xconnect" + $SiteSuffix

$IdentityServerSiteName=$SitePrefix.Trim() + "identityserver" + $SiteSuffix


Write-Host "Unzipping the main file - " + (Get-Item "$SCInstallRoot\*.zip").FullName

# Unzip the copied over zip

Expand-Archive -Path "*.zip"  -Force



if ($PatchType -eq 'cumulative')

{

# The path to the Sitecore cumulative Package to Deploy.

$SitecorePackageZipPath = "$SCInstallRoot\*\Sitecore * rev. * (OnPrem)_single.cumulative.delta.scwdp.zip"

# The path to the Identity Server cumulative Package to Deploy.

$IdentityServerPackageZipPath = "$SCInstallRoot\*\Sitecore.IdentityServer * rev. * (OnPrem)_identityserver.cumulative.delta.scwdp.zip"

# The path to the xConnect Server cumulative Package to Deploy.

$XConnectPackageZipPath = "$SCInstallRoot\*\Sitecore * rev. * (OnPrem)_xp0xconnect.cumulative.delta.scwdp.zip"

}

else

{

# The path to the Sitecore Package to Deploy.

$SitecorePackageZipPath = "$SCInstallRoot\*\Sitecore * rev. * (OnPrem)_single.delta.scwdp.zip"

# The path to the Identity Server Package to Deploy.

$IdentityServerPackageZipPath = "$SCInstallRoot\*\Sitecore.IdentityServer * rev. * (OnPrem)_identityserver.delta.scwdp.zip"

# The path to the xConnect Server Package to Deploy.

$XConnectPackageZipPath = "$SCInstallRoot\*\Sitecore * rev. * (OnPrem)_xp0xconnect.delta.scwdp.zip"

}


# The path to the Sitecore  Package to Deploy.

$SitecorePackagePath = (Get-ChildItem $SitecorePackageZipPath).FullName

# The path to the Identity Server  Package to Deploy.

$IdentityServerPackagePath = (Get-ChildItem $IdentityServerPackageZipPath).FullName

# The path to the xConnect Server  Package to Deploy.

$XConnectPackagePath = (Get-ChildItem $XConnectPackageZipPath).FullName


$SitecorePackageUnzipPath = (Get-Item $SitecorePackageZipPath).FullName

$SitecorePackageUnzipDir = (Get-Item $SitecorePackageUnzipPath ).DirectoryName+"\"+(Get-Item $SitecorePackageUnzipPath ).BaseName


$SitecoreIdentityServerPackageUnzipPath = (Get-Item $IdentityServerPackageZipPath).FullName

$SitecoreIdentityServerPackageUnzipDir = (Get-Item $SitecoreIdentityServerPackageUnzipPath ).DirectoryName+"\"+(Get-Item $SitecoreIdentityServerPackageUnzipPath ).BaseName


$SitecorexConnectServerPackageUnzipPath = (Get-Item $XConnectPackageZipPath).FullName

$SitecorexConnectServerPackageUnzipDir = (Get-Item $SitecorexConnectServerPackageUnzipPath ).DirectoryName+"\"+(Get-Item $SitecorexConnectServerPackageUnzipPath ).BaseName


Write-Host "Unzipping the Sitecore Package file to - " + $SitecorePackageUnzipDir 

Expand-Archive -Path $SitecorePackagePath -Destination $SitecorePackageUnzipDir  -Force

Write-Host "Unzipping the Identity Package file to - " + $SitecoreIdentityServerPackageUnzipDir 

Expand-Archive -Path $IdentityServerPackagePath -Destination $SitecoreIdentityServerPackageUnzipDir  -Force

Write-Host "Unzipping the xConnect Package file to - " + $SitecorexConnectServerPackageUnzipDir

Expand-Archive -Path $XConnectPackagePath -Destination $SitecorexConnectServerPackageUnzipDir  -Force


$SitecorePackageSource = "$SitecorePackageUnzipDir\Content\Website\*"

$SitecorePackageDest = $SitePhysicalRoot + $SitecoreSiteName + '\'


Write-Host "Copying the Sitecore Package file to - " + $SitecorePackageDest

Copy-Item $SitecorePackageSource -Destination $SitecorePackageDest -Force -Recurse


$SitecoreIdPackageSource = "$SitecoreIdentityServerPackageUnzipDir\Content\Website\*"

$SitecoreIdPackageDest = $SitePhysicalRoot + $IdentityServerSiteName + "\"


Write-Host "Copying the Id Package file to - $SitecoreIdPackageDest"

Copy-Item $SitecoreIdPackageSource -Destination $SitecoreIdPackageDest -Force -Recurse



$SitecorexConnectPackageSource = "$SitecorexConnectServerPackageUnzipDir\Content\Website\*"

$SitecorexConnectPackageDest = $SitePhysicalRoot + $XConnectSiteName + '\'


Write-Host "Copying the xConnect Package file to - $SitecorexConnectPackageDest"

Copy-Item $SitecorexConnectPackageSource -Destination $SitecorexConnectPackageDest -Force -Recurse


Write-Host "Process Completed!"


##############################################

Conclusion:

Needless to say, PowerShell script is a very clean approach to add hotfix to the concerned instance. Also, PS scripts integrate so well with ci/cd pipelines. So, one approach that fits all.

Latest 10.3 hotfix installation onto 10.3 instance:


Note that the script can handle only one hotfix zip file at a time. Default is cumulative hotfix and that is a param that can be modified if a delta hotfix must be run. So, the folder must have only one hotfix zip file. It then unzips that one file and deploys to the respective site root, xconnect and identityserver instance. 

Ensure to start the xConnect services once the packages are deployed.

Fresh 10.3 instance:




After the run (ensure to start the stopped xConnect services):



Comments