HttpServletRequestWrapper and Filter lifecycle in tomcat - java

I am coding a Tomcat application and am authenticating against Google's oauth2 services. I was originally going to write a simple Filter to do the authentication but there is no way to set the user principal in a Filter. From my understanding you have to have the Filter call an implemented HttpServletRequestWrapper and set it inside of that class as seen in this post
I'm pretty sure Tomcat only instantiates one Filter of each type you may have defined and all requests go through this single object down the Filter chain (correct me if I'm wrong).
In the linked to code, is it correct for the code to call
next.doFilter(new UserRoleRequestWrapper(user, roles, request), response);
where every request is instantiating a new UserRoleRequestWrapper? Should this Filter instead have one request wrapper instatiated that gets shared amonsgst all requests? I'm having a hard time finding documentation on the specs of classes such as these.

I don't think that a Filter is what you're looking for. Doesn't seem right for this purpose... Filters weren't created for such use cases; they were created for pre/post processing requests and responses, with emphasis on manipulating the actual request/response data, rather than other aspects of the client-server communication (such as security). Remember, authenticating a user may have further repercussions than just handling HTTP request cycles. Security ties into the JavaEE framework in a lower level than HTTP cycles.
If you want to authenticate against oauth2, you should be far better off implementing some sort of a JAAS implementation for it, and plug it into Tomcat.

Related

How to use caching to improve performance of OAuth2 ResourceServer in Spring Boot

I am trying to use externalized Authorization Server and Resource Server protected with OAuth2. Spring Boot allows multiple ways of securing Resource Server with externalized Authorization Server by using RemoteTokenServices or providing user-info-uri. I am using user-info-uri for validating tokens on the resource server.
With this arrangement whenever a request reaches a ResourceServer it simply makes a REST call to user-info-uri using OAuth2RestTemplate. This will overwhelm Authorization Server when there is increased traffic. That is why I want to cache the results for the first call and in the subsequent calls I will check the presence of Token in the cache. If it is present I want to simply allow the request to reach the controller else I want to call user-info-uri.
How to achieve this. I am using JWT for tokens. I know when I use JWT I could provide public key to the resource server but I am not sure if it is the good way since I have too many Resource Servers.
I tried providing UserInfoRestTemplateCustomizer Bean as suggested in here https://docs.spring.io/spring-security-oauth2-boot/docs/current-SNAPSHOT/reference/htmlsingle/#oauth2-boot-resource-server-custom-user-info but not sure what to do here.
I think you will want to supply a custom implementation of the User Service which is used by the Spring Security Context, when it converts a JWT to the AuthenticationContext. The default behavior will call out to the User Info Endpoint, should you have one configured.
It is possible to provide a custom OidcUserService when configuring the security context. From https://docs.spring.io/spring-security/site/docs/5.1.5.RELEASE/reference/htmlsingle/#oauth2login-advanced-oidc-user-service
Another alternative is apply a custom JwtAuthenticationConverter (see HttpSecurity.oauth2ResourceServer().jwtAuthenticationConverter ), which can deal with issues when converting a jwt to authentication. Check out https://docs.spring.io/spring-security/site/docs/5.1.5.RELEASE/reference/htmlsingle/#oauth2resourceserver-authorization
Hope this helps
I found that the default handling did not give me the control I wanted. These were my requirements:
https://authguidance.com/2017/10/03/api-tokens-claims/
Here is the code I ended up using, since I could not get the claims I wanted into the access token.
My example is a little complex but I hope it helps you understand some options for extending Spring Boot default processing ..

Jersey: Display possible actions on a resource

I am using the Jersey implementation of JAX-RS spec to develop RESTful web services. There is a url that can uniquely identify a resource. Is there a way to let know the user of the RESTful services, the possible actions that can be performed on the resource? For example,
Resource name - host1
http://localhost:8080/state-fetcher/rest/object/host1/actions
This should give me all the possible actions that can be performed on the resource - {actions: [GET, POST, DELETE]}
Thanks!
Use the OPTIONS HTTP method on the resource. You will get the allowed methods in Allow header, for example: Allow: GET, HEAD, PUT and in a payload you will find the fragment of wadl associeted with the specified resource.
A RESTful service itself is inteded to be self- descriptive! If the user performs a request, the REST service should send back a list of possible links, which can be performed next, along with the response. That's the motivation and general concept of a RESTful serivice. If you provide a graphical WebClient, you just need to provide the initial link (e.g. http:\example.com\restful), and the response sends back a list of valid links which just needs to be visualized within the GUI. Usually the webservice only provides those links which are accessible in terms of the users role. (This is not a security feature!!! It just prevents that unecessary links are displayed) Otherwise the OPTION method of the HTTP protocol provides information concerning the supported protocol methods.

