Оценка компетенций разработчиков по безопасности
Это цикл об обучении разработчиков безопасности:
- Программа и ресурсы — что требовать
- Оценка и отслеживание (этот раздел) — как проверять
- Руководство по внедрению — как запустить программу
- Культура и коммуникация — как закрепить результат
Улучшить можно только то, что измеряешь. Прежде чем запускать обучение, нужно понять стартовую точку. После обучения — убедиться, что оно сработало. Без регулярной оценки навыки деградируют, а вложения в обучение не дают измеримого результата.
Этот раздел — для руководителя и лидера безопасности. Здесь методы оценки знаний разработчиков, инструменты для построения карт компетенций и способы показать динамику.
Зачем измерять компетенции
Выявить пробелы до обучения. Обучение «обо всём» тратит время на темы, которые команда и так знает. Оценка показывает, что нужно именно вашей команде.
Убедиться, что обучение работает. Сравнение результатов до и после даёт ответ: вложение оправдано или нет.
Отслеживать деградацию. Знания без практики затухают. Регулярная оценка выявляет это раньше, чем проблема даст о себе знать в коде.
Обосновывать инвестиции. Руководству нужны конкретные метрики. Оценка компетенций — основа для отчёта по эффективности программы.
Мотивировать разработчиков. Чёткие уровни компетенций дают понятные цели. Видимый прогресс — стимул к развитию.
Методы оценки
Метод 1: тест на знание теории
Самый простой способ. Вопросы с выбором ответа и короткими ответами по ключевым темам.
Принципы составления теста:
| Принцип | Почему важен |
|---|---|
| Релевантность роли | Не тестируйте backend-разработчиков по iOS-специфике |
| Прогрессия сложности | У1 (базовый) → У2 (средний) → У3 (продвинутый) |
| Практический фокус | Вопросы с кодом лучше вопросов на определения |
| Нет ловушек | Тест на знание, а не на внимательность |
| Объяснение ответов | Разбор ошибок — часть обучения |
Структура теста:
- Длительность: 45–60 минут
- Формат: онлайн, доверительный режим (без строгого контроля)
Разделы:
- Основные концепции безопасности — 10 вопросов (все роли)
- OWASP Top 10 — 10 вопросов (все роли)
- Язык/стек — 10 вопросов (по роли)
- Аутентификация и авторизация — 5 вопросов (backend/fullstack)
- Тестирование безопасности — 5 вопросов (все роли)
Шкала оценки:
- 90%+ → У3 (Эксперт)
- 70–89% → У2 (Практикующий)
- 50–69% → У1 (Осведомлённый)
- Менее 50% → Обязательное обучение
Инструменты для проведения тестов:
- Яндекс Формы (forms.yandex.ru) — бесплатно, интеграция с корпоративными сервисами
- Яндекс Тестирование — для более продвинутого сценария с автоматической проверкой
- Собственная LMS — если в компании уже используется платформа дистанционного обучения
- CTFd (self-hosted) — геймифицированный формат с задачами
Метод 2: упражнение по code review
Более практичный подход — давать разработчикам фрагменты кода с намеренными уязвимостями и просить найти проблемы.
Как проводить:
- Подготовьте 5–10 фрагментов кода с уязвимостями (попросите лидера безопасности)
- Установите время (30–45 минут)
- Попросите разработчика найти и объяснить проблемы
- Оценивайте по количеству найденных уязвимостей и качеству объяснений
Это упражнение значительно ближе к реальной работе, чем теоретический тест. Разработчик, умеющий распознать уязвимость в чужом коде, скорее всего не напишет её сам.
Типичные уязвимости для включения в упражнение (пример набора для Python):
- Жёстко заданный секретный ключ в коде
- SQL-запрос через конкатенацию строк вместо параметризованного
- XSS через вывод пользовательского ввода без экранирования
- Обход пути (path traversal) при работе с файлами
- Инъекция в шаблон (SSTI)
- Небезопасная десериализация
- Инъекция в системную команду
- Включение режима отладки в продуктивной среде
Оценка: за каждую уязвимость — 1 балл, за правильное объяснение эффекта — ещё 1, за предложение корректного исправления — ещё 1. Максимум зависит от числа уязвимостей в упражнении.
Метод 3: CTF (Capture The Flag)
Геймифицированная оценка, при которой разработчики эксплуатируют уязвимости в контролируемой среде и находят «флаги» — секретные строки, подтверждающие выполнение задания.
Почему это работает:
- Вовлекательно и интересно
- Тестирует практические навыки, а не память
- Поощряет обучение через исследование
- Командный формат развивает сотрудничество
Как провести внутренний CTF:
Длительность: 2–4 часа или распределить на несколько дней.
Подготовка: развернуть OWASP Juice Shop (open-source, намеренно уязвимое приложение) или подготовить кастомные задания через CTFd (open-source платформа для CTF). Сформировать команды по 2–3 человека, перемешивая уровни опыта. Подготовить подсказки для застрявших команд.
Задания по уровням:
- Простые (1 звезда): базовый XSS, robots.txt, типичные страницы ошибок
- Средние (2–3 звезды): SQL-инъекция, обход авторизации
- Сложные (4–5 звёзд): небезопасная десериализация, SSRF
После мероприятия: разбор решений по всем заданиям, признание лучших команд, индивидуальные заметки по участию для карты компетенций.
Метод 4: инъекция уязвимостей в код
Наиболее реалистичный метод. лидер безопасности намеренно добавляет уязвимости в тестовую ветку репозитория и просит разработчика провести code review.
Как организовать:
- Создать ветку с намеренными уязвимостями (подготавливает лидер безопасности)
- Попросить разработчика провести review этого PR
- Зафиксировать, какие уязвимости найдены, а какие пропущены
- Дать обратную связь по пропущенным проблемам
Это упражнение максимально близко к реальной рабочей ситуации и выявляет пробелы, которые теоретический тест не покажет.
Создание вопросов для тестов
Использование ИИ для генерации вопросов
Попросите лидера безопасности использовать языковую модель для создания вопросов. Шаблон запроса:
Создай 5 вопросов с выбором ответа по теме [ТЕМА] для разработчиков,
работающих со стеком [ТЕХНОЛОГИИ].
Требования:
— Включи примеры кода, где возможно
— Варьируй сложность (2 × У1, 2 × У2, 1 × У3)
— Сосредоточься на [КОНКРЕТНАЯ ОБЛАСТЬ: SQL-инъекции, аутентификация]
— Укажи правильный ответ и объяснение
— Неправильные варианты должны быть правдоподобными, но явно ошибочными
Примеры вопросов по темам
SQL-инъекции (backend)
Вопрос 1 (У1): Какой из этих вариантов кода уязвим к SQL-инъекции?
- А) Параметризованный запрос через placeholder
- Б) Запрос с подстановкой пользовательского ввода через форматирование строки
- В) Использование ORM (например, Django или SQLAlchemy)
Правильный ответ: Б. Подстановка пользовательских данных напрямую в строку запроса открывает путь к SQL-инъекции. Параметризованные запросы и ORM отделяют данные от структуры запроса.
Вопрос 2 (У2): Разработчик добавил проверку: если значение состоит только из цифр, передаёт его в raw SQL. Защищает ли это от SQL-инъекции?
- А) Нет — проверка цифр устраняет инъекцию, но паттерн остаётся опасным
- Б) Да — числа не могут содержать SQL-конструкции
- В) Зависит от базы данных
Правильный ответ: А (с нюансом). Проверка исключает инъекцию в данном конкретном случае, но паттерн — raw() или аналог с форматированием строк — хрупкий и легко нарушается при рефакторинге. Всегда лучше использовать параметризованные запросы.
Вопрос 3 (У3): В коде используются параметризованные запросы для значений. Защищает ли это от SQL-инъекции при подстановке имени таблицы из пользовательского запроса?
- А) Да — параметризация защищает все вводимые данные
- Б) Нет — имя таблицы является идентификатором, а не значением, и не защищается параметризацией
- В) Зависит от драйвера базы данных
Правильный ответ: Б. Параметризация работает для значений, но не для идентификаторов (имён таблиц, столбцов). При необходимости динамических имён таблиц — используйте белый список допустимых значений.
XSS (frontend/backend)
Вопрос 1 (У1): Что такое XSS?
- А) Cross-Site Scripting — инъекция вредоносного скрипта в страницу, которую видят другие пользователи
- Б) Атака через межсерверный запрос
- В) Перехват трафика между клиентом и сервером
Правильный ответ: А.
Вопрос 2 (У2): В React при использовании JSX {userInput} — уязвимо ли это к XSS?
- А) Нет — React автоматически экранирует содержимое JSX
- Б) Да — JavaScript в строке исполнится
- В) Зависит от версии React
Правильный ответ: А. React экранирует содержимое по умолчанию в JSX-выражениях. Исключение — явное использование dangerouslySetInnerHTML, которое отключает эту защиту.
Аутентификация (все роли)
Вопрос 1 (У1): Где безопаснее всего хранить JWT-токен в браузере?
- А) localStorage
- Б) sessionStorage
- В) HttpOnly cookie
- Г) В URL-параметре
Правильный ответ: В. HttpOnly cookie недоступны через JavaScript, что защищает токен от кражи при XSS-атаке. localStorage и sessionStorage доступны скриптам. URL-параметры логируются и кешируются.
Вопрос 2 (У2): Почему использование MD5 для хранения паролей — ошибка?
- А) MD5 слишком медленный алгоритм
- Б) MD5 имеет известные коллизии и слишком быстр для перебора; соль не используется автоматически
- В) MD5 устарел, но безопасен при добавлении соли
- Г) Нет ничего принципиально неправильного
Правильный ответ: Б. MD5 очень быстр — это делает его непригодным для паролей (перебор возможен с огромной скоростью). Для паролей нужны специально замедленные функции: bcrypt, Argon2, scrypt.
Авторизация (backend)
Вопрос 1 (У1): Что такое IDOR?
- А) Insecure Direct Object Reference — возможность получить доступ к чужим данным, угадав или изменив идентификатор в запросе
- Б) Internal Data Object Routing — внутренний паттерн API
- В) Тип атаки на инфраструктуру
Правильный ответ: А.
Вопрос 2 (У2): Эндпоинт возвращает профиль пользователя по его ID. Что в нём пропущено?
GET /api/users/{user_id}/profile
- А) Валидация формата user_id
- Б) Проверка авторизации — убедиться, что запрашивающий вправе видеть эти данные
- В) Rate limiting
- Г) Требование HTTPS
Правильный ответ: Б. Любой аутентифицированный пользователь может подобрать чужой user_id и получить доступ к чужим данным. Нужна явная проверка: «текущий пользователь — владелец этих данных или администратор».
Построение карт компетенций
Карты компетенций помогают руководителю видеть состояние команды целиком и принимать решения об обучении.
Индивидуальная карта
Разработчик: Алексей Сидоров | Роль: Senior Developer | Уровень: У2
| Область | Результат | Статус |
|---|---|---|
| Безопасное кодирование | 80% | ✓ |
| Аутентификация | 90% | ✓ |
| Валидация ввода | 100% | ✓ |
| Криптография | 40% | ⚠ Пробел |
| Моделирование угроз | 50% | — |
| Тестирование безопасности | 70% | ✓ |
| Управление зависимостями | 80% | ✓ |
| Реагирование на инциденты | 40% | ⚠ Пробел |
Рекомендации: курс по криптографии, участие в учебных учениях по инцидентам.
Тепловая карта команды
| Сотрудник | Безопасный код | Аутентификация | Ввод данных | Криптография | Угрозы | Тестирование | Зависимости |
|---|---|---|---|---|---|---|---|
| Алексей С. | ✓✓ | ✓✓ | ✓✓ | ✗ | ✓ | ✓✓ | ✓✓ |
| Мария К. | ✓✓ | ✓✓ | ✓✓ | ✓✓ | ✓✓ | ✓ | ✓ |
| Дмитрий Л. | ✓ | ✓ | ✓✓ | ✗ | ✗ | ✓ | ✓ |
| Ольга П. | ✓✓ | ✓✓ | ✓✓ | ✓✓ | ✓✓ | ✓✓ | ✓✓ |
| Игорь В. | ✓ | ✓ | ✓ | ✗ | ✗ | ✗ | ✓ |
| Среднее | 80% | 75% | 90% | 45% ПРОБЕЛ | 40% ПРОБЕЛ | 60% | 70% |
✓✓ = Сильный (70%+) · ✓ = Развивается (40–70%) · ✗ = Пробел (менее 40%)
Такая карта сразу показывает: приоритет для ближайшего обучения — криптография и моделирование угроз.
Отслеживание динамики
Оценка Q1:
| Область | Результат | Цель | Статус |
|---|---|---|---|
| Безопасное кодирование | 80% | 80% | Достигнуто |
| Аутентификация | 75% | 80% | В процессе |
| Криптография | 45% | 60% | Пробел |
| Моделирование угроз | 40% | 60% | Пробел |
| Тестирование безопасности | 60% | 70% | В процессе |
Запланированные действия:
- Модуль по аутентификации — завершён
- Воркшоп по моделированию угроз — запланирован на следующий квартал
- Курс по криптографии для команды — запланирован
Цели Q2: криптография — выше 60% · моделирование угроз — выше 60% · все разработчики проходят промежуточную оценку
Инструменты для ведения карт
| Подход | Подходит для | Усилия |
|---|---|---|
| Таблица (Excel/Яндекс Таблицы) | Команды до 10 человек | Низкие |
| Вики/Confluence | Компании с развитой документацией | Низкие |
| LMS-платформа | Компании с автоматизированным обучением | Средние |
| Собственная панель метрик | Специфические требования | Высокие |
Шаблон таблицы для отслеживания:
| Разработчик | Роль | OWASP Top 10 | Аутентификация | Криптография | Тестирование | Моделирование угроз | Дата оценки |
|---|---|---|---|---|---|---|---|
| Алексей С. | Senior | 4/5 | 5/5 | 2/5 | 3/5 | 3/5 | 15.01.2025 |
| Мария К. | Middle | 3/5 | 3/5 | 4/5 | 2/5 | 4/5 | 15.01.2025 |
Анализ «до и после» — шаблон отчёта
Отчёт о влиянии обучения: Q2
Показатели тестов до и после обучения:
| Область | До обучения | После обучения | Прирост |
|---|---|---|---|
| Предотвращение SQL-инъекций | 65% | 88% | +23% |
| Аутентификация | 70% | 85% | +15% |
| Валидация ввода | 60% | 82% | +22% |
Реальное влияние за тот же период:
| Метрика | Q1 | Q2 | Изменение |
|---|---|---|---|
| Находки SAST | 145 | 89 | −39% |
| Уязвимости в продуктиве | 12 | 5 | −58% |
| Среднее время исправления (дни) | 8 | 4 | −50% |
Обучение демонстрирует измеримый возврат инвестиций. Рекомендуется продолжить квартальные оценки и сосредоточить следующий цикл обучения на текущих пробелах.
Метрики для руководителя
| Метрика | Способ измерить | Что считать результатом |
|---|---|---|
| Средний балл оценки | Результаты тестов | Рост каждый квартал |
| Плотность уязвимостей | Находки SAST на 1000 строк кода | Снижение со временем |
| Время на исправление | Данные из трекера задач | Снижение для задач по безопасности |
| Уязвимости в продуктиве | Данные из трекера инцидентов | Меньше с каждым релизом |
| Результативность code review | Комментарии по безопасности в PR | Рост числа выявленных проблем до попадания в продукт |
| Завершение обучения | LMS или таблица | 100% по обязательным модулям |
Типичные ошибки при оценке
- Тест только на теорию. Включайте практические упражнения — только так можно проверить реальные навыки.
- Единый тест для всех. Настраивайте под роль и стек технологий.
- Однократная оценка. Навыки деградируют без практики. Регулярность обязательна.
- Наказание за низкий балл. Это подавляет честность. Низкий результат — информация для руководителя, а не повод для взыскания.
- Оценка без действия. Карта компетенций, которую никто не использует для планирования обучения, — потраченное время.
- Слишком долго. 45–60 минут — максимум для теста. Больше — усталость и снижение качества ответов.
Контрольные точки для руководителя:
- Базовая оценка проведена до начала обучения
- Результаты зафиксированы в карте компетенций (таблица или LMS)
- Определены приоритетные пробелы для первого цикла обучения
- Намечен срок повторной оценки (через 8–12 недель после обучения)
- Метрики SAST и уязвимостей в продуктиве отслеживаются для подтверждения ROI
- Индивидуальные рекомендации по обучению сформированы для каждого разработчика
Вопросы для контроля (задайте лидеру безопасности):
- Все ли разработчики прошли базовую оценку?
- Составлена ли карта пробелов на уровне команды?
- Есть ли индивидуальные учебные планы?
- Когда запланирована следующая оценка?
Что дальше
Следующий раздел — руководство по внедрению: пошаговый план запуска программы, работа с сопротивлением и построение устойчивой культуры безопасной разработки.