-
Notifications
You must be signed in to change notification settings - Fork 12
CircleCI and Sonarcloud
CircleCI is a continuous integration and delivery platform that helps us automate the process of building, testing, and deploying their code. It supports multiple programming languages and provides a scalable infrastructure for developers to continuously build, test, and deploy their applications with ease.
SonarCloud is a cloud-based code analysis platform that helps us manage and maintain the quality of our code. It provides a centralized platform for analyzing code quality in real time, enabling teams to make informed decisions about code improvements and ensuring the maintenance of a high standard of code quality. SonarCloud integrates multiple development tools and provides a comprehensive view of code quality, helping teams identify and resolve issues early in the development cycle.
The .circleci folder, located in the root directory, contains the CircleCI configuration file. This file, named config.yml, holds the necessary configuration information that CircleCI uses to run your builds. You can access the file here.
version: 2.1 # CircleCI version
orbs:
sonarcloud: sonarsource/[email protected]
-
version: 2.1
specifies the version of CircleCI that should be used for this project. -
orbs
is a key in CircleCI that allows you to reuse pre-packaged commands, jobs, and executors in your configuration. -
sonarcloud: sonarsource/[email protected]
specifies the use of the sonarcloud orb, which is provided by SonarSource. The orb version 1.1.1 is specified, which ensures that this particular version of the orb is utilized in this CircleCI configuration.
jobs:
build:
machine: #Linux machine instead of docker environment
image: ubuntu-2004:202111-01
docker_layer_caching: true
Inside the file, within the jobs
section, you can define a custom job, here named build
.
We'll be using the ubuntu-2004:202111-01
image, which has everything needed to run our builds on CircleCI. And we have set docker_layer_caching
to true which utilizes the cache mechanism of Docker to optimize build times. It stores the file system changes made during a build in a cache and uses this cache in subsequent builds to avoid having to download dependencies and perform time-consuming tasks again. This results in faster builds as dependencies are only re-downloaded when their source code changes, and intermediate images can be reused across builds. This feature is especially useful for projects with large dependencies and frequent builds, allowing us to achieve faster feedback and quicker build times.
steps:
- checkout:
path: ~/user/
- restore_cache:
key: user-dependency-cache-{{ checksum "src/package.json" }}
- run:
name: Install dependencies
command: cd src/ && npm install
- save_cache:
key: user-dependency-cache-{{checksum "src/package.json"}}
paths:
- ./src/node_modules
The CircleCI configuration now features dependency caching, which speeds up the build process by reusing previous dependencies. The restore_cache
step checks if a cache exists, and if it does, it restores it to the job. This allows npm install
to only install dependencies that are not in the cache. Once all dependencies are loaded, the save_cache
step saves the updated dependency tree to a new cache in the node_modules
directory.
It's important to note that both restore_cache
and save_cache
include key identifiers, such as {{ checksum "package-lock.json" }}
. This is a dynamic value generated by a template that calculates the SHA256 hash of the contents of the "package.json" file and adds "user-dependency-cache-" to the result. If the contents of "package.json" (or any other dependency management file specified in the cache-key) change, restore_cache
will miss, and save_cache
will create a new cache.
- run:
name: Executing unit test cases
command: cd src && npm test -- --collectCoverage --collectCoverageFrom="services/helper/*"
- store_artifacts:
path: src/coverage/
destination: /coverage/
The above code runs unit test cases for a Node.js project. It specifies a command to change the current working directory to src and then execute the npm test command with two command line options: --collectCoverage
and --collectCoverageFrom="services/helper/\*"
.
The --collectCoverage
option enables the collection of code coverage information during the test run. The --collectCoverageFrom="services/helper/*" option further restricts the coverage collection to only the files located in the services/helper directory.
This step is executed in the context of a CircleCI build job, and its output (such as test results and coverage reports) is saved as artifacts for later analysis or viewed in the CircleCI UI. This is useful for preserving build outputs, such as log files, test reports, or compiled code so that they can be reviewed or used as inputs for later stages of the CI/CD pipeline.
- sonarcloud/scan
- run:
name: Checking prerequisites
command: |-
docker-compose --version
- run:
name: Starting the docker containers
command: |-
cd dev-ops/ && docker-compose up -d
- run:
name: Running test cases
command: |-
cd src/ && npm run test:integration
- store_test_results:
path: ./dev-ops/report
The above code is a series of CircleCI configuration steps for a project that uses Docker containers. The steps perform the following actions:
-
sonarcloud/scan
is a pre-defined CircleCI step that performs a code analysis using SonarCloud. - Check the version of the
docker-compose
command, to ensure that it is installed and available. - Start the Docker containers for the project by running the
docker-compose up -d
command from the dev-ops directory. - Run the integration test cases for the project by executing the npm run test:integration command from the src directory.
- Store the test results generated during the previous step, by saving the contents of the ./dev-ops/report directory as CircleCI artifacts.
The store_test_results
step is especially useful for preserving and reviewing the test results so that the build can be evaluated and validated before deploying it to production.
workflows:
build-and-test:
jobs:
- build:
context:
- SonarCloud
filters:
tags:
only:
- develop
The workflow is named build-and-test
and contains a single job named build. The context property of the job specifies that it should use the SonarCloud context, which is a pre-configured environment that provides access to SonarCloud.
The filters
property of the job is used to specify the conditions under which the job should run. In this case, the tags filter is used to specify that the job should only run when the Git branch is develop
. This allows you to control when the build and test process runs, based on the branch that is being built.
This is just a basic example, and the actual configuration of your workflow may vary depending on the specific requirements of your project. However, this code should give you an idea of how to use CircleCI workflows and filters to control the build and test process for a project that uses SonarCloud.
The 'sonar-project.properties' file in the root directory of our project is used to add custom properties to SonarCloud. It is a configuration file that defines the project properties used by SonarCloud to analyze and measure the code quality, security, and maintainability, such as the project key, name, version, language, and source code location. The file can also specify custom settings, rules, and integrate with plugins and tools to improve the analysis process and provide in-depth insights.
sonar.projectKey=ELEVATE-Project_user
sonar.organization=elevate-project
sonar.projectName=User
sonar.projectVersion=1.0
sonar.sources=src/
sonar.exclusions=src/integration-test/**/*,src/test/*
sonar.coverage.exclusions=src/api-doc/**/*,src/db/**/model.js,src/module/**/*,src/validators/**/*,src/integrationJest.config.js,src/setupFileAfterEnv.js
sonar.tests=src/
sonar.test.inclusions=src/integration-test/**/*,src/test/*
sonar.javascript.lcov.reportPaths=src/coverage/lcov.info
sonar.projectKey
is a unique identifier for the project, sonar.organization
is the name of the organization to which the project belongs, sonar.projectName
is the name of the project, and sonar.projectVersion
is the version of the project.
sonar.sources
and sonar.exclusions
define the location of the source code and the files that should be excluded from the analysis.
sonar.coverage.exclusions
specifies files that should be excluded from code coverage analysis.
sonar.tests
and sonar.test.inclusions
define the location of the test files and the specific test files to be included in the analysis.Read more about the exclutions and inclutions here.
sonar.javascript.lcov.reportPaths
provides the path to the lcov file, which contains information about the code coverage of the project.