У меня есть приложение Spring boot 2 (остальное API) и я использую библиотеку Springfox Swagger 2, включая библиотеку пользовательского интерфейса. Когда я открываю интерфейс swagger, найденный в http://localhost:8080/swagger-ui.html
, все работает, как и ожидалось, но выполняются два запроса, которые дают результат 404 в логгере:
http://localhost:8080/ (nothing is mapped to the root of my app)
http://localhost:8080/csfr (this mapping also doesn't exist, but I know it stands for 'cross site forged request')
Очевидно, Swagger делает это, потому что он «поддерживает» какую-то проверку токена csfr как объяснил здесь. В течение нескольких месяцев ведется расследование, можно ли настроить эти вызовы 404, поэтому сейчас я обдумываю внедрение конечной точки. Я не могу найти информацию о том, что на самом деле реализовать. Какой заголовок/токен ожидает swagger и что он будет делать с содержащейся в нем информацией? Могу ли я использовать это, чтобы сделать мое приложение (или конечную точку swagger) более безопасным или доступным? Короче: в чем смысл :)?
Вы можете увидеть swagger-ui с API, пожалуйста, поделитесь соответствующим кодом
Я думаю, возможно, вы имели в виду ".. делается запрос на host:port/csrf", а не csfr :)
Позвольте мне ответить на ваши вопросы один за другим.
Why are the request made to
http://localhost:8080/
andhttp://localhost:8080/csrf
?
Это связано с тем, что в Springfox Swagger по умолчанию включена поддержка CSRF. Что это делает, так это то, что всякий раз, когда вы пытаетесь получить доступ к любым конечным точкам swagger в своем приложении, оно проверяет токен CSRF в указанном ниже порядке и прикрепляет его к заголовку запроса.
/
/csrf
Причина, по которой Springfox Swagger прикрепляет токен CSRF, заключается в том, что в случае, если ваше приложение имеет CSRF-защита включена, запросы к конечным точкам swagger завершатся ошибкой, если они не имеют токена CSRF как часть заголовка.
What kind of header/token is swagger expecting, and what will it do with the information in it?
Как я уже говорил ранее, swagger ожидает токен CSRF и прикрепит его к заголовку запроса, когда вы попытаетесь получить доступ к любым конечным точкам swagger.
Can I use this to make my app (or the swagger endpoint) more secure or accessible?
Включение защиты CSRF в вашем приложении защитит ваше приложение от CSRF-атак, а не обязательно только что, предоставив токен CSRF для присоединения к заголовку. Если вы включили защиту CSRF в своем приложении, вы должен предоставляете токен CSRF любым из трех вышеперечисленных способов для доступа к любым конечным точкам swagger в вашем приложении. Вы можете прочитать об использовании включения защиты CSRF здесь.
I'm failing to find information on what to actually implement
Нет смысла реализовывать предоставление токена CSRF для swagger, если вы не включили защиту CSRF в своем приложении, так как это было бы просто избыточным. Но если вы хотите реализовать предоставление токена CSRF для swagger, вы можете сделать это одним из трех способов ниже:
1) Токен CSRF в ваших метатегах, обслуживаемый в /
<html>
<head>
<meta name = "_csrf" content = "${_csrf.token}"/>
<!-- default header name is X-CSRF-TOKEN -->
<meta name = "_csrf_header" content = "${_csrf.headerName}"/>
</head>
Это на случай, если вы используете какой-либо механизм шаблонов, такой как JSP, тимелеаф и т. д.
2) Конечная точка /csrf
Определите конечную точку /csrf
для предоставления токена CSRF.
@RequestMapping("/csrf")
public CsrfToken csrf() {
//logic to return the CSRF token
}
3) Токен CSRF в вашем файле cookie
Искомое имя файла cookie по умолчанию — XSRF-TOKEN
, а возвращаемое имя заголовка по умолчанию — X-XSRF-TOKEN
. Безопасность Spring обеспечивает способ хранения токена CSRF в файле cookie в соответствии с требованиями swagger с приведенной ниже конфигурацией.
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
}
}
Реализация любого из вышеперечисленных 3 предоставит swagger с токеном CSRF для прикрепления к заголовку запроса.
Ссылка на вышеизложенное взята из PR на GitHub, который предоставил поддержку CSRF для Springfox swagger, а также из документации по безопасности Spring, на которую я ссылался ранее.
В настоящее время существует открытый вопрос, касающийся включенной по умолчанию поддержки CSRF здесь и пары открытых PR с исправлением #2639 и #2706.
вы говорите: «Это потому, что Springfox Swagger по умолчанию включил поддержку CSRF». Есть ли способ отключить эту поддержку, чтобы запросы больше не выполнялись, и, следовательно, 404 больше не возникало?
@user1884155 user1884155 Боюсь, в настоящее время нет возможности отключить поддержку CSRF. Я добавил соответствующую проблему и открыл PR для того же в своем ответе.
@MadhuBhat Но если значение CSRF раскрывается через index или /csrf, не открывает ли оно уязвимость для повторной атаки?
@VukDjapic я как-то пропустил ответ на твой вопрос. По сути, в приложении производственного уровня он может находиться за шлюзом API, чтобы он не был доступен извне и, следовательно, не получал никакого внешнего трафика.
В зависимости от 2) конечной точки /csrf
В моем случае я пока отключил WebSecurity, а также получил код ошибки 404 для /csrf. Я исправил это с помощью простого контроллера, как упоминалось выше. Вот мой контроллер:
@Controller
public class CSRFController {
@RequestMapping(value = "/csrf", method = RequestMethod.GET, produces = "application/json;charset=UTF-8")
public ResponseEntity<CsrfToken> getToken(final HttpServletRequest request) {
return ResponseEntity.ok().body(new HttpSessionCsrfTokenRepository().generateToken(request));
}
}
Если вы используете это, вам нужно добавить зависимость maven для веб-безопасности:
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-web</artifactId>
</dependency>
Вы можете поделиться исходным кодом двух API, которые дают 404?