Handling complex authorization in spring security

I have a spring MVC web app using pre- and post- authorization method annotations.
I have a particular method in one of my services that needs to apply much more complex authorization logic.
I notice there's a PermissionsEvaluator interface, but that appears to be intended for a more global approach to permissions rather than per-module. I suppose one could write an implementation that delegated to module-specific PermissionsEvaluators, but that seems like a lot of work.
Additionally, I'd be doubling up on a lot of effort. The authorization decision is based on intermediate state during the actual processing. If I used the PreAuthorize mechanism, I'd be generating that state once for authorization, then again "for realsies".
Is there a standard spring exception I can throw from my service layer directly? Is there some other approach I should consider?
Consider using AccessDeniedException. It is thrown internally by Spring Security when a pre- or post-condition evaluates to false. By default it generates a 403 Forbidden page.

Securing a stateful web service

We are planning on developing a layer of REST services to expose services hosted on a legacy system. These services will be used by a classic web application and native mobile phone applications.
This legacy system is secured in such a way that an initial username + password authentication is required (a process that can take 5 to 10 seconds). After the initial authentication, a time-constrained token is returned. This token must then be included in all further requests or else requests will be rejected.
Due to a security requirement, the legacy security token cannot be returned outside of the REST service layer. This means that the REST service layer needs to keep this token in some form of user session, or else the expensive username + password authentication process would need to be repeated for every call to the legacy system.
The REST service layer will be implemented using a Java 6 + Spring 3 + Spring Security 3 stack. At first sight, it looks like this setup will run fine: Spring-based REST services will be secured using a rather standard Spring Security configuration, the legacy security token will be stored in the user's HTTP session and every call will retrieve this token using the user's session and send it to the legacy system.
But there lies the question: how will REST clients send the necessary data so that the user's HTTP session is retrieved properly? This is normally done transparently by the web browser using the JSESSIONID cookie, but no browser is involved in this process. Sure, REST clients could add cookie management to their code, but is this an easy task for all Spring RestTemplate, iPhone, BlackBerry and Android clients?
The alternative would be to bypass the HTTP session at the REST service layer and use some other form of user session, maybe using a database, that would be identified using some key that would be sent by REST clients through a HTTP header or simple request query. The question then becomes, how can Spring Security be configured to use this alternative session mechanism instead of the standard Servlet HttpSession?
Surely I am not the first dealing with this situation. What am I missing?
Thanks!
There's nothing magical about cookies. They're just strings in HTTP headers. Any decent client API can handle them, although many require explicit configuration to enable cookie processing.
An alternative to using cookies is to put the JSESSIONID into the URL. I don't know anything about spring-security, but it seems that that's actually the default for at least some types of URL requests, unless disable-url-rewriting is explicitly set to true . This can be considered a security weakness, though.
Unfortunately authentication is highly problematic -- a bit of a blind spot in terms of web standards and browser implementations. You are right that cookies are not considered "RESTful" but purists, but even on fully-featured browsers avoiding takes quite a bit of hackery, as described in this article: Rest based authentication.
Unfortunately I haven't done any mobile development, so I can't suggest what the best compromise is. You might want to start by checking what authentication models each of your targetted platforms does support. In particular, two main options are:
HTTP authentication (ideally "digest", not "basic")
Cookies
One possibility would be to provide both options. Obviously not ideal from a technical or security point of view, but could have merits in terms of usability.

Java servlet and authentication

I have a small application with 3-4 servlets and a basic module that provide me authentication like:
public class Authentication {
public boolean isUserAuthenticated(){
....
}
}
Is there a way to check the authentication using my class BEFORE every other servlet calls, without have to add code in each of them? I'd like to avoid the check of the user for every servlet I have and for every servlet I will have to add.
Any suggestion is well accepted :)
Thanks, Roberto
Absolutely, use a servlet filter. It's the standard way of implementing security in Java Web applications.
The Java Servlet specification version
2.3 introduces a new component type, called a filter. A filter dynamically
intercepts requests and responses to
transform or use the information
contained in the requests or
responses. Filters typically do not
themselves create responses, but
instead provide universal functions
that can be "attached" to any type of
servlet or JSP page.
You can put your authentication logic in a Servlet Filter. If the filter finds a request not authenticated, it can redirect the user to a login page (or whatever).
Anything that gets to a servlet is implicitly authenticated by then.
Use Acegi Security (now Spring Security). Using Spring will also make your life easier in other ways. (Spring security works using a servlet filter as mentioned in above posts).
User Authentication can be done though servlet filters.
Check the detailed example User Authentication Filter Example

Categories

Resources