Периметр
под напряжением.
Найдено 47 findings, из них 6 критичных, 14 средних. Самый дорогой риск — захват e-mail-домена через DMARC=none + dangling-CNAME у mail-staging.
Что нужно чинить сегодня.
Reflected XSS на /search?q=
Пользовательский ввод параметра q попадает в DOM без экранирования. Воспроизведено на главном поиске и на поддомене docs.acme-corp.io. Эксплуатация: один HTTP-запрос, без авторизации.
// payload GET /search?q=<svg/onload=alert(1)> HTTP/1.1 Host: acme-corp.io // response (200, in <h1>) <h1>Результаты по запросу: <svg/onload=alert(1)></h1>
DMARC=none + dangling CNAME для mail-staging
Запись mail-staging.acme-corp.io указывает на удалённый Heroku-инстанс — кандидат на subdomain takeover. В сочетании с DMARC p=none позволяет провести фишинг от имени домена.
// CNAME chain mail-staging.acme-corp.io CNAME acme-mail-stg.herokuapp.com acme-mail-stg.herokuapp.com → 404 No such app // DMARC _dmarc.acme-corp.io TXT "v=DMARC1; p=none; rua=mailto:..."
SQLi (boolean-based) в /api/v1/orders?status=
Параметр status склеивается в SQL-запрос без bind. Time-based проверка: ' AND SLEEP(5)-- — отклик 5.07 сек.
GET /api/v1/orders?status=open' AND SLEEP(5)-- HTTP/1.1 Authorization: Bearer eyJ... // 200 OK · 5.07s (baseline 0.12s)
Открытый /actuator на admin-api.acme-corp.io
Spring Boot Actuator доступен без аутентификации. Доступны /env, /heapdump, /loggers. Утечка переменных окружения, в том числе строк подключения.
GET /actuator/env HTTP/1.1 Host: admin-api.acme-corp.io // 200 OK { "propertySources":[{ "name":"systemEnvironment", "properties": { "DATABASE_URL": "postgres://app:Z9q...@..." }}]}
SSRF через параметр /api/preview?url=
Эндпоинт превьюшек принимает произвольный URL. Удалось обратиться к internal IMDS (169.254.169.254) и получить метаданные инстанса.
Открытый /.git на legacy.acme-corp.io
Каталог /.git доступен по HTTP. Скачивание дерева восстанавливает исходный код проекта 2022 года, включая статичные ключи Yandex Cloud.
Можно отложить на спринт.
| ID | Finding | Модуль | CVSS | Severity | Хост |
|---|---|---|---|---|---|
| F-007 | Отсутствует Content-Security-Policy | Headers | 5.4 | MED | acme-corp.io |
| F-008 | X-Frame-Options не установлен | Headers | 4.3 | MED | app.acme-corp.io |
| F-009 | HSTS max-age=300 (рекомендуется ≥31536000) | TLS | 3.7 | MED | acme-corp.io |
| F-010 | Открытый swagger.json на /api/docs | Surface | 5.0 | MED | api.acme-corp.io |
| F-011 | jQuery 1.11.3 (CVE-2020-11023) | Tech | 6.1 | MED | legacy.acme-corp.io |
| F-012 | SPF + ~all вместо -all | DNS | 3.4 | MED | acme-corp.io |
| F-013 | Cookie без флага HttpOnly (sessionId) | Headers | 5.0 | MED | app.acme-corp.io |
| F-014 | Открытый /robots.txt раскрывает /internal/ | Surface | 3.1 | MED | acme-corp.io |
| F-015 | Reflected open-redirect /go?to= | Pentest | 6.4 | MED | acme-corp.io |
| F-016 | Поддомен dev.acme-corp.io доступен извне | Surface | 5.5 | MED | dev.acme-corp.io |
Что чинить и в каком порядке.
Ранжировано по impact ÷ effort. Можно экспортировать в Jira / Linear / GitHub Issues одной кнопкой.
Удалить dangling CNAME mail-staging
Удалите неиспользуемую DNS-запись и перейдите на DMARC p=quarantine
Закрыть /.git на legacy
Удалите каталог из публичного root, отзовите Yandex Cloud ключи
Закрыть /actuator
Включите management.endpoints.web.exposure.include=health,info
Экранирование XSS в /search
Server-side escape + CSP script-src 'self'
Параметризовать SQL в /api/v1/orders
Прерывистые prepared statements; ревью соседних эндпоинтов
Whitelist URL для /api/preview
Allow-list схем + блок IMDS, RFC1918, link-local