GitLab CI/CD
GitLab CI/CD is configured entirely via a single YAML file committed at the root of your repository: .gitlab-ci.yml. Every push triggers the pipeline.
Anatomy of a pipeline
Section titled “Anatomy of a pipeline”stages: - build - test - deploy
variables: IMAGE_TAG: $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA
build:image: stage: build image: docker:24 services: - docker:24-dind script: - docker build -t $IMAGE_TAG . - docker push $IMAGE_TAG
test:unit: stage: test image: node:22-alpine script: - npm ci - npm test
deploy:production: stage: deploy script: - kubectl set image deployment/app app=$IMAGE_TAG only: - mainKey concepts
Section titled “Key concepts”Stages and jobs
Section titled “Stages and jobs”- Stages define the order of execution. All jobs in a stage run in parallel.
- Jobs are the atomic units of work. A job fails → the stage fails → pipeline stops (by default).
Variables
Section titled “Variables”| Variable | Description |
|---|---|
$CI_COMMIT_SHA | Full commit hash |
$CI_COMMIT_SHORT_SHA | Short 8-char hash — useful for image tags |
$CI_COMMIT_REF_NAME | Branch or tag name |
$CI_REGISTRY_IMAGE | Full path to the GitLab container registry image |
$CI_PROJECT_ID | Numeric project ID |
$CI_ENVIRONMENT_NAME | Name of the deployment environment |
Rules vs only/except
Section titled “Rules vs only/except”Prefer rules: — it’s more expressive and evaluated in order:
deploy:staging: rules: - if: $CI_COMMIT_BRANCH == "develop" - if: $CI_MERGE_REQUEST_ID when: neverRunning a job locally
Section titled “Running a job locally”$ gitlab-runner exec docker test:unit Running with gitlab-runner 17.0.0 (HEAD) Preparing the “docker” executor… Using Docker executor with image node:22-alpine… Pulling docker image node:22-alpine… Running on runner-local via hostname… Getting source from Git repository… Executing “step_script” stage of the job script $ npm ci added 412 packages in 8s $ npm test PASS src/utils.test.ts Test Suites: 1 passed, 1 total Job succeeded
Security checklist
Section titled “Security checklist”- Never echo secrets — use masked CI/CD variables
- Pin runner images to specific digests, not
latest - Enable
SECURE_ANALYZERS_PREFIXto pull scanners from your mirror registry - Use protected variables for production credentials
- Enable pipeline security reports (SAST, dependency, container scanning)
Next steps
Section titled “Next steps”- Pipeline Security — add SAST, image scanning, and secrets detection