CSRF (Cross-Site Request Forgery)

Подделка межсайтовых запросов выглядит так:

Symfony forms

Очень просто щелкнуть по ссылке или кнопке через ClickJacking или «угон кликов» (применяется для того чтобы обойти защиту от подмены HTTP-запросов),  гораздо сложнее заполнить поле ввода или атрибут формы. С помощью представленного в HTML5 “Drag and Drop” API можно очень просто заполнить поля форм, заставив жертву выполнить перетаскивание объекта с помощью мыши. Атакующий сайт может быть замаскирован под  обычную игру, в которой пользователь должен  взять и перетащить с помощью мыши некий нарисованный  объект. В это время атакующий начинает заполнять атрибуты формы и поля ввода.

Например:

<div draggable=ʺtrueʺ ondragstart=ʺevent.dataTransfer.setData (ʹtext/plainʹ, ʹEvil dataʹ)ʺ>

<h3>DRAG ME!!</h3>

</div>

Данный метод был разработан Полом Стоуном (Paul Stone) в 2010 году.

Можно было бы привести пример: BAD GUY отправляет сразу ссылку /fakevotingservice и пользователь переходит по ней, но это уже не межсайтовый запрос, и если в результате плохое действие будет выполнено, то это уже проблема сайта (ведь сайт не должен позволять делать что-то, без подтверждения).

Как защищаются - коротко

  • при первом входе на страницу сайта - сайт создает и отдает пользователю уникальный временный токен (в куке или input-поле формы)
  • пользователь выполняет действие на веб-сайте при этом так же отправляя выданный сайтом токен
  • сайт проверяет, и если токен невалиден - завершает работу с сайтом (отклоняет действие пользователя) с 403 Forbidden.

Как защититься - подробно

Для обеспечение защиты от CSRF согласно OWASP система должна руководствоваться следующими принципами:

Требования к CSRF токену

Для безопасной реализации токен должен быть:

  • Уникальным
  • Действовать единожды
  • Размер, устойчивый к подбору
  • Сгенерирован криптостойким генератором псевдослучайных чисел
  • Ограниченное время жизни

Архитектурное решение

Этапы реализации:

  1. Инициализация токена (получение хэша, время жизни)
  2. Хранение токена (stateful/stateless)
  3. Получение токена на клиенте (HTTP header/html)
  4. Протухание токена (модальное окно с информированием пользователя, действия)

Для хранения и последующей валидации используются два подхода:

Syncronizer Token Pattern - хранение токена на клиенте + сервере (в хранилище cache или db). 

Double Submit Cookie - хранение токена в cookie, с последующей повторной генерацией токена на сервере (чтобы проверить токен клиента на изменение). 

Хранение токена не в Cookie - плохая практика

Является проблемой т.к. иногда необходимо заботиться о пробросе токена в WebView и <iframe />, следовательно следующие варианты более проблематичны:

  • Кастомный header (обычно X-CSRF-Token)
  • <meta> - тег в html страницы
  • hidden <input> внутри формы с POST запросом

От вопроса доставки зависит скорость отклика и сложность подхода работы с токеном для frontend приложений.

При получении через HTTP заголовок нужно вызывать отдельный запрос одним из способов:

  • При начале сессии
  • При загрузке страницы
  • Перед отправкой POST запроса

Выбор этого варианта увеличивает время отклика для пользователя и заставляет frontend разработчика описывать отдельный запрос и куда-то сохранять ключ. Более безопасно из-за использования кастомных заголовков.

При получении внутри html страницы с frontend разработчика пишет меньше. Появляется вопрос с обновлением при протухании.

Решение: доставляем токен до клиента внутри html загруженной страницы в теге <meta />

Защита куки - плохая практика

Не все пользователи используют современные браузеры, следовательно некоторым браузеры игнорируют HSTS аттрибуты у куки с токеном: SameSite = strict, Secure = true, HttpOnly.

Детальное описание проблемы

Представлено следующими ресурсами:

Тестирование узявимостей

Гайд по тестированию CSRF уязвимостей описан в статье.

Инструменты для тестирования:


11.09.2021 07:08

Комментарии

+
Irina |

Copyrights © 2007 - 2026 YaPro.Ru