Как лучше всего предотвратить атаки CSRF в приложении GAE?

Итак, что является лучшим способом предотвратить атаку XSRF для приложения GAE? Представьте себе следующее:

  • Любой пользователь может видеть публичный объект пользователя, а в запросе используется идентификатор db.Model, чтобы выяснить, какой объект показывать. Вредоносный пользователь теперь имеет идентификатор.
  • Вредоносный пользователь создает свой собственный объект и проверяет форму удаления. Теперь они знают, как удалить объект с определенным идентификатором.
  • Вредоносный пользователь получает невиновного пользователя для отправки запроса на удаление для этого пользовательского объекта.

Какие шаги я могу добавить для предотвращения # 3? Обратите внимание, что когда я говорю ID, я использую фактическую идентификационную часть ключа. Одна из моих идей заключалась в том, чтобы использовать полное ключевое значение в запросах на удаление, но не позволит злоумышленнику понять это? Насколько я знаю, ключевым является некоторая комбинация типа класса модели, идентификатора приложения и идентификатора экземпляра объекта, поэтому они могли бы, вероятно, извлечь ключ из идентификатора, если захотят.

Любые другие идеи? Джефф написал сообщение об этом и предложил пару методов - значение скрытой формы, которое будет меняться при каждом запросе, и значение cookie, написанное через js к форме. Я не хочу исключать пользователей, не являющихся пользователями javascript, поэтому решение cookie не подходит - для значения скрытой формы мне придется записывать хранилище данных по каждому запросу, который отображает удаляемый объект, а не идеальную ситуацию для масштабируемого приложение!

Любые другие идеи?

Ответ 1

Когда вы создаете страницу, которая позволяет пользователю удалить объект, сгенерируйте случайный токен и включите его в поле скрытой формы. Также установите cookie только для HTTP с этим значением. Когда вы получите запрос на удаление, убедитесь, что случайный токен из формы и значение из файла cookie совпадают.

Ваш случайный токен должен быть не просто случайным числом. Вы должны зашифровать комбинацию случайного числа и идентификатора пользователя, чтобы затруднить для злоумышленников подделку своих жетонов. Вы также должны использовать разные ключи шифрования для значения, хранящегося в форме, и значения, хранящегося в файле cookie, поэтому, если один из токенов действительно течет, хакеру еще трудно подделать другой токен.

Этот подход подтверждает, что запрос удаления происходит из вашей формы, путем наличия маркера безопасности в форме; и не требует записи в хранилище данных.

Этот подход по-прежнему уязвим для атак с межсайтовыми сценариями, когда злоумышленник может получить скрытое значение из формы или отправить форму, поэтому тщательно протестируйте свой сайт для уязвимостей межсайтового скриптинга. Этот подход также уязвим для "clickjacking" .

Ответ 2

Простой: проверьте референт. Это (намеренно) невозможно установить с помощью Javascript, HTML-форм и т.д. Если он пуст (некоторые прокси и браузеры линяют ссылки) или с вашего собственного сайта - или, более конкретно, из ожидаемого источника - разрешите его. В противном случае запретите его и запишите.

Редактировать: Jeff написал следующую статью несколькими способами, чтобы предотвратить атаки CSRF.

Ответ 3

В ответе сервера, отображающем форму, создается магический хеш (на основе клиента ip + дата/время + случайная соль, что угодно). Поместите его в файл cookie и сохраните где-нибудь на сервере. Во время обработки действия отправки проверьте хэш cookie на запись в базе данных.

Если такого хэша нет или он отличается, отклоните его.

После успешной отправки вы можете удалить запись хеша, изменить ее состояние для отправки - что вам подходит.

Этот метод должен защищать вас во многих случаях, но, безусловно, по-прежнему не на 100% пуленепробиваемый.

Сделайте поиск статей по CSRF, возможно, вы найдете хорошие ответы на эту тему Stack Overflow.;)

Не выполняйте проверки реферера или проверки IP-клиента - он слишком подвержен ошибкам (информация о реферере может быть очищена пользовательским агентом, прокси или пользовательскими настройками), и клиентский IP-адрес может измениться между созданием формы и представлением - не наказывать пользователя за динамическое распределение IP-адресов.