Are there issues with using Spring Security's HttpSessionSecurityContextRepository on CloudFoundry? - spring-security

I understand that Spring Security's HttpSessionSecurityContextRepository makes use of HttpSession.
Furthermore, I have read that PaaS such as CloudFoundry try to avoid session replication for the purpose of scalability.
I intend to deploy an application to the CloudFoundry PaaS.
Are there issues with using HttpSessionSecurityContextRepository on CF?

CloudFoundry documentation simply says that HTTP Sessions are not replicated across instances by default. All this means is that applications deployed on multiple instances will be unable to use any sort of HTTP session clustering by default. HTTP sessions become sticky, that is, all HTTP requests in the same session will be routed to the instance on which the session for the request resides. In case an instance fails, users who had active session on that instance will be migrated to other instances but they will lose their session information, which will mean they will have to login again.
This does not mean it is unsafe to use Spring Security in such an environment. The semantics with Spring Security will be the same as those without it. Once a user has logged in, they will continue to access the CloudFoundry instance on which their session was created. If that instance crashed, they will be automatically ported to another instance but will have to login again.
If the default set up (without session replication) is a concern, it is certainly possible to share sessions across instances. CloudFoundry forums list two ways of achieving this - via Redis and using JDBC. It is also possible to implement your own solution using one of the CloudFoundry services.

Related

Can Spring Session be setup in an application not running a spring application?

We have a CMS running in one tomcat container, that is not a spring application. We also have multiple applications running on separate tc server instances that contain our custom code (account management, cart, etc.). These are all spring 4.0.x applications and are secured with Spring Security.
I would like to enable Spring Session between all of these environments. Do you foresee any issues using Spring Session in an environment such as this?
Spring Session should work on projects that are not otherwise Spring. If you take a look at the HttpSession Sample listed in the Samples section of the reference and you will see it works just fine with a standard servlet too.
In fact, depending on how you choose to integrate, Spring Session requires no additional dependencies on Spring at all. For example, the Hazelcast sample demonstrates how you don't need any Spring dependencies (other than Spring Session itself).
The possible problems I'd foresee:
If your CMS uses session very heavily, then the IO of retrieving your Session on every request can slow down things significantly
The SESSION cookie is how the session is stored in the browser and then passed back to the application. Spring Session by default writes this in a cookie with the path of the context root. This means that the SESSION cookie will not be visible to all of the applications. You can customize this with your own implementation. You can follow issue 87 for progress on making this available by default.

Current recommendation for enabling session in Azure Websites for Session variables and TempData?

I have a MVC3, ASP.NET 4.5 web application deployed on Azure Websites, using SQL Azure.
Currently I am using some "inproc" Session variables which I need to remove since I am going to start using multi website instances. I could just store the Session variable values in the SQL Azure DB, but I am also using TempData, which also uses Session state, "under the bonnet". Due to TempData use, I do need to implement an "out of proc" session solution.
I have seen some recommendation for using AppFabric caching, but I am unsure whether this is still current, and whether it is correct for Azure websites.
Also my development setup is on a Windows 7 machine with SQL Server 2008 R2. So a solution should be transferable with minimum pain.
There is also a "thread agility" issue with session variables, and a open source solution has been created using REDIS caching, but I have no experience of this, or REDIS. See: GitHub site
So thoughts I have are:
1) Angieslist/AL-redis custom provider, see: GITHUB link . Not entirely sure that this can be used in a Azure Websites application.
2) Appfabric. Not sure if this is relevant or current for Azure Websites.
3) SQL Azure session provider.
4) Azure Table storage.
5) Use a custome TempData provider to persist via cookies ie https://www.nuget.org/packages/BrockAllen.CookieTempData.dll/1.2.2, and then remove other session variables.
I would be very grateful for advice on a good Azure Websites session implementation mechanism which is simple. My data is pretty simple. I think I have one object which I quess I will need to serialize, probably via Json.NET
If you have more than one instance of an Azure Web Site, sticky sessions are enabled by default by the load balancer. This means that a user will be directed to the same instance (server) and that you'll be able to use session state in your app.
You may also find the Distributed Caching section (Ch 12) of this ebook helpful http://aka.ms/CloudApps_PDF

Problems while implementing SSO with Spring Security CAS extension

