Como definir um cabeçalho em uma resposta com o Spring 5
1. Visão geral
Neste tutorial rápido,we’ll go through different ways of setting a header on a service response, para endpoints não reativos ou para APIs usandoSpring’s 5 WebFlux framework.
Podemos encontrar mais informações sobre este framework emprevious posts.
2. Cabeçalhos para componentes não reativos
Se quisermos definir cabeçalhos em respostas únicas, podemos usar objetosHttpServletResponse ouResponseEntity.
Por outro lado, se nosso objetivo é adicionar um filtro para todas ou várias respostas, precisaremos configurar umFilter.
2.1. UsandoHttpServletResponse
Simplesmente temos que adicionar o objetoHttpServletResponse ao nosso endpoint REST como um argumento e, em seguida, usar o métodoaddHeader():
@GetMapping("/http-servlet-response")
public String usingHttpServletResponse(HttpServletResponse response) {
response.addHeader("example-Example-Header", "Value-HttpServletResponse");
return "Response with header using HttpServletResponse";
}
Conforme mostrado no exemplo, não precisamos retornar o objeto de resposta.
2.2. UsandoResponseEntity
Neste caso, vamos usar oBodyBuilder fornecido pela classeResponseEntity:
@GetMapping("/response-entity-builder-with-http-headers")
public ResponseEntity usingResponseEntityBuilderAndHttpHeaders() {
HttpHeaders responseHeaders = new HttpHeaders();
responseHeaders.set("example-Example-Header",
"Value-ResponseEntityBuilderWithHttpHeaders");
return ResponseEntity.ok()
.headers(responseHeaders)
.body("Response with header using ResponseEntity");
}
A classeHttpHeaders oferece muitos métodos convenientes para definir os cabeçalhos mais comuns.
Podemos ver mais exemplos ilustrando esses pontos emour Github repo.
2.3. Adicionando um cabeçalho para todas as respostas
Agora, vamos imaginar que queremos definir um cabeçalho específico para muitos de nossos endpoints.
Obviamente, seria frustrante se tivéssemos que replicar o código anterior em cada método de mapeamento.
A melhor abordagem para fazer isso é porconfiguring a Filter in our service:
@WebFilter("/filter-response-header/*")
public class AddResponseHeaderFilter implements Filter {
@Override
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
HttpServletResponse httpServletResponse = (HttpServletResponse) response;
httpServletResponse.setHeader(
"example-Example-Filter-Header", "Value-Filter");
chain.doFilter(request, response);
}
@Override
public void init(FilterConfig filterConfig) throws ServletException {
// ...
}
@Override
public void destroy() {
// ...
}
}
A anotação@WebFilter nos permite indicar ourlPatterns para o qual esteFilter lavado se torna efetivo.
Como apontamosin this article, para tornar nossoFilter detectável até Spring, precisamos adicionar a anotação@ServletComponentScan annotation à nossa classe Spring Application:
@ServletComponentScan
@SpringBootApplication
public class ResponseHeadersApplication {
public static void main(String[] args) {
SpringApplication.run(ResponseHeadersApplication.class, args);
}
}
Podemos evitar esta última etapa se não precisarmos de nenhuma das funcionalidades fornecidas por@WebFilter, usando a anotação@Component em nossa classeFilter.
3. Cabeçalhos para endpoints reativos
Novamente, veremos como definir cabeçalhos em respostas de endpoint único usando classes e interfacesServerHttpResponse,ResponseEntity orServerResponse (para endpoints funcionais).
Também aprenderemos como implementar um Spring 5WebFilter para adicionar um cabeçalho em todas as nossas respostas.
3.1. UsandoServerHttpResponse
Esta abordagem é bastante semelhante à contraparteHttpServletResponse:
@GetMapping("/server-http-response")
public Mono usingServerHttpResponse(ServerHttpResponse response) {
response.getHeaders().add("example-Example-Header", "Value-ServerHttpResponse");
return Mono.just("Response with header using ServerHttpResponse");
}
3.2. UsandoResponseEntity
Podemos usar a classeResponseEntity exatamente como fazemos para endpoints não reativos:
@GetMapping("/response-entity")
public Mono> usingResponseEntityBuilder() {
String responseHeaderKey = "example-Example-Header";
String responseHeaderValue = "Value-ResponseEntityBuilder";
String responseBody = "Response with header using ResponseEntity (builder)";
return Mono.just(ResponseEntity.ok()
.header(responseHeaderKey, responseHeaderValue)
.body(responseBody));
}
3.3. UsandoServerResponse
As classes e interfaces introduzidas nas duas últimas subseções podem ser usadas em@Controller classes sannotated, mas não são adequadas para os novosSpring 5 Functional Web Framework.
Se quisermos a interfaceto set a header on a HandlerFunction then we’ll need to get our hands on the ServerResponse:
public Mono useHandler(final ServerRequest request) {
return ServerResponse.ok()
.header("example-Example-Header", "Value-Handler")
.body(Mono.just("Response with header using Handler"),String.class);
}
3.4. Adicionando um cabeçalho para todas as respostas
Por último,Spring 5 provides a WebFilter interface to set a header on all the responses recuperado por um serviço:
@Component
public class AddResponseHeaderWebFilter implements WebFilter {
@Override
public Mono filter(ServerWebExchange exchange, WebFilterChain chain) {
exchange.getResponse()
.getHeaders()
.add("example-Example-Filter-Header", "Value-Filter");
return chain.filter(exchange);
}
}
4. Conclusão
Em conclusão, aprendemos muitas maneiras diferentes de definir um cabeçalho em uma resposta, se quisermos defini-lo em um único endpoint ou se quisermos configurar todas as nossas APIs restantes, mesmo se estivermos migrando para a pilha reativa , agora temos o conhecimento para fazer todas essas coisas.
Como sempre, todos os exemplos podem ser acessados em nosso repositório Github, tanto osnon-reactive onese os que usamSpring 5 specific functionality.