Monday, December 25, 2023

CI/CD Pipeline for SFCC - Jenkins - part I

Story time: Setting up an efficient CI/CD Pipeline for Salesforce Commerce Cloud

A little bit of context

Our main vendor was running this capability, which enabled the team to run deployments once per week or maybe every other day. That seemed great as the status quo;

However, waiting for a build to complete in 3-4 hours doesn't work for me, the goal was to enable the team to deploy at least every hour or less.

Following a nice combination of creativity plus thinking outside of the box, we setup a pipeline which deploys under 15 minutes (12) to 4 different Instances of SFCC (DEV, INT, QA and STG).

I am not going to showcase what it looked like in the past, because water under the bridge



Overview

Jenkins is an open source automation server. It helps automate the parts of software development related to building, testing, and deploying, facilitating continuous integration, and continuous delivery. It is a server-based system that runs in servlet containers such as Apache Tomcat.

Build great things at any scale

Jenkins provides hundreds of plugins to support building, deploying and automating any project.

We decided to set it up on a VM in Azure since that's what we have. We started with a Windows VM for the following reason, we wanted to mirror as much as possible the original setup done by our vendor so we could leverage if there was any institutional knowledge. 

In a future iteration we might use Linx and why not, a Dockerized image.

The fun part is in the job

  • Be organized

Yourself from the future will thank you


  • Define a unique and short name in order to avoid issues with file system limitations


Your newly created workspace

  • Add a meaningful description
  • Define a clear build strategy - build retention - this will help you to manage your disk space
  • Reference your GitHub repo



  • Make use of Display Name



  • Enable CI/CD! - This is where we let Jenkins do the checking if there is a new change that needs to be deployed - currently we set that value to 30


  • Always delete your workspace in order to prevent old code to be present, we always need a fresh copy of the repo
  • Add timestamps to the Console Output - they are super helpful
  • Clean up your workspace, but be selective so it will be fast

Not everything has to be deleted when you clean up your workspace

  • Use secret bindings (no hardcoded passwords!)



  • Add your own build steps. Since you-all came to see the cooking recipe for SFCC Deployments, here it is:

The steps are quite self explanatory, however one pre-requisiten is to have installed SFCC-CLI

Windows batch commands

:: Setting variables
call set PREFIX=DEVOPS
call set PATH=%PATH%;C:\Program Files\7-Zip
call set COMMIT_SHORT=%GIT_COMMIT:~0,7%
call set BRANCH=%GIT_BRANCH:/=_%
call set BUILD_VERSION=%PREFIX%_%BRANCH%_%BUILD_NUMBER%_%COMMIT_SHORT%

:: Delete Folders to skip
call rmdir /S /Q cartridges\useless_folder

:: Install NPM & Build project
:: --silent flag suppress output
call npm install --silent
call npm run build --silent

:: Package build
:: Since workspace is always cleaned, this next step is optional
call rmdir /S /Q %BUILD_VERSION%
call mkdir %BUILD_VERSION%

:: Robocopy
:: skipping files: .project .tern-project .gitignore README.md *.java *.c *.php
:: skipping folders: .settings junk
call robocopy cartridges %BUILD_VERSION% /E /Z /ZB /R:5 /W:5 /TBD /NP /V /MT:16 /XF .project .tern-project .gitignore README.md *.java *.c *.php /XD .settings junk

:: 7z
:: "-mx[N]" specifies compression level
:: "-mmt[N]" set number of CPU threads
call 7z a %BUILD_VERSION%.zip %BUILD_VERSION% -mx9 -mmt16


Shell commands

#Setting variables export PREFIX="DEVOPS" export TARGET_INSTANCE_DEV="development-domain.demandware.net" export TARGET_INSTANCE_INT="integration-domain.demandware.net" export TARGET_INSTANCE_QA="cert.qa.domain.demandware.net" export TARGET_INSTANCE_STG="cert.staging.domain.demandware.net" export COMMIT_SHORT="${GIT_COMMIT::7}" export BRANCH=${GIT_BRANCH//\//} export BUILD_VERSION=${PREFIX}${BRANCH}${BUILD_NUMBER}${COMMIT_SHORT} echo "DEPLOYING $BUILD_VERSION TO $TARGET_INSTANCE_DEV, $TARGET_INSTANCE_INT, $TARGET_INSTANCE_QA and $TARGET_INSTANCE_STG" #Login into SFCC npx sfcc-ci client:auth --selfsigned $SFCC_CLIENT $SFCC_CLIENT_SECRET --renew #Deploy package npx sfcc-ci code:deploy $BUILD_VERSION.zip -i $TARGET_INSTANCE_DEV npx sfcc-ci code:deploy $BUILD_VERSION.zip -i $TARGET_INSTANCE_INT npx sfcc-ci code:deploy $BUILD_VERSION.zip -i $TARGET_INSTANCE_QA -c $SFCC_TEST_REALM_CERT -p $SFCC_TEST_REALM_CERT_SECRET npx sfcc-ci code:deploy $BUILD_VERSION.zip -i $TARGET_INSTANCE_STG -c $SFCC_REALM_CERT -p $SFCC_REALM_CERT_SECRET


Some things to consider, we leveraged P12 Cert to deploy to our QA and STG environment to make sure we take advantage of 2FA.

So there you have it. 

Feel free to use this as your baseline and please share your refined versions.





No comments:

Post a Comment