GitLab Dependency Scanning and SBOMs: Get Ahead of the Next Supply-Chain Scare
Wire dependency scanning and SBOM generation into GitLab CI so you can answer 'are we affected?' in minutes the next time a popular package is compromised.
- #gitlab
- #cicd
- #dependency-scanning
- #sbom
- #supply-chain
- #security
Every few months a popular package gets compromised, and a familiar scramble begins: every engineering org on earth trying to answer one question — are we affected? The teams that answer it in ten minutes have one thing the panicking teams don’t: an up-to-date inventory of what’s actually in their software. That inventory is what dependency scanning and SBOMs give you, and GitLab CI can produce both on every pipeline.
This is how to set it up, and how to make it pay off when the next scare lands.
Dependency scanning vs. SAST
People conflate these. SAST scans the code you wrote. Dependency scanning scans the code you pulled in — your package-lock.json, go.sum, Gemfile.lock, requirements.txt, and so on. Given that modern apps are 80-95% third-party code by line count, the dependency surface is usually where the real risk lives.
GitLab’s dependency scanning reads your lockfiles, resolves the full dependency tree (including transitive deps you never explicitly added), and matches each package version against known-vulnerability databases.
The basic wire-up
It’s template-driven like the other security scanners:
include:
- template: Jobs/Dependency-Scanning.gitlab-ci.yml
stages:
- test
dependency_scanning:
stage: test
variables:
DS_EXCLUDED_PATHS: "spec, test, tests, tmp"
Findings land in the merge request’s Security tab as a gl-dependency-scanning-report.json artifact, scoped to what the MR introduced. The key behavior: if a developer bumps a dependency to a version with a known CVE, the reviewer sees it before merge. That’s the whole point — catch the bad bump at the cheapest possible moment.
SBOMs: the inventory that saves you later
A Software Bill of Materials (SBOM) is a machine-readable list of every component in your software, with versions. GitLab’s dependency scanning emits a CycloneDX SBOM as a CI artifact. Capture and retain it:
dependency_scanning:
stage: test
artifacts:
paths:
- "**/gl-sbom-*.cdx.json"
expire_in: 90 days
reports:
cyclonedx: "**/gl-sbom-*.cdx.json"
Why retain it for 90 days? Because the value of an SBOM isn’t at build time — it’s three weeks later when a CVE drops for a transitive dependency you didn’t know you had. With retained SBOMs you can grep your inventory across every service and answer “are we affected, and where?” without redeploying anything.
GitLab aggregates these into a Dependency List at the project and group level, so you get a searchable view of every component across your org. When the next xz-style backdoor hits, you search one place instead of cloning forty repos.
Don’t drown in the backlog
The first time you turn dependency scanning on against a mature repo, you will get a wall of findings. Most of them are not urgent. The trick is triage by reachability and severity, not raw count:
- Filter by severity first. Critical and High with a known exploit get attention today. Low-severity transitive findings can wait.
- Check reachability. A vulnerable function you never call is lower risk than one in your hot path. GitLab’s analyzers increasingly flag whether the vulnerable code is actually reachable — lean on that.
- Use
allow_failure: trueinitially. Make findings visible without blocking every pipeline. Tighten to blocking on Critical-only once the backlog is under control.
dependency_scanning:
allow_failure: true
rules:
- if: '$CI_PIPELINE_SOURCE == "merge_request_event"'
- if: '$CI_PIPELINE_SOURCE == "schedule"'
Running it on a schedule matters as much as running it on MRs: new CVEs are published against code you already shipped and haven’t touched. A nightly scan catches the vulnerability that appeared after your last commit.
Automate the dependency bumps
Finding a vulnerable dependency is half the job; the other half is bumping it without breaking everything. This is where I lean on AI. Hand it the finding (package, current version, fixed version) plus the relevant call sites, and ask: “what’s the breaking-change risk in this upgrade, and what in my code touches the changed API?” The model is good at reading a changelog and your usage together and telling you whether it’s a one-line bump or a refactor.
For the review of the resulting bump PR, our AI Code Review assistant flags whether a dependency change touches a risky surface and explains the diff in plain language — exactly the judgment call that eats reviewer time on a security bump. The rest of our GitLab CI/CD guides cover the container scanning and OIDC pieces that round out a supply-chain posture.
Put it together
A solid baseline: dependency scanning on every MR and on a nightly schedule, SBOMs captured as artifacts with 90-day retention and surfaced in the group Dependency List, allow_failure: true until the backlog is clean then blocking on Critical. Findings scoped to the MR so reviewers see what the change introduced.
Do that, and the next supply-chain scare becomes a search query instead of a fire drill. The inventory you build quietly on every pipeline is the thing that lets you answer “are we affected?” before the postmortem instead of during it.
Vulnerability findings, reachability assessments, and AI upgrade advice are assistive, not authoritative. Verify exploitability and test upgrades against your own systems before relying on them.
Download the Free 500-Prompt DevOps AI Toolkit
500 battle-tested, copy-paste AI prompts engineered by a senior systems engineer — every one with fill-in placeholders and safety/back-out notes. Drop your email and it's yours.
- 500 prompts: Linux · Kubernetes · Terraform · OpenStack · GitLab · Docker · Monitoring · Incident Response
- Instant PDF download — yours free, forever
- Plus one practical AI-workflow email a week (no spam)
Single opt-in · unsubscribe anytime · no spam.