How to set HTTP Strict Transport Security in Dropwizard - jersey

Using latest Dropwizard how I can set HTTP Strict Transport Security? I was thinking of something like the following:
FilterRegistration.Dynamic htstFilter = environment.servlets().addFilter("HEADER", HeaderFilter.class);
htstFilter.setInitParameter("header", "Strict-Transport-Security, max-age=31536000; includeSubDomains");
Will this work?

Related

Spring Cloud Gateway deletes SESSION cookie after a call to resource server

I'm having a problem with SESSION cookie being reset by Spring Cloud Gateway after a call to a resource server.
I have an Angular application, a Spring Cloud Gateway application, an external Authorization Server and a Resource Server of my own.
The Angular application first authorizes via Spring Cloud Gateway app (who delegates this work to external Authorization Server using OAuth2) and receives a SESSION cookie. At this point the user is authenticated and Authentication object is available in Spring Cloud Gateway app.
Next, the Angular app calls an endpoint of Spring Cloud Gateway app, which actually forwards the call to the Resource Server (and includes the Bearer token in the call, so the call works fine), the Resource server returns some result, which is successfully send back through the Spring Cloud Gateway app to the Angular app. BUT alongside successful response the Spring Cloud Gateway app sends this header:
set-cookie: SESSION=; Max-Age=0; Expires=Sat, 17 Aug 2019 20:39:44 GMT; Path=/; HTTPOnly
which kills the cookie on the client side and makes subsequent calls impossible, even though the Authentication object is still alive and the session looks to fine as well.
Does anyone know what can be the reason of such behavior?
We had the exact issue in our WebFlux resource servers -- the API gateway would proxy a request to a resource server, so the first request worked, but subsequent requests would try to authenticate again because the SESSION cookie was cleared out, resulting in some X-XSRF-TOKEN errors.
We solved this by adding .requestCache().requestCache(NoOpServerRequestCache.getInstance()) to our securityWebFilterChain bean definition in our WebFlux resource servers.
#EnableWebFluxSecurity
#EnableReactiveMethodSecurity
class ResourceServerConfiguration {
#Value('${spring.security.oauth2.resourceserver.jwt.jwk-set-uri}')
String jwkSetUri
#Bean
SecurityWebFilterChain securityWebFilterChain(ServerHttpSecurity http) {
http
.csrf().disable()
.requestCache().requestCache(NoOpServerRequestCache.getInstance()).and()
.httpBasic().disable()
.formLogin().disable()
.oauth2ResourceServer().jwt().jwkSetUri(jwkSetUri)
.and().and()
.authorizeExchange()
.pathMatchers("/v1/**").authenticated()
}
}
In the "classic" MVC world, you would configure your ResourceServerConfigurer classes like this:
#Override
protected void configure(HttpSecurity http) throws Exception {
http.sessionManagement()
.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
}
Update 11/22/2022
Our microservice architecture has begun to expand, and we started seeing this issue again on services not owned by our team. Turns out they had stateful web services, meaning, sessions were created when calling them which caused the SESSION cookie to get overridden on the Spring Cloud Gateway client application. We applied this to our configuration to permanently resolve this issue:
server:
reactive:
session:
cookie:
name: SESSION_${spring.application.name}
👆 This eliminates an issue where SESSION cookies from other web service calls collide with the Gateway client's SESSION cookie.
I had encountered the same case.
Did the external Authorization Server produce a cookie which is base64 encode?
Such as Set-Cookie: SESSION=YWZjOTc4YmUtOTNmNy00N2UxLTg0NjgtYWJlNWMwZmNiOWUx
If so, it will cause the problem.
The CookieWebSessionIdResolver defined in Spring Web used by Spring Cloud Gateway does not deal with the base64 encoded cookie values. Instead, it directly uses the raw cookie value to find the corresponding session in the storage. Obviously, no Authentication object will be found. So that Spring Cloud Gateway choose to kill the "invalid" cookie given by the Angular app.
There are two solutions given below.
Disable base64 encoding of cookie values in the external Authorization Server if it is also managed by you.
Override WebSessionIdResolver to change the default behaviour so as to decode cookie values when reading by session manager. And don't forget to register it as a Spring Bean in your Spring Cloud Gateway implementation.
In my case, Solution 1 was choosen. My Authorization Server uses Spring Security + Spring Session. I changed the default settings of HttpSessionIdResolver like this.
CookieHttpSessionIdResolver cookieHttpSessionIdResolver = new CookieHttpSessionIdResolver();
DefaultCookieSerializer defaultCookieSerializer = new DefaultCookieSerializer();
defaultCookieSerializer.setUseBase64Encoding(false);
defaultCookieSerializer.setCookieName("SESSION");
cookieHttpSessionIdResolver.setCookieSerializer(defaultCookieSerializer);

Spring WebClient with proxy server: Missing HTTP headers

