За последние 24 часа нас посетили 30706 программистов и 1479 роботов. Сейчас ищут 858 программистов ...

Защита от CSRF

Тема в разделе "PHP для новичков", создана пользователем machetero, 31 янв 2016.

  1. machetero

    machetero Активный пользователь

    С нами с:
    25 окт 2014
    Сообщения:
    499
    Симпатии:
    21
    Я забыл как защищаться от CSRF. Помню только, что в запросе, скрытым полем отправляется токен. А что дальше забыл. Напомните кто знает.
     
  2. denis01

    denis01 Суперстар
    Команда форума Модератор

    С нами с:
    9 дек 2014
    Сообщения:
    12.227
    Симпатии:
    1.714
    Адрес:
    Молдова, г.Кишинёв
    искал готовые решения?
     
  3. [vs]

    [vs] Суперстар
    Команда форума Модератор

    С нами с:
    27 сен 2007
    Сообщения:
    10.559
    Симпатии:
    632
    Любое действие должно выполняться с одноразовым токеном
     
  4. machetero

    machetero Активный пользователь

    С нами с:
    25 окт 2014
    Сообщения:
    499
    Симпатии:
    21
    я чутка погуглил. нашёл "защита от csrf в joomla". там полностью механизм не описывается.
     
  5. Fell-x27

    Fell-x27 Суперстар
    Команда форума Модератор

    С нами с:
    25 июл 2013
    Сообщения:
    12.156
    Симпатии:
    1.771
    Адрес:
    :сердА
    1) генеришь токен.
    2) пишешь в сессию.
    3) вставляешь его в скрытое поле в форму.
    4) когда приходит форма, проверяешь, есть ли в ней токен, есть ли в сессии токен, совпадают ли они. Если нет, игноришь - пришедшие данные от имени этого пользователя были посланы откуда угодно, но не со страницы твоего сайта, сгенеренной твоим сервером конкретно для этого человека.
     
  6. machetero

    machetero Активный пользователь

    С нами с:
    25 окт 2014
    Сообщения:
    499
    Симпатии:
    21
    Спасибо Fell-x27
     
  7. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    не забудьте удалять из сессии, а не то она распухнет. Допустим 10 токенов держать.
     
  8. artoodetoo

    artoodetoo Суперстар
    Команда форума Модератор

    С нами с:
    11 июн 2010
    Сообщения:
    11.128
    Симпатии:
    1.248
    Адрес:
    там-сям
    токен может генериться функцией от адреса и чего-то уникального для пользователя. можно еще время устаревания добавить.
    тогда не понадобится его хранить.

    Добавлено спустя 6 минут:
    другой вариант: генерить случайный токен, а в куку засовывать "подпись", зависящую от токена, адреса и секретного ключа. при проверке вычислять подпись заново и сравнивать с той, что в куке. на сервере кроме ключа ничего не хранится.
     
  9. runcore

    runcore Старожил

    С нами с:
    12 окт 2012
    Сообщения:
    3.625
    Симпатии:
    158
    Fell-x27
    +1
    самое простое и рабочее решение
     
  10. artoodetoo

    artoodetoo Суперстар
    Команда форума Модератор

    С нами с:
    11 июн 2010
    Сообщения:
    11.128
    Симпатии:
    1.248
    Адрес:
    там-сям
    в wordpress используются т.н. nonce — теоретически эти токены должны быть одноразовыми. но использование ajax вносит свой геморой. приходится делать одноразовое многоразовым. вордпресовцы пошли на компромис, у них токен устаревает за несколько часов. таким образом они сокращают количество того, что необходимо хранить.
     
  11. machetero

    machetero Активный пользователь

    С нами с:
    25 окт 2014
    Сообщения:
    499
    Симпатии:
    21
    Спрошу здесь. Генерить токен и писать в сессию/куку явно не в шаблоне надо, а выносить в хэлперы. Не новое для меня слово, тем не менее я не знаю куда это надо выносить. Буду благодарен тому кто объяснить что такое хэлперы.
     
  12. [vs]

    [vs] Суперстар
    Команда форума Модератор

    С нами с:
    27 сен 2007
    Сообщения:
    10.559
    Симпатии:
    632
  13. Fell-x27

    Fell-x27 Суперстар
    Команда форума Модератор

    С нами с:
    25 июл 2013
    Сообщения:
    12.156
    Симпатии:
    1.771
    Адрес:
    :сердА
    ХЗ. У меня вот просто есть функция API::get_token(); Я ее втыкаю в код, генерирующий форму в нужное место и доволен. Она сама скрытое поле сгенерит(опционально), и токен, и сама в сессию запишет данные. Потом, в критических местах вызывается функция API::check_token(), которая тоже сама все делает и возвращает true или false, в зависимости от того, сочла она запрос подлинным или поддельным.

    Кто тебе мешает сделать нечто подобное у себя? В итоге в шаблон выходят только вызовы.
     
  14. igordata

    igordata Суперстар
    Команда форума Модератор

    С нами с:
    18 мар 2010
    Сообщения:
    32.408
    Симпатии:
    1.768
    как она работает?
     
  15. denis01

    denis01 Суперстар
    Команда форума Модератор

    С нами с:
    9 дек 2014
    Сообщения:
    12.227
    Симпатии:
    1.714
    Адрес:
    Молдова, г.Кишинёв
    Это предположим только в роутере происходит?
     
  16. [vs]

    [vs] Суперстар
    Команда форума Модератор

    С нами с:
    27 сен 2007
    Сообщения:
    10.559
    Симпатии:
    632
    если только в одном месте, то будет требоваться токен для загрузки любой страницы, в то время как требуется только защита записи (изменения).
     
  17. artoodetoo

    artoodetoo Суперстар
    Команда форума Модератор

    С нами с:
    11 июн 2010
    Сообщения:
    11.128
    Симпатии:
    1.248
    Адрес:
    там-сям
    конечно всё подряд не стоит, но не только изменение данных. user logout, например, может и должен защищаться от csrf. иначе кто-то может подсунуть тебе картинку с адресом выхода и давай досвидания ))) здесь токен может быть get-параметром.

    Добавлено спустя 4 минуты 32 секунды:
    посмотрите здесь на форуме: ссылки "Выход", "Подписаться на тему", "В закладки" прикрыты некими хешами. это оно и есть!
     
  18. Fell-x27

    Fell-x27 Суперстар
    Команда форума Модератор

    С нами с:
    25 июл 2013
    Сообщения:
    12.156
    Симпатии:
    1.771
    Адрес:
    :сердА
    проверяет, есть ли в запросе токен с таким-то случайно сгенеренным именем, проверяет, есть ли в сессии переменная с таким именем, и совпадают ли их значения. Если да, при том, что ранее совпали фингерпринты все, то ок, запрос честный, возвращаем true.
    Это там происходит, где ты обрабатываешь запрос конкретный. Можно и на роутере, но тогда зачастую в холостую будут идти проверки даже тогда, когда они не нужны. А с
    Код (PHP):
    1. if (API::check_token()){
    2. //code
    3. } 
    можно быть уверенным, что там, где это важно, код обернут в защиту. Но это чисто мое имхо. Автор и любой другой может делать так, как сам считает нужным для себя и как считает возможным исходя из своей архитектуры.

    Добавлено спустя 1 минуту 4 секунды:
    Мое любимое развлечение, когда кто-то на форуме просит затестить его проект, натыканный кнопками в виде стилизованных УРЛов с чистыми гетами :)