Предположим, у меня есть REST API, который также используется для установки / сброса паролей. Давайте также предположим, что это работает через соединения HTTPS. Есть ли веская причина не вводить этот пароль в путь вызова, скажем, я закодирую его в BASE64?
Примером может быть сброс пароля таким образом:
http://www.example.com/user/joe/resetpassword/OLDPASSWD/NEWPASSWD
Я понимаю, что BASE64 - это не шифрование, но я хочу только защитить пароль для серфинга в этом случае.
resetpassword/OLDPASSWD/NEWPASSWD
это не ресурс. Это вызов процесса. Вам не нужно вставлять все в URL.Ответы:
Хороший сервер регистрирует все отправленные ему запросы, включая URL-адреса (часто без переменной части после '?'), IP-адрес источника, время выполнения ... Вы действительно хотите, чтобы этот журнал (потенциально читаемый широкой группой администраторов) содержал критически безопасная информация как пароли? Base64 не стопор против них.
источник
То, что вы предлагаете, не является ни безопасным, ни RESTful.
@Netch уже упоминал о проблеме с журналами, но есть и другая проблема, которая заключается в том, что вы показываете пароли, отправляемые по HTTP, что упрощает захват паролей с помощью любого вида перехватчика проводов или атаки «человек посередине».
Когда вы выполняете запрос GET с использованием REST, различные элементы в URL представляют более мелкозернистые элементы. Ваш URL читается так, как будто вы возвращаете NEWPASSWD часть OLDPASSWD, которая является частью пароля для сброса. Это не имеет никакого семантического смысла. GET не должны использоваться для сохранения данных.
Вы должны делать что-то вроде этого:
POST, потому что вы пишете данные, и https, потому что вы не хотите, чтобы их прослушивали.
(Это действительно низкий уровень безопасности. Абсолютный минимум, который вы должны сделать.)
источник
/user/joe/password
это немного лучше, но не оптимально.PUT
, потому чтоPUT
идемпотент. Но когда пароль был изменен сsecret
наsupersecret
успешно, то тот же запрос не будет выполнен во второй раз, такPOST
что здесь правильно. Конечно, как сказал @whirlwin, этот ресурс не очень хорошо назван.Предлагаемая схема имеет проблемы в нескольких областях.
Безопасность
URL-пути часто регистрируются; установка нехэшированных паролей в пути - плохая практика.
HTTP
Информация об аутентификации / авторизации должна появиться в заголовке авторизации. Или, возможно, для браузера - заголовок Cookie.
ОСТАЛЬНЫЕ
Глаголы, такие как
resetpassword
в вашем URL, как правило, являются явным признаком не-репрезентативной парадигмы передачи состояния. URL должен представлять ресурс. Что это значит, чтобы получитьresetpassword
? Или УДАЛИТЬ?API
Эта схема требует всегда знать предыдущий пароль. Вы, вероятно, захотите разрешить больше дел; например, пароль утерян.
Вы можете использовать обычную или дайджест-аутентификацию , которая является хорошо понятной схемой.
Он не помещает сверхсекретную информацию в путь и следует соглашениям HTTP и REST.
Если вам нужно было разрешить какой-либо другой режим авторизации (например, какой-нибудь токен, отправленный через проверенный канал для сброса пароля), вы можете просто использовать другой заголовок авторизации без необходимости что-либо менять.
источник
Помимо безопасности, проблема в том, что это не очень RESTful подход.
OLDPASSWD
иNEWPASSWD
ничего не стоит в иерархии ресурсов, и, что еще хуже, операция не идемпотентна.Таким образом, вы можете использовать только в
POST
качестве своего глагола, и вы не должны включать два пароля в путь к ресурсу.источник
PUT
дисквалифицируется как глагол. С ним можно было бы перенастроить,PUT
но в его нынешнем виде это не так.Проблема состоит в том, чтобы избежать простых текстовых паролей в ваших запросах. Существует два варианта выполнения остальных требований веб-сервиса.
1. Хеширование на стороне клиента
2. Шифрование
Примечание: HTTPS требуется для обоих вариантов!
источник
Каковы особенности операции сброса пароля?
Пункт 1 здесь означает, что вы не можете использовать GET, вы должны либо POST-то, представляющее операцию смены пароля, в URI, представляющий ресурс, который обрабатывает изменения пароля, либо PUT, представляющее новый пароль, в URI, представляющий пароль или представляющий что-то пользователь) которого пароль является функцией.
Как правило, мы бы POST, не в последнюю очередь потому, что это может быть неудобно ПОСТАВЛЯТЬ что-то, что мы не можем позже ПОЛУЧИТЬ и, конечно, мы не можем получить пароль.
Таким образом, пункт 2 будет представлять данные, представляющие новый пароль, в том виде, в котором он размещен.
Пункт 3 означает, что нам нужно авторизовать запрос. Это означает, что, если пользователь является текущим пользователем, нам потребуется подтверждение текущего пароля (хотя не обязательно получать текущий пароль, например, при вызове на основе хеша). был использован, чтобы доказать знание этого, не отправляя это)
Следовательно, URI должен быть похож на
<http://example.net/changeCurrentUserPassword>
или<http://example.net/users/joe/changePassword>
.Мы можем решить, что хотим получить текущий пароль в данных POST, а также в общем используемом механизме авторизации.
источник