Подтвердить что ты не робот

Обеспечивает ли безопасность приложение REST с аутентификацией JWT и Basic?

У меня есть приложение Spring REST, которое сначала было защищено базовой аутентификацией.

Затем я добавил контроллер входа, который создает JWT JSON Web Token, который используется в последующих запросах.

Можно ли переместить следующий код из контроллера входа в систему и в фильтр безопасности? Тогда мне больше не понадобится контроллер входа.

tokenAuthenticationService.addTokenToResponseHeader(responseHeaders, credentialsResource.getEmail());

Или я могу удалить базовую аутентификацию?

Это хорошая конструкция для смешивания базовой аутентификации с JWT?

Хотя все работает отлично, я немного в темноте здесь, чтобы лучше всего создать эту безопасность.

4b9b3361

Ответ 1

Предполагая, что 100% TLS для всей связи - как во время, так и во всех случаях после входа в систему - аутентификация с использованием имени пользователя/пароля с помощью базовой аутентификации и получения JWT в обмене является допустимым вариантом использования. Это почти точно, как работает один из потоков OAuth 2 ( "предоставление пароля" ).

Идея заключается в том, что конечный пользователь аутентифицируется через одну конечную точку, например. /login/token используя любой механизм, который вы хотите, и ответ должен содержать JWT, который должен быть отправлен обратно на все последующие запросы. JWT должен быть JWS (т.е. Криптографически подписанным JWT) с правильным полем истечения JWT (exp): это гарантирует, что клиент не сможет манипулировать JWT или сделать его живым дольше, чем нужно.

Вам не нужен заголовок X-Auth-Token: для этого точного варианта использования была создана схема HTTP Authentication Bearer: в основном любой бит информации, которая отслеживает имя схемы Bearer, представляет собой "несущую" информацию, которая должна быть подтвержденным. Вы просто установите заголовок Authorization:

Authorization: Bearer <JWT value here>

Однако, если ваш клиент REST "ненадежен" (например, браузер с поддержкой JavaScript), я бы даже не сделал этого: любое значение в ответе HTTP, доступное через JavaScript, - в основном любое значение заголовка или значение тела ответа - может быть обнюхано и перехвачено с помощью атак MITM XSS.

Лучше хранить значение JWT в cookie с защищенным доступом, только для http файлов cookie (config cookie: setSecure (true), setHttpOnly (true)). Это гарантирует, что браузер будет:

  • только когда-либо передают файл cookie через соединение TLS и
  • никогда не делает значение cookie доступным для кода JavaScript.

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

Самый простой способ сделать это - установить только защищенный (но НЕ только http) cookie со случайным значением, например. UUID.

Затем, при каждом запросе на ваш сервер убедитесь, что ваш собственный код JavaScript считывает значение cookie и устанавливает его в пользовательский заголовок, например. X-CSRF-токен и проверить это значение для каждого запроса на сервере. Клиенты внешних доменов не могут устанавливать пользовательские заголовки для запросов в ваш домен, если только внешний клиент не получит авторизацию через запрос параметров HTTP, поэтому любая попытка атаки CSRF (например, в IFrame, что бы там ни было) не будет выполнена для них.

Это лучшая в своем роде защита, доступная для ненадежных клиентов JavaScript в Интернете сегодня, о которой мы знаем. Stormpath написал статью о этих методах, если вам интересно.

Наконец, Stormpath Java Servlet Plugin уже делает все это для вас (и гораздо более классный материал, включая дополнительные автоматические проверки безопасности) когда-либо писать, или, что еще хуже, поддерживать его самостоятельно. Просмотрите раздел HTTP Request Authentication и пример Form/Ajax, чтобы узнать, как его использовать. НТН!