Cross-Site Request Подделка, ака CSRF или один-клик атаки , является диффузная проблема проблема безопасности , где самовольных команды посылаются из браузера пользователя на веб — сайт или веб — приложения. CSRF отличается от межсайтового скриптинга в том смысле, что ему не нужно внедрять код в доверенные страницы, но он может работать с ненадежными из-за открытой веб-архитектуры.
Быстрый пример
Я просматривал систему отслеживания ошибок в популярном веб-сервисе, чтобы предложить улучшение, где я увидел, что единственный критический билет был связан с уязвимостями CSRF.
Веб-сайт использует ссылки для удаления данных текущего пользователя, например / delete_my_items. Когда пользователь переходит по ссылке, представленной на странице его учетной записи, его cookie-файл сеанса устанавливает его личность, и его данные удаляются.
Чтобы выполнить атаку, нам нужно только заставить пользователя загрузить этот URL. Простая ссылка, вероятно, не будет работать, но мы можем легко достичь той же цели с помощью изображения:
<img src="http://application.com/delete_my_items" />
Мы просто должны предоставить пользователю ссылку на страницу, содержащую это изображение, или отправить его ему по электронной почте в формате HTML.
Как это работает
В отличие от XMLHttpRequest, изображения и другие ресурсы могут быть загружены с любого имени хоста, и даже если тег изображения размещен на другом веб-сайте, это не будет иметь значения.
Поскольку запрос выполняется браузером пользователя, он будет передавать куки-файл сеанса, как это было бы для любой страницы application.com.
Смысл всех CSRF-атак заключается в том, чтобы обмануть браузер в отправке нежелательного HTTP-запроса , чтобы не было необходимости похищать личность пользователя. Возможно, поэтому наши банки выходят из системы после 2 минут бездействия или требуют одноразовых токенов для авторизации денежных переводов.
Предположения CSRF
Чтобы атака CSRF была возможной, необходимо проверить некоторые предположения:
- атакованный веб-сайт не проверяет HTTP-заголовок Referer , поэтому он принимает запросы, исходящие с внешних страниц.
- Веб-сайт принимает изменение данных через отправку форм или URL-адреса, которые имеют побочные эффекты, которые может использовать злоумышленник.
- Злоумышленник может определить все значения для входных данных запроса . В простейшем случае аутентификация выполняется исключительно с помощью cookie-файла сеанса, поэтому злоумышленнику просто нужно заполнить нечувствительные поля.
- Пользователь должен загрузить вредоносную страницу, содержащую код злоумышленника. Судя по количеству лайков в Facebook, нажатие на все, что движется, является довольно распространенным поведением.
Контрмеры
Каждая контрмера может поднять планку и сделать CSRF более трудным для выполнения.
Прежде всего, не используйте GET для операций с побочными эффектами. CSRF полагается на запросы, которые вызывают побочные эффекты, такие как удаление или изменение данных, а использование GET только упрощает выполнение этих запросов.
Однако POST недостаточно : злоумышленник может отправить форму с использованием JavaScript после загрузки страницы и создать фантомный запрос POST.
Существуют различные альтернативы, чтобы избежать CSRF для запросов POST.
1. Заголовок рефери
Вы можете проверить HTTP-заголовок Referer и убедиться, что запрос возник со внутренней страницы вашего веб-приложения. Referred может быть очень легко подделан вредоносным пользовательским агентом, но обычный пользователь использует браузер общего назначения, а не злонамеренный пользовательский агент.
Этот подход предполагает, что никто не может внедрить HTML / JavaScript на ваших страницах для создания запроса; в противном случае реферер будет правильным.
Проблема в том, что удаление реферера действительно распространено : до 11% HTTP-запросов его не содержат ; например, корпоративные прокси или старые пользовательские агенты обычно удаляют его. Таким образом, строгая проверка реферера блокирует более десятой части вашей пользовательской базы от выполнения запросов POST.
2. Токен сеанса
Решения, основанные на одноразовом токене для форм , гораздо более популярны: токен сохраняется в сеансе пользователя и передается в каждой официальной форме.
Zend_Form_Element_Hash является примером этой техники: скрытое поле добавляется в формы и заполняется токеном . Чтобы сделать успешный запрос, злоумышленник должен знать токен пользователя, но не может получить к нему доступ, поскольку внешняя страница не может загрузить форму в другом домене с помощью JavaScript.
В 2011 году это стандартный подход.
3. Двойной файл cookie
Вариант предыдущего метода состоит в сопоставлении токена, отправленного с формой и файлом cookie , а не со значением сеанса.
Из-за той же политики происхождения код JavaScript, загруженный с другого хоста, не может прочитать набор cookie на официальном имени хоста. Таким образом, хотя официальные формы будут отправлять значение вместе с cookie, злоумышленнику придется угадывать значение cookie, чтобы включить его в запрос (невозможная задача, если значение достаточно длинное).
Преимущество этого варианта заключается в том, что для хранения токенов форм используется меньше серверных ресурсов, и вы не будете подвергаться DDOS-атаке, основанной на загрузке нескольких форм.
Вывод
Предложение самой известной статьи о CSRF заключается в добавлении заголовка Origin к HTTP, в качестве альтернативы Referer. Этот заголовок будет отправлен только для запросов POST и будет содержать только имя хоста вместо полного URL, чтобы обеспечить конфиденциальность.
Методы, описанные в этой статье, жизнеспособны и заслуживают внимания для любого приложения, содержащего полезные данные; они затрудняют тестирование с некоторыми инструментами, которые создают HTTP-запросы, но они не являются проблемой для инструментов на основе браузера, таких как Selenium.