Автоматизация пентеста в CI/CD: безопасность до деплоя, не после
Здравствуй, воин клавиатуры! 🔥 Пора зашить безопасность в конвейер, а не тушить пожар после релиза. Гоняем очередной репорт — «security as code», без соплей, только payload’ы и yaml.
Точка входа: почему «после деплоя» — уже поздно
Классика провала: пентест раз в квартал, а между сканами накопилось 200 коммитов с новыми зависимостями и дырами. Формула DevSecOps простая — чем раньше находишь баг, тем дешевле его чинить: на этапе кода это копейки, в проде — инцидент, репутационные потери и разбор полётов с клиентом. Смещаем проверки влево (shift left) и бьём тревогу на каждый push, а не на релиз.
Карта стадий: что сканить и где
CI/CD — это конвейер с чёткими точками контроля, под каждую — свой класс инструментов:
| Стадия пайплайна | Что проверяем | Инструменты |
|---|---|---|
| Pre-commit / код | Секреты, утечки токенов | gitleaks, TruffleHog |
| Build (SAST) | Уязвимые паттерны в коде | Semgrep, CodeQL, Bandit, Gosec |
| Build (SCA) | Дырявые зависимости | Snyk, OWASP Dependency-Check, Trivy |
| Package | Уязвимости в Docker-образах | Trivy, Grype, Clair |
| IaC | Мисконфиги Terraform/K8s | Checkov, Terrascan |
| Staging / после деплоя | Живые баги в работающем приложении | OWASP ZAP, Nuclei |
Каждая стадия — отдельный gate. WAF — не стена, а приглашение, но пайплайн без gate — открытая дверь с ковриком «welcome, hacker».
Секреты и SAST: ловим на входе
Первый рубеж — не пускать хардкод-пароли и API-ключи в репу. Ставь pre-commit хук с detect-secrets или gitleaks локально у разработчиков, а в CI — обязательный шаг, который валит билд при находке:
- name: Secrets scan
uses: gitleaks/gitleaks-action@v2
Дальше — SAST. Semgrep рвёт по скорости и покрывает JS/TS/Python/Go одним движком с готовыми правилами под OWASP Top 10:
- name: SAST scan
run: semgrep ci --config=auto
Контейнеры и зависимости: не тащи дыры в прод
Собрал Docker-образ — прогони Trivy до пуша в registry, иначе твой красивый минимальный Alpine окажется с уязвимой libssl внутри:
- name: Container scan
uses: aquasecurity/trivy-action@master
with:
image-ref: myapp:latest
exit-code: 1
severity: CRITICAL,HIGH
Флаг exit-code: 1 — это твой gate: находит критическую CVE — валит пайплайн, деплой не проходит. Без этого сканирование превращается в красивый, но бесполезный отчёт, который никто не читает.
DAST после деплоя: nuclei в бою
На staging нужен живой прогон против реально работающего приложения — тут в дело идёт nuclei-action, официальный GitHub Action от ProjectDiscovery:
name: DAST-scan
on:
push:
branches: [staging]
jobs:
scan:
runs-on: ubuntu-latest
timeout-minutes: 10
steps:
- uses: actions/checkout@v4
- name: Run Nuclei
uses: projectdiscovery/nuclei-action@v3
with:
args: -u https://staging.example.com -severity critical,high -tags cve,exposure
Лайфхак от опытных ребят: всегда вешай timeout-minutes на джобу со сканом. Завис скан — встал весь пайплайн, включая деплои, стоящие в очереди за ним. Забыл — и твой конвейер превращается в пробку на Кутузовском в пятницу вечером.
Результаты можно выгружать в SARIF и публиковать прямо в GitHub Code Scanning — тогда находки Nuclei ложатся рядом с findings от CodeQL в одной вкладке Security.
Лайфхаки и грабли
- Не сканируй прод напрямую первым запуском. Гоняй Nuclei и ZAP на staging-копии, иначе легитимный скан выглядит как настоящая атака и вызывает панику у SOC.
- Разделяй gate по severity. Критические уязвимости — блокируют деплой, medium/low — создают issue, но не рушат билд. Иначе разработчики просто выключат твой pipeline через неделю.
- Регулярно обновляй темплейты и правила. Свежие nuclei-templates и Semgrep-rules ловят вчерашние 0day, устаревшие — только позавчерашние.
- Собирай всё в один дашборд. DefectDojo или ASPM-платформа типа Cycode агрегируют находки SAST/SCA/DAST в единый список, иначе разработчики тонут в пяти разных отчётах.
- Секреты — приоритет номер один. Утечка одного AWS-ключа в коммите весит больше, чем десять XSS в форме обратной связи.
Собери пайплайн так: секреты → SAST → SCA/контейнер → IaC → деплой на staging → DAST → gate на прод. Каждая стадия — фильтр, и только чистый код долетает до продакшена. Зашей это в пентест-практику, и админы перестанут думать, что их код безопасен просто потому, что «тесты прошли» 😎.
Похожие статьи

Как писать RedTeam-отчёт: чтобы не уснул ни CTO, ни разработчик

Nuclei templates: пиши свои, перестань быть скриптокиддером
