DevSecOps Guide 2026: Security in Every Stage of the Pipeline
Advertisement
DevSecOps 2026: Shift Security Left
The average data breach costs $4.45 million and takes 277 days to identify. DevSecOps catches vulnerabilities before they reach production — at a fraction of the cost.
- SAST: Static Code Analysis
- Dependency Scanning
- Secrets Detection
- Container Security Scanning
- SBOM: Software Bill of Materials
- Infrastructure Security
- Security Checklist for Every PR
SAST: Static Code Analysis
# .github/workflows/security.yml
name: Security Scanning
on: [push, pull_request]
jobs:
# CodeQL: Finds security vulnerabilities in code
codeql:
name: CodeQL Analysis
runs-on: ubuntu-latest
permissions:
security-events: write
strategy:
matrix:
language: ['javascript', 'typescript']
steps:
- uses: actions/checkout@v4
- uses: github/codeql-action/init@v3
with:
languages: ${{ matrix.language }}
queries: security-and-quality
- uses: github/codeql-action/autobuild@v3
- uses: github/codeql-action/analyze@v3
with:
category: '/language:${{ matrix.language }}'
Dependency Scanning
# Check for known vulnerabilities in dependencies
dependency-scan:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: npm audit
run: npm audit --audit-level=high
# Fails if high or critical vulnerabilities found
- name: Snyk dependency scan
uses: snyk/actions/node@master
with:
args: --severity-threshold=high
env:
SNYK_TOKEN: ${{ secrets.SNYK_TOKEN }}
- name: OWASP Dependency Check
uses: dependency-check/Dependency-Check_Action@main
with:
project: 'webcoderspeed'
path: '.'
format: 'HTML'
args: >
--failOnCVSS 7
--enableRetired
- uses: actions/upload-artifact@v4
with:
name: dependency-report
path: reports/
Secrets Detection
# Find accidental secrets committed to code
secrets-scan:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0 # Full history for Gitleaks
- name: Gitleaks - detect secrets
uses: gitleaks/gitleaks-action@v2
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: TruffleHog scan
uses: trufflesecurity/trufflehog@main
with:
path: ./
base: ${{ github.event.repository.default_branch }}
extra_args: --debug --only-verified
# .gitleaks.toml — Custom rules
[[rules]]
description = "Custom API Key"
regex = '''(?i)webcoderspeed[_\-]?api[_\-]?key['":\s]+[a-zA-Z0-9]{20,}'''
tags = ["api", "custom"]
[allowlist]
paths = [".gitleaks.toml", "tests/"]
regexes = ["EXAMPLE_KEY", "YOUR_KEY_HERE"]
Container Security Scanning
# Scan Docker images for vulnerabilities
container-scan:
runs-on: ubuntu-latest
needs: build
steps:
- name: Trivy scan
uses: aquasecurity/trivy-action@master
with:
image-ref: 'ghcr.io/${{ github.repository }}:${{ github.sha }}'
format: 'sarif'
output: 'trivy-results.sarif'
severity: 'CRITICAL,HIGH'
exit-code: '1' # Fail on critical/high
- uses: github/codeql-action/upload-sarif@v3
with:
sarif_file: 'trivy-results.sarif'
# Security hardening in Dockerfile
FROM node:20-alpine
# Don't run as root
RUN addgroup --system --gid 1001 nodejs && \
adduser --system --uid 1001 nodeuser
# Install security updates
RUN apk update && apk upgrade && rm -rf /var/cache/apk/*
# Read-only filesystem
WORKDIR /app
COPY . .
USER nodeuser
# No new privileges
# Use: docker run --security-opt=no-new-privileges myapp
SBOM: Software Bill of Materials
# Generate inventory of all dependencies
sbom:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Generate SBOM with Syft
uses: anchore/sbom-action@v0
with:
format: spdx-json
output-file: sbom.spdx.json
- uses: actions/upload-artifact@v4
with:
name: sbom
path: sbom.spdx.json
Infrastructure Security
# Terraform: Security group — principle of least privilege
resource "aws_security_group" "api" {
name = "api-sg"
vpc_id = aws_vpc.main.id
# Allow only HTTPS inbound
ingress {
from_port = 443
to_port = 443
protocol = "tcp"
cidr_blocks = ["0.0.0.0/0"]
}
# Deny all other inbound by default
# Allow all outbound (restrict for sensitive apps)
egress {
from_port = 0
to_port = 0
protocol = "-1"
cidr_blocks = ["0.0.0.0/0"]
}
}
# Never allow SSH from 0.0.0.0/0 in production
# Use AWS Systems Manager Session Manager instead
Security Checklist for Every PR
# .github/pull_request_template.md
## Security Checklist
- [ ] No secrets or API keys committed (Gitleaks passed)
- [ ] No new HIGH/CRITICAL vulnerabilities (npm audit passed)
- [ ] Input validation on all new API endpoints
- [ ] Authorization check for user-owned resources
- [ ] SQL queries use parameterized statements
- [ ] New dependencies reviewed for security
- [ ] Sensitive data not logged
Security is not a feature you add at the end — it's a discipline you practice throughout development. One leaked secret or unpatched vulnerability is all it takes.
Advertisement