SonarQube Installation
SonarQube is a Static Application Security Testing (SAST)
Prerequisites
Section titled “Prerequisites”Kubernetes Cluster
Section titled “Kubernetes Cluster”SonarQube will be installed on 🟢 Management Kubernetes Cluster
- 📥Ingress Service provided as Kubernetes Ingress Class (
IngressClass) - 🛡️TLS Certificate for SonarQube provided as Kubernetes Secret
- SonarQube will be exposed as HTTPS with Kubernetes Ingress.
Application Dependencies
Section titled “Application Dependencies”SonarQube depends on multiple dependencies to be up and running but only the following will be provisioned and/or managed by you.
- 📦PostgreSQL SQL Database ; Deploy external/dedicated instance of Database.
- Do you bring your own PostgreSQL SQL Database for SonarQube?
- In case will be installed on Kubernetes Cluster.
- Will require 💿Persistence Storage as Kubernetes Storage Class (
StorageClass)
- Will require 💿Persistence Storage as Kubernetes Storage Class (
Provisioning Summary
Section titled “Provisioning Summary”Once finished everything, these are systems that up and running.
| No. | Tool | Description | Kubernetes Namespace | Kubernetes Cluster |
|---|---|---|---|---|
| 1. | PostgreSQL for SonarQube | Database System for SonarQube | devsecops-system | 🟢 Management |
| 2. | SonarQube | Static Application Security Testing (SAST) | devsecops-system | 🟢 Management |
Complete Prerequisites
Section titled “Complete Prerequisites”Kubernetes Cluster
Section titled “Kubernetes Cluster”Prepare Shell Variables
Section titled “Prepare Shell Variables”Ensure you have defined and loaded your Global Shell Variables as described in Shell Variables.
-
Connect to
🟢 ManagementKubernetes Cluster ; i.e w/ Kubeconfig FileEnsure you have defined and loaded your Global Shell Variables as described in Shell Variables.
Terminal window source $HOME/opstella-installation/shell-values/kubernetes/management_cluster.vars.shsource $HOME/opstella-installation/shell-values/tools/sonarqube.vars.shTerminal window export KUBECONFIG="$HOME/opstella-installation/kubeconfigs/management_cluster.yaml" -
Export Required Shell Variables
Ensure
SONARQUBE_DOMAINandSONARQUBE_ADMIN_PASSWORDare defined as per the Shell Variables guide.Ensure
K8S_INTERNAL_DOMAIN,K8S_INGRESSCLASS_NAME,K8S_STORAGECLASS_NAME,K8S_INGRESS_TLS_CERTIFICATE_SECRET_NAMEare defined as per the Shell Variables guide. Additionally, export the following variables:Terminal window # PostgreSQL Backend Passwordsexport SONARQUBE_POSTGRES_SUPERUSER_PASSWORD="CHANGEME"export SONARQUBE_POSTGRES_USER_PASSWORD="CHANGEME" -
Create Kubernetes Secret for 🛡️ TLS Certificate for SonarQube in Namespace
devsecops-system.Kubernetes Ingress for SonarQube will associate TLS Certificate with Kubernetes Secret named
$K8S_INGRESS_TLS_CERTIFICATE_SECRET_NAME.Create one using from
.crtand.keyfile.Terminal window kubectl create secret tls $K8S_INGRESS_TLS_CERTIFICATE_SECRET_NAME \--cert=/path/to/cert/file --key=/path/to/key/file \--namespace devsecops-system💡 Should return
secret/... createdmessage.
Application Dependencies
Section titled “Application Dependencies”PostgreSQL SQL Database
Section titled “PostgreSQL SQL Database”-
Set PostgreSQL Information
- Database Name:
sonarqube(Defined in manifest) - Database User:
sonarqube(Defined in manifest) - Database Password:
${SONARQUBE_POSTGRES_USER_PASSWORD}(Previously exported) - Postgres Superuser Password:
${SONARQUBE_POSTGRES_SUPERUSER_PASSWORD}(Previously exported)
- Database Name:
-
Provision PostgreSQL for SonarQube
The following manifest defines the entire PostgreSQL system, including credentials and the CNPG cluster.
Terminal window kubectl apply --namespace devsecops-system -f - <<EOF---# SonarQube Postgres Superuser CredentialsapiVersion: v1kind: Secrettype: kubernetes.io/basic-authmetadata:name: sonarqube-postgres-superusernamespace: devsecops-systemstringData:username: postgrespassword: "${SONARQUBE_POSTGRES_SUPERUSER_PASSWORD}"---# SonarQube Application User CredentialsapiVersion: v1kind: Secrettype: kubernetes.io/basic-authmetadata:name: sonarqube-postgres-usernamespace: devsecops-systemstringData:username: sonarqubepassword: "${SONARQUBE_POSTGRES_USER_PASSWORD}"---# S3 Credentials for Postgres Backups (to SeaweedFS HA)apiVersion: v1kind: Secrettype: Opaquemetadata:name: sonarqube-postgres-s3-secretnamespace: devsecops-systemstringData:S3_ACCESS_KEY: "postgres-backup"S3_SECRET_KEY: "${SEAWEEDFS_HA_S3_POSTGRES_BACKUP_PASSWORD}"---apiVersion: barmancloud.cnpg.io/v1kind: ObjectStoremetadata:name: sonarqube-postgres-backupnamespace: devsecops-systemspec:# This resource defines the backup destination for the Barman Cloud Pluginconfiguration:destinationPath: s3://postgres-backups/endpointURL: http://seaweedfs-s3.apps-supporting-services.svc:9000s3Credentials:accessKeyId:name: sonarqube-postgres-s3-secretkey: S3_ACCESS_KEYsecretAccessKey:name: sonarqube-postgres-s3-secretkey: S3_SECRET_KEYwal:compression: gzipdata:compression: gzip# Retention policy for backups and WALs handled by the pluginretentionPolicy: "30d"---apiVersion: postgresql.cnpg.io/v1kind: Clustermetadata:name: sonarqube-postgresnamespace: devsecops-systemlabels:app.kubernetes.io/name: sonarqube-postgresapp.kubernetes.io/part-of: sonarqubespec:instances: 1# Image configuration (Postgres 16)imageCatalogRef:apiGroup: postgresql.cnpg.iokind: ClusterImageCatalogname: postgresql-standard-trixiemajor: 16# Enable the Barman Cloud Plugin for backupsplugins:- name: barman-cloud.cloudnative-pg.ioisWALArchiver: trueparameters:serverName: "sonarqube-postgres"barmanObjectName: "sonarqube-postgres-backup"# Storage Configurationstorage:size: 5GistorageClass: "${K8S_STORAGECLASS_NAME}"walStorage:size: 2GistorageClass: "${K8S_STORAGECLASS_NAME}"# Bootstrap Configurationbootstrap:initdb:database: sonarqubeowner: sonarqubesecret:name: sonarqube-postgres-user# Superuser credentials (root/postgres)superuserSecret:name: sonarqube-postgres-superuser# Backup Configuration (Barman Cloud Plugin will automatically detect matching ObjectStore)backup:{}# Resourcesresources:requests:memory: "256Mi"cpu: "200m"limits:memory: "1Gi"cpu: "1000m"EOF💡 Should return
secret/sonarqube-postgres-superuser,secret/sonarqube-postgres-user, andcluster.postgresql.cnpg.io/sonarqube-postgrescreated messages. -
Check for PostgreSQL for SonarQube Readiness - MUST be Ready and Running.
Get Pod Status - PostgreSQL for SonarQube
Terminal window kubectl get pods -n devsecops-system💡 PostgreSQL for SonarQube MUST be
RunningNAME READY STATUS RESTARTS AGE... (deducted)sonarqube-postgres-1 2/2 Running 0 XdXhsonarqube-postgres-2 2/2 Running 0 XdXhsonarqube-postgres-3 2/2 Running 0 XdXh
Pre-Installation
Section titled “Pre-Installation”Prepare SonarQube Resources
Section titled “Prepare SonarQube Resources”-
Install Opstella Logo for Single Sign-On Button
You will be creating Kubernetes ConfigMap named
sonarqube-opstella-logoTerminal window # Create Kubernetes ConfigMapkubectl create configmap sonarqube-opstella-logo \-n devsecops-system \--from-file=$HOME/opstella-installation/assets/files/opstella-logo.svg💡 Should return
configmap/sonarqube-opstella-logo createdmessage.
Prepare SonarQube Configurations
Section titled “Prepare SonarQube Configurations”-
SonarQube Entrypoint Domain
- Domain:
${SONARQUBE_DOMAIN}(Previously exported)
- Domain:
-
Set SonarQube Credentials for Initial Admin Account
-
Admin Username:
admin(Cannot be changed) -
Admin Password:
${SONARQUBE_ADMIN_PASSWORD}(Previously exported) -
PostgreSQL Connection and Credentials
- Use previously mentioned in Application Dependencies/PostgreSQL for SonarQube
export SONARQUBE_DB_HOST="jdbc:postgresql://sonarqube-postgres-rw.devsecops-system.svc.${K8S_INTERNAL_DOMAIN}/sonarqube?socketTimeout=1500" -
-
Create Kubernetes Secret named
sonarqube-credentialsTerminal window kubectl apply --namespace devsecops-system -f - <<EOFapiVersion: v1kind: Secrettype: Opaquemetadata:name: sonarqube-credentialsstringData:password: ${SONARQUBE_ADMIN_PASSWORD}currentPassword: adminEOF -
Create Helm Values Configurations
Terminal window cat <<EOF > $HOME/opstella-installation/helm-values/sonarqube-full-values.yaml# OPSTELLA_CUSTOMIZE/Helm: Deploy Name Overriding; defaults will deploy sonarqube pods with 'sonarqube-sonarqube-0' name, saddd.nameOverride: sonarqubefullnameOverride: sonarqube# Kubernetes: Fundamental ConfigurationsclusterDomain: ${K8S_INTERNAL_DOMAIN}# OPSTELLA_CUSTOMIZE: Disable built-in NGINX Ingress from Helm Chartnginx:enabled: false# Kubernetes: Expose through Ingressingress:enabled: truehosts:- name: ${SONARQUBE_DOMAIN}path: "/"ingressClassName: ${K8S_INGRESSCLASS_NAME}annotations:nginx.ingress.kubernetes.io/proxy-body-size: 100mingress.kubernetes.io/proxy-body-size: 100mtls:- secretName: ${K8S_INGRESS_TLS_CERTIFICATE_SECRET_NAME}hosts:- ${SONARQUBE_DOMAIN}# TODO: Application: Monitoring - Move to Existing SecretmonitoringPasscode: "P@ssw0rd"# OPSTELLA_CUSTOMIZE/Application: SonarQube Editioncommunity:enabled: true# Application: Database Configurationpostgresql:enabled: falsejdbcOverwrite:enable: true# The JDBC url of the external DBjdbcUrl: ${SONARQUBE_DB_HOST}# The DB user that should be used for the JDBC connectionjdbcUsername: sonarqube## Alternatively, use a pre-existing k8s secret containing the DB passwordjdbcSecretName: sonarqube-postgres-user## and the secretValueKey of the password found within that secretjdbcSecretPasswordKey: password# Application: SonarQube Plugins Configurations# - OIDC Pluginplugins:install:- https://github.com/vaulttec/sonar-auth-oidc/releases/download/v2.1.1/sonar-auth-oidc-plugin-2.1.1.jar## Kubernetes/Application: Authentication# The above values can be also provided by a secret that contains "password" and "currentPassword" as keys. You can generate such a secret in your cluster# using "kubectl create secret generic admin-password-secret-name --from-literal=password=admin --from-literal=currentPassword=admin"setAdminPassword:passwordSecretName: sonarqube-credentials# OPSTELLA_CUSTOMIZE/Application: Add Opstella Platform Logo for OIDC Loginpersistence:volumes:- name: opstella-logoconfigMap:name: sonarqube-opstella-logoitems:- key: opstella-logo.svgpath: opstella-logo.svgmounts:- name: opstella-logomountPath: /opt/sonarqube/web/images/opstella-logo.svgsubPath: opstella-logo.svgreadOnly: true# Kubernetes: Security ContextcontainerSecurityContext:allowPrivilegeEscalation: falseprivileged: falserunAsNonRoot: truerunAsUser: 1000runAsGroup: 0seccompProfile:type: RuntimeDefaultcapabilities:drop: ["ALL"]## OPSTELLA_CUSTOMIZE: Disable By Default to encourage configurations on Host OS instead.initSysctl:enabled: false## OPSTELLA_CUSTOMIZE: Disable By Default to encourage configurations on CSI driver instead.initFs:enabled: falseEOF
Installation
Section titled “Installation”-
Check for PostgreSQL for SonarQube Readiness - MUST be Running and Ready.
Get Pod Status - PostgreSQL for SonarQube
Terminal window kubectl get pods -n devsecops-system💡 PostgreSQL for SonarQube MUST be
RunningNAME READY STATUS RESTARTS AGE... (deducted)sonarqube-postgres-1 2/2 Running 0 XdXhsonarqube-postgres-2 2/2 Running 0 XdXhsonarqube-postgres-3 2/2 Running 0 XdXh -
Add SonarQube Helm Repository
Terminal window helm repo add sonarqube https://SonarSource.github.io/helm-chart-sonarqubehelm repo update -
Install SonarQube
-
Install a Helm Release with specific Helm Chart Version
--version 10.8.1(App Version: 10.8.1)Terminal window helm install sonarqube sonarqube/sonarqube --version 10.8.1 \--namespace devsecops-system \-f $HOME/opstella-installation/helm-values/sonarqube-full-values.yaml
-
Post-Installation
Section titled “Post-Installation”SonarQube Testing
Section titled “SonarQube Testing”-
Get Pod Status - SonarQube
Terminal window kubectl get pods -n devsecops-system💡 SonarQube should be
RunningNAME READY STATUS RESTARTS AGE... (deducted)sonarqube-0 1/1 Running 0 XdXh -
Visit
https://${SONARQUBE_DOMAIN}- It should be accessible.
- TLS Certificate should be valid and coresponding to your TLS Certificate Installed

-
Login with Users
-
Try to login with Initial Admin Account
admin,$SONARQUBE_ADMIN_PASSWORD(Log in with credentials), if success then it works.
-
Finished?
Use the below navigation to proceed