I'm using the Spring WebClient from spring-boot-starter-webflux 2.1.3.RELEASE to check the anonymity level of proxy servers. After I made some requests with the WebClient to a custom node.js http server through some proxy servers, there are no proxy related HTTP headers in my requests. I'm missing e.g. x-forwarded-for, via, x-proxy-id.. just the remote-address is exposed.
As far as I understood it, the netty client connects to the proxy via tcp CONNECT for every proxy type (HTTP,SOCKS4/5) and this is the reason for the missing headers.
Question:
Is there a way to get classic proxy HTTP headers with this approach or is there another way to configure a proxy server with the WebClient?
My example configuration:
HttpClient httpClient = HttpClient.create()
.tcpConfiguration(tcpClient ->
tcpClient
.proxy(proxy -> {
proxy.type(ProxyProvider.Proxy.HTTP).address(new InetSocketAddress(ip, port));})
.option(ChannelOption.CONNECT_TIMEOUT_MILLIS, 10000)
.doOnConnected(connection ->
connection
.addHandlerLast(new ReadTimeoutHandler(10000))
.addHandlerLast(new WriteTimeoutHandler(10000))));
ReactorClientHttpConnector connector = new ReactorClientHttpConnector(httpClient);
WebClient build = WebClient.builder()
.baseUrl(baseUrl)
.clientConnector(connector)
.build();
Expected headers
{"user-agent":"ReactorNetty/0.8.4.RELEASE","host":"21X.8X.XX.145:8XX","accept":"*/*","x-proxy-id":"719306848","x-forwarded-for":"21X.8X.XX.145","via":"1.1 101.XX.8X.11X (Mikrotik HttpProxy)"}
Actual headers
{"user-agent":"ReactorNetty/0.8.4.RELEASE","host":"21X.8X.XX.145:8XX","accept":"*/*"}
The reason for the missing headers is the CONNECT request, which establishes a TCP tunnel instead of sending HTTP requests to the proxy.
But unfortunately as stated in
https://github.com/netty/netty/issues/8269
and
https://github.com/spring-projects/spring-framework/issues/21767
the underlying netty client which is used by the webclient issuing a CONNECT request for every type of proxy and this will not be changed.

Interceptor for http outbound gateway

Has sprint integration http outbound gateway has any configuration property to add interceptor into org.springframework.web.client.RestTemplate ?
I want to intercept the httpRequest for adding some security information in request (like interceptor property in ws-ouboundgatewy) ,But I could not see any interceptor configuration option in http outbound gateway?.
Do we have any other option to achieve this functionality ?
You can inject to the <int-http:outbound-gateway> any custom RestTemplate bean using rest-template attribute on the first one.
But from other side I don't see any mentions for interceptor logic in the RestTemplate...

Can I add cookie with Spring SockJs websocket implementation

Can I add custom cookies over websocket in Spring SockJS implementation? The way we can add it with http request/ response?
Forget to mention that I see way to read cookie from headers :: HttpHeaders headers= session.getHandshakeHeaders(); -But I do not see a way to set headers. With headers I can read the cookies -but how to set it?
This is all work-in-progress still, but at this time you can configure a HandshakeInterceptor on the DefaultSockJsService. That gives you access to the request and response before and after the handshake.

JerseyClient using DefaultHttpClient

I need to access a JAX-WS webservice protected by SSL using Jersey Client. I have successfully got this working with limited configuration and just letting the Client use the default HTTPURLConnection API.
This approach wont work however for my overall solution because it does not allow me the flexibility to change the credentials used when making a request to the WS. I'm trying to use DefaultHTTPClient instead and then passing it to the Client object on intialization.
NTCredentials credentials = new NTCredentials("username", "password",
computerName, domainName);
DefaultHttpClient httpClienttemp = new DefaultHttpClient();
DefaultHttpClient httpClient = wrapClient(httpClienttemp);
httpClient.getCredentialsProvider().setCredentials(AuthScope.ANY, credentials );
ClientConfig config = new DefaultClientConfig();
The wrapClient method creates an X509TrustManager and overrides the necessary methods so that all certificates are accepted. It also creates a SchemeRegistry entry for https access on port 443. This configuration results in a Connection refused exception.
The strange thing is, if i add an additional entry in the SchemeRegistry for http and give it a port of 443 then the request does get sent however a Connection Reset exception then gets thrown.
The Url i use to create the WebResource object is https however the SOAPAction i declare in the header uses http. Any ideas where im going wrong?
This is a limitation of the default HTTP Client (com.sun.jersey.api.client.Client) documented in the Jersey docs. You will have to use Apache HTTP Client to achieve this functionality.
Looks like someone already recommended doing this in the answer to your previous question: Jersey Client API - authentication.
EDIT: Corrected reference to the default Jersey HTTP Client to avoid confusion.

Resources