Фильтр сервлета: как получить все заголовки из servletRequest?
Вот как выглядит мой WebFilter
@WebFilter("/rest/*")
public class AuthTokenValidatorFilter implements Filter {
@Override
public void init(final FilterConfig filterConfig) throws ServletException {
}
@Override
public void doFilter(final ServletRequest servletRequest, final ServletResponse servletResponse, final FilterChain filterChain) throws IOException, ServletException {
final Enumeration<String> attributeNames = servletRequest.getAttributeNames();
while (attributeNames.hasMoreElements()) {
System.out.println("{attribute} " + servletRequest.getParameter(attributeNames.nextElement()));
}
final Enumeration<String> parameterNames = servletRequest.getParameterNames();
while (parameterNames.hasMoreElements()) {
System.out.println("{parameter} " + servletRequest.getParameter(parameterNames.nextElement()));
}
filterChain.doFilter(servletRequest, servletResponse);
}
@Override
public void destroy() {
}
}
Я попытался узнать в Интернете, как получить значения для HTTP headers
, исходящие из запроса.
Я ничего не нашел, поэтому я попытался перечислить servletRequest.getAttributeNames()
и servletRequest.getParameterNames()
, ничего не зная, но у меня нет заголовков.
Вопрос
Как я могу получить все заголовки, исходящие от запроса?
Ответы
Ответ 1
Введите запрос ServletRequest
в HttpServletRequest
(только если ServletRequest request
является instanceof
HttpServletRequest
).
Затем вы можете использовать HttpServletRequest.getHeader()
и HttpServletRequest.getHeaderNames()
.
Что-то вроде этого:
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
HttpServletRequest httpRequest = (HttpServletRequest) request;
Enumeration<String> headerNames = httpRequest.getHeaderNames();
if (headerNames != null) {
while (headerNames.hasMoreElements()) {
System.out.println("Header: " + httpRequest.getHeader(headerNames.nextElement()));
}
}
//doFilter
chain.doFilter(httpRequest, response);
}
Ответ 2
В Java 8 вы можете использовать поток для сбора заголовков запросов:
HttpServletRequest httpRequest = (HttpServletRequest) request;
Map<String, String> headers = Collections
.list(httpRequest.getHeaderNames())
.stream()
.collect(Collectors.toMap(h -> h, httpRequest::getHeader));
ОБНОВЛЕНО
@Matthias напомнил мне о возможности иметь несколько значений для одного заголовка:
Map<String, List<String>>
Map<String, List<String>> headersMap = Collections
.list(httpRequest.getHeaderNames())
.stream()
.collect(Collectors.toMap(
Function.identity(),
h -> Collections.list(httpRequest.getHeaders(h))
));
org.springframework.http.HttpHeaders
HttpHeaders httpHeaders = Collections
.list(httpRequest.getHeaderNames())
.stream()
.collect(Collectors.toMap(
Function.identity(),
h -> Collections.list(r.getHeaders(h)),
(oldValue, newValue) -> newValue,
HttpHeaders::new
));
https://gist.github.com/Cepr0/fd5d9459f17da13b29126cf313328fe3
Ответ 3
Следует учитывать, что один и тот же заголовок HTTP может встречаться несколько раз с разными значениями:
Map<String, Serializable> headers = Collections.list(request.getHeaderNames()).stream().collect(Collectors.toMap(h -> h, h -> {
ArrayList<String> headerValues = Collections.list(request.getHeaders(h));
return headerValues.size() == 1 ? headerValues.get(0) : headerValues;
}));
Ответ 4
@cepro
Я получаю эту ошибку компиляции в вашем коде
"Требуются несовместимые типы: Java.util.map Найдено: java.lang.Object"
Интересно, чего не хватает