How stateless server can keep session state on server side? - java

I'me reading Marting Fowler's famous book Patterns of enterprise application architecture to systematize my knowledge.
I've read chapter Session and States and I a bit confused. In the first part of the chapter author recommend to use stateless server to avoid some sort of issues. Then author says that sometimes wee need to save some data on the server side - for example user cart in a internet shop. But to implement session with state we can use stateless server. Then author describes ways to save session state(client, server, database)
But after reading this chapter I don't understand what a stateless server is. How a server can be stateless if it keeps session state ?

Quora has a nice definition:
A stateless service is a service that does not store any data on the application server. It reads or writes data to the database, returns a value (or not), and after that, any information on the task itself is forgotten.
Meaning: it isn't that server itself that keeps the state data. It can put it into some database. It might then provide the client with some sort of token that the client can include in future calls. And that token enables other servers to retrieve the corresponding data from say, a database.
The key point is: sure, the information needs to be stored somewhere. But that somewhere isn't the server, but some infrastructure that all the stateless servers can get to.

Related

Managing session in stateless microservices

If microservices are stateless , how can we manage session in JSP based projects .Assuming I am breaking age old monolith to microservices .
You can't manage session in a stateless server.
What you can do is that storage a unique token and its corresponding information into Redis/MemCache.
You need to storage the token instead of JSESSIONID in client.
The fact that most implementations of microservices in the industry communicate via HTTP does not mean that microservices are meant to be used as web servers.
A microservice:
does not have to communicate via HTTP (though most implementations do, for convenience)
is not meant to receive requests issued by a web browser (although you can use a web browser to issue requests to an HTTP-listening microservice to test it)
is certainly not meant to generate responses containing HTML that can be rendered in a browser.
For these reasons, microservices generally do not have a concept of a session.
If you absolutely must make your microservice session-aware, and retain it stateless (so that it can still be legitimately called a microservice) then you have to have it fetch all necessary session information from your persistence store each time a request arrives, and save whatever parts of it have changed back into the persistence store right before returning its response. But that's not how microservices are meant to work.
Generally, the way we use microservices on the web is as follows:
Either we have javascript running on the browser which maintains session state and issues sessionless requests to the microservice, containing authentication information if necessary, [*] or
We build a conventional web server which maintains session state the traditional way and is therefore not a microservice, and we have that web server internally issue sessionless requests to microservices in order to do its job.
Footnote:
[*] please note that my acknowledgement of the fact that many people do this does not in any way constitute an endorsement of this practice.

any benefit from using Hazelcast instead of MongoDB to store user sessions/keys?

We are running mongodb instance to store data in a collections, no problems with it and mongo is our main data storage.
Today, we are going to develop Oauth2 support for the product and have to store the user sessions (security key, access token and etc.. ) and the access token have to be validated against the authentication server only after the defined timeout so that not every request will wait for validation by authentication server.
First request for secured resource (create) shall always be authenticated against the authentication server. Any subsequent request will be validated internally (cache) and check the internal timeout and only if expired, another request to the authentication server will be issued.
To solve that requirements, we have to introduce some kind of a distributed cache, to store (with TTL support) the user sessions and etc, expire it based on a ttl.. .i wrote about that above.
Two options here:
store user session in the hazelcast and share it across all App servers - nice choice, to persists all user session in eviction map.
store user sessions in MongoDb - and do the same.
Do you see any benefits of using Hazelcast instead of storing the temp data inside Mongo? Any significant performance improvements you're aware of ?
I'm new to Hazelcast, so don't aware about all killer features.
Disclaimer: I am the founder of Hazelcast...
Hazelcast is much simpler and simplicity matters a lot.
You can embed Hazelcast into your application (if your application is
written in Java). No need to deploy and maintain remote nosql
cluster.
Hazelcast works directly with your application objects. No
JSON or any other format. Write and read java objects.
You can
execute Java code on your in-memory data. No need to fetch and
process data; send your code over to the data.
You can listen for
the updates on your data. "Notify me when this map or key is
updated".
Hazelcast has rich set of data structures like queue,
topic, semaphores, locks, multimap etc. Imagine sharing a queue
across multiple nodes and be able to do blocking queue poll/take
operation... this is really cool :)
Hazelcast is an in-memory grid so it should be significantly faster than MongoDB for that kind of usage. They also have pre-made session clustering code for Java servlets if you do not want to create that yourself.
Code for the session clustering here on github. Or here for Maven artifact.

Spring MVC session storage

This is just the continuation of this post.
I'm coming from ASP.NET world. In ASP.NET I had a few options to store the session: "In proc" and "Out Proc" which mean the session will be serialized and stored either in database or in Session management service. This practice is also relevant to load balancing if I don't want to have my session sticky.
what is the Java/tomcat alternate solution for such cases?
How can I store out of proc session?
What is the load balancer solution?
Thank you in advance.
There is no built-in "out proc" session type for J2EE (at least, not one that is known to me). If you need to store "session" type data, but can not use the HttpSession to do so, then you will have to roll your own solution. This is likely to involve the following:
A session identifier that is stored on the client. You will want to use an identifier that is not easily spoofed if your application faces the Internet (versus an internal only app).
An API (maybe just a few classes) on the server side to retreive the session information from somewhere (perhaps a central database).
https://wiki.jasig.org/display/CAS4UM/JPA+Session+Storage

