От угроз к приоритетам: ранжирование риска и выбор мер защиты
Список угроз — это бэклог, а не план. Урок превращает перечисленные угрозы в приоритеты через вероятность x ущерб, объясняет, почему DREAD утратил доверие, и проводит четыре ответа — снизить, устранить, передать, принять — вплоть до остаточного риска.
Проход STRIDE по сервису оформления заказа выдал сорок одну угрозу. DFD сделала видимой каждую границу доверия, деревья атак показали три правдоподобных пути к подделке цены, а abuse cases читались как враждебный набор QA. Сейчас четверг, после обеда, в спринте есть место максимум для двух security-историй, и техлид задаёт единственный важный вопрос: какие две? Сорок одна угроза — это не план, это бэклог без порядка. Вся ценность модели испаряется, если ты не можешь сказать, какая угроза получит инженеро-неделю, а какая подождёт квартал. Ранжирование — это момент, когда моделирование угроз перестаёт быть рисованием диаграмм и начинает окупаться.
К концу урока ты сможешь взять перечисленный список угроз и превратить его в обоснованный, считающийся с бюджетом порядок приоритетов, а затем выбрать правильный ответ для каждой угрозы — и понимать, какую из них ты сознательно примешь.
От списка к порядку: вероятность x ущерб
Результат STRIDE, DFD и деревьев атак — это множество, неупорядоченное по построению. Приоритизация навязывает порядок, и рабочая ось здесь — риск = вероятность x ущерб. Вероятность — это насколько правдоподобна атака для реального противника: нужен ли ему государственный масштаб и zero-day или достаточно скучающего пользователя, правящего URL? Ущерб — это во что тебе обойдётся, когда атака сработает: испорченная маркетинговая страница — это не утёкшая таблица клиентов, и ни то ни другое — не баг с подменой цены, из-за которого каждый заказ уезжает за одну копейку.
Причина, по которой множат, а не складывают, в том, что риск определяется своим самым слабым обоснованием. Катастрофический ущерб при ничтожной вероятности — это ячейка низкого риска; тривиальный ущерб, происходящий постоянно, — тоже низкий. Угрозы, которые должны лишать сна, — те, что высоки по обеим осям, и умножение делает так, что это вытекает из арифметики, а не из спора. Смысл оценки — не ложная точность. Смысл в том, чтобы навязать согласованный, воспроизводимый разговор: чтобы два инженера, оценивая одну угрозу, попали в одну окрестность, и чтобы ранжирование пережило уход того, кто его построил.
Почему DREAD утратил доверие
Годами схемой оценки по умолчанию был DREAD — Damage, Reproducibility, Exploitability, Affected users, Discoverability — каждый фактор по шкале 1–10 и суммируется. Звучит научно, но это не так. Проблема в том, что входы субъективны, а шкала не определена: нет общего рубрикатора, что делает Damage шестёркой, а что семёркой, поэтому два рецензента оценивают одну угрозу по-разному, и тот же рецензент во вторник оценит её иначе. Discoverability (обнаруживаемость) — фактор активно вредный: он поощряет security-through-obscurity, занижая оценку бага лишь потому, что его сейчас трудно найти, — а это ровно наоборот тому, как следует рассуждать о противнике, у которого всё время мира. Microsoft, популяризовавшая DREAD, тихо отказалась от неё внутри по этим причинам. Система оценки, вывод которой нельзя воспроизвести, — это не измерение; это число, которое выглядит как измерение, что хуже, потому что выдаёт догадку за данные.
Вместо этого команды берут небольшую лесенку лучше откалиброванных инструментов, выбираемых по тому, что именно оценивается:
- Качественные матрицы риска для угроз из модели. Сетка 3x3 или 5x5 «вероятность x ущерб», где каждый диапазон определён («высокая вероятность = эксплуатируется неаутентифицированным пользователем с публичным инструментарием»). Определённые диапазоны — в этом весь смысл: они делают оценку воспроизводимой, не притворяясь точностью до второго знака.
- CVSS для известных уязвимостей — CVE в зависимости, находка сканера. CVSS даёт стандартизированный, вендоронезависимый базовый балл 0–10 из определённых метрик (вектор атаки, сложность, требуемые привилегии, область, влияние на CIA), так что «CVE-2023-xxxx — это 9.8» означает одно и то же между командами и инструментами. CVSS — для уязвимостей, на которые можно указать пальцем; он не предназначен для ранжирования проектных угроз, выведенных из DFD.
- OWASP Risk Rating Methodology, когда нужна определённая, но гибкая факторная модель. Она разделяет вероятность (факторы агента угрозы + уязвимости: навык, мотив, лёгкость обнаружения, лёгкость эксплуатации) и ущерб (технические + бизнес-факторы), оценивает каждый фактор по определённой шкале 0–9 и сводит их в матрицу Low/Medium/High — амбиция DREAD, но уже с настоящими рубрикаторами под ней.
Зрелый ход — подбирать инструмент под вход: матрица для смоделированных угроз, CVSS для каталогизированных CVE, OWASP Risk Rating, когда нужна аудируемая разбивка по факторам. Смешивание — оценка проектной угрозы через CVSS или CVE в зависимости через взмах руки — даёт числа, которым никто не доверяет.
| Вероятность ↓ / Ущерб → | Низкий ущерб | Средний ущерб | Высокий ущерб |
|---|---|---|---|
| Высокая вероятность | Средний — починить скоро | Высокий — этот спринт | Критический — бросить всё |
| Средняя вероятность | Низкий — в бэклог | Средний — починить скоро | Высокий — этот спринт |
| Низкая вероятность | Низкий — принять / мониторить | Низкий — в бэклог | Средний — ячейка-ловушка |
Ячейка-ловушка: низкая вероятность, высокий ущерб
Самая дорогая ошибка в ранжировании — не переоценка шума. Это округление низковероятной, высокоущербной угрозы до нуля, потому что «этого никогда не случится». Та правая нижняя ячейка матрицы — место, где живёт хвостовой риск, а хвостовой риск — это то, что хоронит компании. Никогда не проверявшийся путь восстановления из бэкапа, SSRF к cloud-metadata, требующий конкретной мисконфигурации, баг с подменой цены, требующий перехвата запроса, — каждый кажется отдалённым, пока в один день условия не сойдутся, и тогда ущерб тотален. Дисциплина в том, чтобы относиться к этой ячейке как к Среднему, а не нулю: она не обгоняет высоковероятную-высокоущербную позицию в этом спринте, но заслуживает отслеживаемого решения — компенсирующего контроля, монитора, алерта, — а не молчаливого пропуска. Сбой именно в молчаливом пропуске: угроза, которую не записали, никогда не будет пересмотрена, и «мы решили, что риск приемлем» — позиция защитимая только тогда, когда есть запись, что вы это решили.
▸Почему это работает
Почему не ранжировать всё и не идти сверху вниз, пока спринт не заполнится? Потому что инженерный бюджет конечен, а меры стоят дико по-разному. Высокорисковая угроза, закрываемая добавлением одной серверной проверки авторизации, — дешёвая ценность; среднерисковая угроза, требующая трёхнедельной переархитектуры, — дорогая ценность. Зрелая приоритизация взвешивает снижение риска на единицу усилий, а не сырой риск — иногда ты закрываешь четыре средних угрозы дешёвыми фиксами вместо одной высокой, которая стоит месяц, потому что суммарно сожжённого риска больше. Сырой ранг говорит, что важно; ранг с поправкой на стоимость говорит, что делать в четверг.
Четыре ответа: снизить, устранить, передать, принять
Ранжированная угроза не закрыта, пока ты не выбрал ответ, и их ровно четыре. Снизить (mitigate) — добавить контроль, уменьшающий вероятность или ущерб: ограничить частоту запросов на сброс пароля, ограничить запрос владельцем, добавить правило WAF. Это частый случай, и он почти никогда не сводит риск к нулю — то, что остаётся, — это остаточный риск, риск, остающийся после контроля. Устранить (eliminate) — удалить функциональность или актив целиком: если SSRF — это функция «загрузить произвольный URL», и продукт может жить без неё, удаление убирает угрозу вместо того, чтобы её сторожить. Самая дешёвая уязвимость для починки — та, которую ты так и не отгрузил. Передать (transfer) — переложить финансовое последствие на кого-то ещё: кибер-страхование или платёжный процессор, владеющий PCI-областью, чтобы утечка карточных данных была по договору их. Передача двигает стоимость, а не событие — утечка всё равно происходит, клиент всё равно затронут, а твою репутацию не застрахуешь. Принять (accept) — решить, что остаточный риск ниже твоей планки, и сознательно ничего не делать, с зафиксированным согласованием от того, у кого есть полномочия владеть этим решением.
Твоя модель помечает низковероятную, высокоущербную угрозу: функция «загрузить картинку по URL» может быть превращена в SSRF против cloud-metadata эндпоинта. Функцию использует ~2% клиентов, и продакт-команда к ней прохладна. Какой ответ — сильнейший первый ход?
Замыкание цикла: хорошо ли мы поработали?
Модель угроз — это живой артефакт, а не документ, который подшивают. Честный закрывающий вопрос — хорошо ли мы поработали? — состоит из двух половин. Первая, проверить модель: покрыли ли мы систему (каждый элемент DFD, каждую границу доверия), нашли ли значимые угрозы и действительно ли меры отгружены и работают? Мера, помеченная «готово» в модели, но так и не влитая, — это ложь, которую наследует следующий рецензент. Вторая, замкнуть цикл во времени: перезапускать модель при изменении архитектуры, скармливать реальные инциденты и находки пентеста обратно для рекалибровки вероятности (угроза, которую ты оценил как «низковероятную» и которая только что произошла, — теперь данные, а не догадка) и переранжировать по мере движения системы и ландшафта угроз. Модель, к которой возвращаются после каждого инцидента и каждой крупной фичи, остаётся правдивой; написанная однажды и положенная на полку устаревает за квартал.
Расположи сквозной мини-цикл моделирования угроз по порядку — от сырого перечисления до замыкания цикла:
- 1 Перечислить угрозы (STRIDE по DFD, деревья атак, abuse cases)
- 2 Оценить каждую угрозу по вероятности x ущербу с определёнными диапазонами
- 3 Ранжировать в матрицу и применить приоритизацию с поправкой на стоимость в рамках бюджета
- 4 Выбрать ответ на каждую угрозу: снизить / устранить / передать / принять
- 5 Проверить модель и скармливать инциденты обратно, чтобы переранжировать во времени
Почему DREAD вышел из моды для ранжирования смоделированных угроз?
Ты добавляешь кибер-страхование, покрывающее стоимость возможной утечки данных клиентов. Какой это ответ и что он НЕ меняет?
- 01Почему DREAD широко критикуют и что команды используют вместо него для ранжирования угроз?
- 02Проведи одну низковероятную, высокоущербную угрозу через четыре ответа и объясни остаточный риск.
Список угроз — это бэклог, а не план: приоритизация навязывает порядок, и рабочая ось — риск = вероятность x ущерб (умножаем, поэтому угроза набирает высоко, только когда обе оси высоки). Смысл оценки — согласованный, воспроизводимый разговор, а не ложная точность, — и именно поэтому DREAD утратил доверие: его субъективные, неопределённые факторы не воспроизводятся, а фактор Discoverability поощряет обскурность. Подбирай инструмент под вход: качественные матрицы риска для смоделированных угроз, CVSS для известных CVE, OWASP Risk Rating для аудируемой разбивки по факторам. При конечном бюджете приоритизируй по снижению риска на единицу усилий, а не по сырому рангу. Затем каждая угроза выходит через один из четырёх ответов — снизить (оставляя остаточный риск), устранить, передать (стоимость, а не событие) или принять (с зафиксированным согласованием). Определяющий сбой — молчаливое округление низковероятной, высокоущербной угрозы до нуля; эта ячейка хвостового риска хоронит компании, поэтому она заслуживает отслеживаемого решения. Наконец, замкни цикл: проверь, что меры действительно отгружены, и скармливай реальные инциденты обратно, чтобы рекалибровать вероятность и переранжировать по мере движения системы. Теперь, когда тебе вручают сорок одну угрозу и два слота спринта, твой первый вопрос: какие ячейки правые-верхние, какие фиксы дёшевы и какую угрозу мы сознательно решаем принять на записи?
Практика
Начни сверху. Задачи идут от простого к сложному: вспомнить факт, применить к случаю, затем senior-уровень. Открой, попробуй, потом открой ответ.
Что-то непонятно?
Задай вопрос по этому уроку. Вопросы анонимны и попадают напрямую автору — урок станет лучше.
Примени это
Примени этот урок в реальном проекте.