I am reading Spring Security documentation it says that SecurityContextHolder provides different types of strategy for apps with specific thread behaviour. For example - Swing applications.
I understood that in web apps we can use ThredLocal strategy. But when to use other 2 strategies and how they work I cant understand.
See Spring Security Reference:
SecurityContextHolder, SecurityContext and Authentication Objects
The most fundamental object is SecurityContextHolder. This is where we store details of the present security context of the application, which includes details of the principal currently using the application. By default the SecurityContextHolder uses a ThreadLocal to store these details, which means that the security context is always available to methods in the same thread of execution, even if the security context is not explicitly passed around as an argument to those methods. Using a ThreadLocal in this way is quite safe if care is taken to clear the thread after the present principal’s request is processed. Of course, Spring Security takes care of this for you automatically so there is no need to worry about it.
Some applications aren’t entirely suitable for using a ThreadLocal, because of the specific way they work with threads. For example, a Swing client might want all threads in a Java Virtual Machine to use the same security context. SecurityContextHolder can be configured with a strategy on startup to specify how you would like the context to be stored. For a standalone application you would use the SecurityContextHolder.MODE_GLOBAL strategy. Other applications might want to have threads spawned by the secure thread also assume the same security identity. This is achieved by using SecurityContextHolder.MODE_INHERITABLETHREADLOCAL. You can change the mode from the default SecurityContextHolder.MODE_THREADLOCAL in two ways. The first is to set a system property, the second is to call a static method on SecurityContextHolder. Most applications won’t need to change from the default, but if you do, take a look at the JavaDoc for SecurityContextHolder to learn more.
Related
I am interested in finding a pattern or strategy for identifying which code path called a specific API method (or set of methods).
Here are some examples of differentiation in my application:
Caller calls API via an exposed REST controller
Caller calls API via some other internal API
Caller calls API via a user-created plugin
The application does use Spring for core wiring as well as Spring Security. However, the caller could be any user so using the Spring security context to inspect authentication or their associated granted authorities doesn't appear to be the right fit. The same user could call into the API method via one of the exposed REST URIs or call in via an arbitrary plugin entry-way.
How can one manage this type of identification without exposing additional or semi-duplicated APIs for different entry-points? I would like to be able to identify where a particular call originates. Slight differences in functionality can occur depending on whether the call came from one of our REST endpoints as opposed to one user-generated plugin as opposed to some other user-generated plugin.
This could hint at using some form of interception/aspect, but I do not have control over plugin code since I did not generate it. Plugins do have to register in order to get integrated so there is a programmatic hook there.
Looking for suggestions on how to manage this type of issue whether it's using additional Spring feature functionality or an alternative idea or library.
In fact this is a nice question.
As far as i see there are these options:
semi duplicated API (already mentioned above)
different users (or user-groups)
get callstack using reflection (but hard to do and not really recommended)
instead of user you can use some kind of authorization-token "per session" and see if the session is create via HTTP call or if it is an "internal" session
check some kind of session-id and save inside your session where it was created (internal or external, ...)
For now i don't see any other possibilities.
ps: to "flag" the session as internal/external can be done by adding an own spring handler.
Hope this brings you to the right point and helps you out.
Is it recommended to use ThreadLocal to store a Thread Context?
I am building a backend server application where there are typical services that I need to run.
Note: We are not building this over a SOA architecture.
Before the start of each service I need to give it a state which has some Service Contex which is variable map to work up on. This variable map is shared when services are running parallelly.
Now for example a service needs to check weather it has to be halted or timed-out based on some thread related parameters.
Question: Is it a good approach to keep the thread context inside thread local and then building api's over service context to access parameters over these variables.
This would help me to hide the complex behavior and it wouldn't open up my internal things.
Thanks,
Aditya
It looks like your server application framework ought to provide you with the means to implement this functionality in a simpler way - unless you are implementing your own framework.
Now for example a service needs to check weather it has to be halted or timed-out based on some thread related parameters.
An EJB container provides this kind of functionality. EJBs also provides a session context and the means to ensure that the context can be restored if execution is transferred between threads (by passivation + activation).
You can use ThreadLocal quite freely but you must define your thread model cleanly (see if you have any control on the thread creation)... also keep in mind that assuring the state stored in the ThreadLocal might not what you expect, if you are relying on any clean-up code.
Also: do use (cant stress more) WeakReference for anything that your code is not directly responsible.
I've bean studying JMX for a while, but I'm stuck.
I have an application that exposes some functionality to remote clients via JMX, although existing security features may be sufficiant for most cases my application uses Apache Shiro framework as the security backend.
My problem is that i don't how to gather client data serverside. Shiro needs a way to identify a client (subject), normally executing thread is associated with a subject but online JMX documentation does not give much clue about thread model of remote JMX.
How can i associate a client with a thread or is there a way to retrieve client data inside the interacted MBeans?
After researching and trying different techniques; there are two winners:
1- New feature called ClientContext that will be a part of Java 7: Java 7 is not yet complete, and ClientContext will break backwards compatibility.
2- Attaching Shiro subject to AccessControlContext: This is the solution I choose, Shiro's default subject retrieval mechanism does not consider Java's access control context. I ran a test a long ago to test this but it didn't work. Now I know why: by default SecurityUtils.getSubject() call attaches the retrieved Subject to the currently calling thread, but this approach is useless since threads can be shared between clients. But AccessControlContext is much more powerful, and it looks like JMX plays nicely with it; your access control context (which is authenticated during login at JMXAuthenticator) can be accessed from a MBeanServerForwarder or even inside your MBean. I tested this with a multiple clients retrieving their principal, it simply works.
Edit: How i attach Shiro subject to the current AccessControlContext?
1- Create an unattached Shiro subject using the builder class Subject.Builder.
2- Authenticate the user (using Shiro subject's login method, etc.)
3- Create a mutable JAAS subject with a singleton set containing the Shiro subject as the private credentials.
4- Provide the JAAS subject to the underlying Java security System (for example, Return the subject inside a JMXAuthenticator's authentication method)
A helper class can be created to simplify this approach. When you need an action to be performed on behalf of the Shiro subject (for authorization, etc.), get it from AccessControlContext and use one of the Subject.execute... methods. This can be performed inside a proxy or a forwarder (like MBeanServerForwarder).
I'm experimenting with a solution to authorization and authentication by storing a subject class in a ThreadLocal map. The design is for an API, so I won't have access to the servlets involved, and I need to use EJB3 (so CDI is not an option). I have a few questions about using ThreadLocal with EJB3
Presuming that each request cleans its ThreadLocal map after it's done, is there any risk in using a ThreadLocal variable with stateless session beans? In other words, is there any risk that two requests get access to the same thread at the same time?
Is there any way of enforcing servlets to clean the ThreadLocal after they're done? I've looked into interceptors, but I've understood that they work poorly with EJB3, and work varyingly well in different application servers. Any other way?
Regarding Martin's answer, it's worth noting that Spring Security itself uses a ThreadLocal anyway by default (SecurityContextHolder), so I'd be cautious about using it if you need the security context to survive across EJB invocations. Certainly it won't work across remote invocations; it might with local, but I don't think there are any guarantees.
Typically, when using Spring Security I avoid EJB and use Spring Framework for wiring a POJO middle-tier and for providing services like transaction demarcation via AOP. The security context is then available throughout the middle tier as the thread remains the same across the entire call.
I'd recommend against using ThreadLocal in an EJB container. Authorisation and Authentication is a cross-cutting concern, I'd personally look at using something like AOP for that (e.g. How Spring security deals with it).
To answer my own question, no, not with any security it seems. Using a threadlocal variable may work if I have control of the whole process, but if I did then I could use CDI och JSP to keep request local variables.
Points to everybody who answered though.
our product is built on a client-server architecture, with the server implemented in Java (we are using POJO's with Spring framework). We have two API levels on the server:
the external API, which uses REST web services - useful for external clients and integrations with other servers.
the internal API, which uses pure Java classes - useful for the actual code inside (as many times the business logic invokes an API call) and for integration with plusins developed inside out company and deployed as parts of our product. The external REST API also uses the internal API.
We implemented permission checking (using Spring security) in the internal API because we wanted to control access at the lowest API level.
But here comes the problem: there are some operations defined on the API level that are regarded as forbidden for a currently logged user, but which should be performed smoothly by the server itself. For example, deleting some entity could be forbidden for the user, but the server might want to delete this entity as a side effect of some other operation performed by the user and we want this to be allowed.
So what is the best approach for allowing the server to perform an operation (in some kind of super-user mode) that might be forbidden for the actual logged-in user?
As I see it we have several options each of which have its pros and cons:
Implement permission checking in external level API (REST) - bad because plugins will bypass permissions checks.
Turn off permission checking for the current thread after the request was granted - too dangerous, we might allow too many server actions that should be forbidden.
Explicitly ask the internal API level to perform the operation in the privileged mode (just like PrivilegedAction in java security framework) - too verbose.
As none of the above approaches is ideal, I wonder what is the best-practice approach for this problem?
Thanks.
Security is applied at the bounds of a module. If I understand you, your system applies security on two levels of abstraction of the (roughly) same API. It sounds complex, as you have to make a double security check on the whole two APIs.
Consider migrating the REST needed methods from the internal API to the external one, and deleting security stuff in the internal API.
external API will manage security for external clients (at the boundaries of your app)
internal API will be strictly reserved for internal app and plugin use (and you would happy hack it, as no external clients are bounded to it)
Do you really need to control the plugin's permissions to your application logic ? Is there a good reason for it ? Plugins are developped by your company, after all. Maybe a formal document explaining to plugin's developpers what should not be done, or a safety test suite validation for the plugin (e.g. assert plugin does not call "this" method) will do the job either.
If you still need to consider these plugins as "untrusted", add the methods they need to your external API (on your app boundary) and create specific security profile for each use: "restProfile", "clientProfile" & "pluginProfile". Each will have specific rights on your external API methods.
It sounds like you need two levels of internal API, one exposed to plugins and one not.
The best way of enabling that would be using OSGi (or Spring Modules). It allows you to explicitly state which packages and classes can be accessed by other modules (ie REST modules and plugin modules). Those would be the exposed level of your new internal API and you would use Spring Security to further restrict access selectively. The internal packages and classes would contain the methods which did all the low level stuff (like deleting entities) and you wouldn't be able to call them directly. Some of the exposed API would just duplicate the internal API with a security check, but that would be ok.
The problem with the best way is that Spring Modules strikes me as still a bit too immature even to put into a new webapp project. There's no way I'd want to shoehorn it into an old project.
You could probably achieve something similar using Spring Security and AspectJ, but it strikes me that the performance overhead would be prohibitive.
One solution that would be quite cool if you could re-architect your system would be to take tasks requiring security elevation offline, or rather make them asynchronous. Using Quartz and/or Apache Camel (or a proper ESB) you could make the "delete my account" method create an offline task that can at a future date be executed as an atomic unit of work with admin priveliges. That means you can cleanly do your security checks for the user requesting account deletion in a completely separate thread to where the deletion actually takes place. This would have the advantage of making the web thread more responsive, although you'd still want to do somethings immediately to preserve the illusion that the requested action had been completed.
If you're using Spring, you may as well utilize it fully. Spring offers AOP that allows you to use interceptors and perform these cross-system checks, and in the event of an unauthorized action, prevent the action.
You can read more about this in Spring's online documentation here.
Hope this helps...
Yuval =8-)