accessing php session from a command line java program

I am designing an enterprise security server for our company - we own many different applications, most written in java and a few written in PHP. I could provide a remote API that would give each application access to the server. I could also create 'agents' that each application could include that would do all the work for them, but allow my server control over their sessions and thus their authentications/authorizations. Issue is I would probably be better to write the agent in java because 80% or more of our apps are in java.
If I wrote the agent in java does anyone know if there was a way this program could access the php session? If not does anyone have a suggestion regarding a better way to go about doing this?
The session data is stored as a (php) serialized array in a temporary folder. The locations for these are set in the php.ini file.
But you can change both the format of the data and the place it is stored (e.g. to a database or shared memory or somewhere else) by writing your own handler.
A quick google suggests that several people have written [de]serializers in Java for PHP data. e.g. http://hurring.com/scott/code/java/serialize/
If you have problems with the built-in PHP serialize function - have a google for WDDX (which IIRC comes as standard) and serializes data into XML.
You might want to think about how you keep the session data appearing to be active to PHP if you want the agent to continue independently of the web session.
C.
You can hook into PHP's session handling using session_set_save_handler() (an example for a simple but complete custom handler is included in the manual). You should be able to synchronize PHP's session management with a central Java server that way.
Your PHP application would receive a session ID through a cookie ($_COOKIE["SESSION_ID"] or whatever).
Your custom session_save_handler would, instead of maintaining a session store of its own, pass that session ID to your central Java-based security server, and get all the session data in return. Writing into a session from PHP would be routed the same way.
You could of course also go the other way, and poll PHP's internal session data from the outside, but wouldn't quite understand what exactly for. If that is the case, can you go into more detail there?

Client side sessions

I want the clients of several related web apps to hold their own authentication state. This improves scalability, because no session replication between cluster nodes is needed. And it makes integration of different server technologies like Java Servlets and PHP easier.
My plan is as follows:
Set a signed and encrypted cookie with the user name and session expiration time after client authentication.
When the client sends a request, the server decrypts and validates the cookie and grants or denies access depending on the cookie values.
The session expiration will be updated through resetting the cookie.
All servers that want to use the session have only to know the cookie mechanism and the decryption key. See also: Session state in the client tier
Is this approach ok? Would it be possible to integrate it into a servlet container / application Server so that it is transparent to the applications? A servlet should be able to use HttpServletRequest#getRemoteUser() for example. Is this possible? Or would I need something above the container level like Spring Security? Are there any existing libraries for client side session management?
Not a good idea. Storing vital data like session expiry and user name entirely on client side is too dangerous IMO, encrypted or not. Even if the concept is technically safe in itself (I can't answer that in depth, I'm no encryption expert), a break-in could be facilitated without compromising your server, just by acquiring your encryption key.
Somebody who gets hold of the key could generate session cookies at will, impersonating any user for any length of time, something the classical session concept is designed to prevent.
There are better and scalable solutions for this problem. Why not, for instance, set up a central session verification instance that all associated servers and services can poll? Look around on the web, I am 100% sure there are ready-made solutions addressing your needs.
I disagree with the posters saying this approach is not secure. Variants of it are used in a number of well respected frameworks, such as Rails and Play!, for precisely the reasons you outline, and it's perfectly secure when implemented correctly.
This improves scalability, because no session replication between cluster nodes is needed.
First, using HTTP Session doesn't really prevent you from scaling, even when using HTTP Session State replication (some mechanisms are smarter than others by the way, for example WebLogic's in-memory replication doesn't have a big overhead). Second, do you really need it? Most applications (the majority) don't need Session replication. Third, am I understanding right: do you plan to not use HTTP Session at all?
(...) Set a signed and encrypted cookie with the user name and session expiration time after client authentication.
Don't do this! Don't store a username and other sensible data used by the server in a cookie, this is a very bad idea! You actually need to admit that it's just a matter of time before someone figures out how your system works and breaks it (especially if your cookie is candidate for crib attacks). Sor, really, you should store data in the Session on the server-side and only an ID in the cookie, like things are actually working. This is much more secure.
Is this approach ok?
No. And you don't need this for interoperable single-sign on (if this is what you are trying to build). Just use a centralized authentication solution like CASJasig which has libraries for various technologies.
This is not really how Sessions are implemented. The cookie itself doesn't need to carry any data of the session itself, it's just a reference to it.
What the Cookie holds is usually a Session ID which is then linked to the data on the server.
If you don't have a central data session server for the other servers to access, I suggest to get one :).
You can avoid duplication of data in a clustered environment by using a state server - a server that is well known by all the nodes in the clusters and maintains the session data for all the users. Every time a user performs a request, it send a cookie with session id to the applications server; this one should retrieve the session from the state server. This is possible for asp.net development, but I'm not sure how easy Java supports this approach.
As Pekka said, not a good idea. One can intercept your cookie with sensitive session data. Even with SSL, by using fiddler2 one can decrypt the traffic

Categories