I'm trying to use Spring Security CAS extension to authenticate users on my applications. Earlier there was only one application, so SSO was not needed. Now there is one more application and I want the user to log in once and use all the applications without having to go through authentication again (SSO, basically). I've a bunch of questions like these -
All the applications I have are part of a single tomcat container and will be served via same domain. I checked Tomcat SSO Valve, but it seems to need container based authentication, I'm not really sure if I would want to use that for authentication / authorization. I'm using spring security form-based login. Do I really need something like Jasig CAS or will it be an overkill?
Spring Security and CAS deployerContext Configuration - http://pastie.org/8408976 and http://pastie.org/8408967
I set up Spring Security CAS with Jasig server and SSO seems to work as logging in to any of the applications suffices to access the other application. I've modified the deployerConfigContext.xml to replace the inMemoryServiceRegistryDaoImpl with JPA / Hibernate one. But I always see the below line in my logs. Though the tables have been created (SERVICETICKET and so on) in my db. These tables are always empty when I try logging in and out.
2013-10-17 16:41:18,882 INFO [org.jasig.cas.services.DefaultServicesManagerImpl] - <Loaded 0 services.>
When I try to access URL https://localhost/cas/services, it returns an error "This website has a redirect loop". and I see the below piece repeating n number of times in the logs (with different ticket numbers)-
http://pastie.org/8408940
I don't have any REST or stateless services accessing authenticated resources, do I need proxy tickets at all?
Note: I'm using Spring Security 3.1.4.RELEASE and CAS server 3.5.2 version.
Any pointers will be helpful.
I set up Spring Security CAS with Jasig server and SSO seems to work
as logging in to any of the applications suffices to access the other
application. I've modified the deployerConfigContext.xml to replace
the inMemoryServiceRegistryDaoImpl with JPA / Hibernate one. But I
always see the below line in my logs. Though the tables have been
created (SERVICETICKET and so on) in my db. These tables are always
empty when I try logging in and out.
When I try to access URL `https://localhost/cas/services`, it returns an error "This website has a redirect loop". and I see the
below piece repeating n number of times in the logs (with different
ticket numbers)
I figured out the solution to this. This was happening as filterProcessesUrl in CAS server configuration had the string "acegi" (old name for Spring Security), which didn't match to "spring", hence the problem. Modifying that helped. Not sure why old name was hardcoded there. Also, it didn't pick up this string from cas.properties, so figuring it out was a little more difficult.
I hope to get answers for other questions.

How to store spring security session information in redis?

I am using Spring security for Authentication and Authorization in my application. I am using Neo4j database as backend and implemented userDetailsService for authentication.
However, whenever my application restarts, user is forced to login once again.
To overcome this, i am thinking to store session information in redis database and load the data to Spring security Context whenever application gets started.
Kindly pass on if there are any articles and pointers to implement the same.
I am thinking of following implementation for it,
1) For every successful authentication, store user details and session details in redis.
This must be implemented in loadUserByUsername() method of UserDetailsService implementation
2) Remove the data from redis, whenver user logs out, Where can i do this information? Is there any spring security function where i can call this
3) Load all the data from redis to spring security whenever application restarts, again where do i need to write this logic?
Please let me know if i have missed any information.
All you need to do is to implement a
SecurityContextRepository that handles security context storage to reds
Eventually a custom filter that retrieves/ stores session information (GenericFilterBean)
I think it is possible to just give the standard filter a different repository, but I am not sure, I needed my own implementation anyway...
Store session in a redis is out-of the box functionality now
http://docs.spring.io/spring-session/docs/current/reference/html5/guides/httpsession.html
You need to configure remember-me feature of Spring Security.
Remember-me or persistent-login authentication refers to web sites being able to remember the identity of a principal between sessions. This is typically accomplished by sending a cookie to the browser, with the cookie being detected during future sessions and causing automated login to take place. Spring Security provides the necessary hooks for these operations to take place, and has two concrete remember-me implementations. One uses hashing to preserve the security of cookie-based tokens and the other uses a database or other persistent storage mechanism to store the generated tokens.
More information available in Spring Security documentation:
http://static.springsource.org/spring-security/site/docs/3.1.x/reference/remember-me.html
You can use out of box implementations or inject your own (aforementioned redis).
As Luke Taylor said, Tomcat's default action is serialize/deserialize sessions on container restart.
Here
pathname attribute of standard manager is the name of the serialization file. If you dont specify a path name attirbute the default is SESSIONS.SER
If you dont want to have sesssions back when restarted, you need to specify it as empty string value..

Getting logged off on Azure

We have an ASP.NET MVC3 based Web role running on the Azure cloud, using Forms Authentication.
Occasionally we have noticed that users that are logged in will get logged out automatically without any action (while the browser window is open).
Has anyone else seen this? Any ideas as to why this might be happening?
It has been observed on multiple machines for multiple users using multiple browsers.
Thanks!
Not much to go on, here, but...
Are you running multiple instances? If so, did you set up SQL Azure or Cache as your Session Provider? If not, you'd have two sets of session state, and depending on which VM instance you hit, your user's session state may or may not be present.
Is the logout happening after 20 minutes of inactivity? That's the default timeout for the AppPool before it recycles.
Does this happen in the Compute Emulator as well as when you deploy?
Since the windows azure network load balancing doesn't support affinity, each single client request will be redirected to any node instance. If you don't use SQL Azure or Azure AppFabric Cache as Session Provider, each instance will have his asp.net session in-memory. Then each in-memory session will be invisible to other instances.
Most likely either you are running InProc for your Session and when the users go to a new server they are having to log in again or your server is restarting for some reason. If you are using InProc, switch to AppFabric Caching and if you are using that already, log into the box and check the event logs to see if the process is restarting (look for an unhandled exception).

Resources