Thursday, December 18th, 2008

Flex and Flash RIA’s, Authentication, Sessions, Scalability

When the concept of Rich Internet Applications was formally introduced, it required developers to start thinking about the web a little differently. RIA's are capable of providing a much smoother user experience, but there are other design changes that we must consider as well....beyond the user interface.

One of the most obvious differences between traditional, page-based web applications and RIA's is that page-based apps generally require page refreshes, while Flex applications don't. This presents new challenges for web developers who have just started building Flex applications. Developers are now forced to change the way they think about the view state.

Traditional Use of Session Variables

In page-based apps, the view state is mostly handled on the server. This makes sense, since most user interaction requires a new request to the web server. The server processes that user interaction, determines what the new view should look like, then sends that view (HTML) back to the browser. In this scenario, it the easiest place to maintain information about a user is in a session on the server.

A typical example is in user authentication. It might go something like this:

  1. A user submits their username and password via an HTML form.
  2. Server receives the credentials and verifies them against the users in a database.
  3. If the user is valid, a session is created to store some information about this user.
  4. When requests are made from the browser, the user session info is used to help determine what HTML will be returned to the browser.

Problems with Traditional Sessions in Flex Apps

There are various scenarios that might cause a user's session to die. Sessions are usually set to expire if the app doesn't make any requests to the server for a given length of time, or the session may die if the web server requires a restart. This is fine for page-based apps. If the session expires and the browser requests a new HTML view, the server can just return a login screen notifying the user that they should log in again. Since RIAs don't require page refreshes, and we're now maintaining view state on the client, the session on the server may expire, even if the user is interacting with the application on the client. The Flex app *could* periodically make dummy requests to the server in order to keep the session alive, but this is a clunky solution and requires unnecessary traffic and load on the web server. While we *could* still kick the user back to a login screen when their session expires, we don't want this to happen if a user is actively using the application.

Another, more general, problem with sessions is that they tie your application to one web server. For example, if you are load balancing your site between multiple web servers, and you try to maintain information about a user after login using a session, then that session will only exist on the server that received the login request. The other servers won't know anything about that user's session. There are ways around this, but generally, if your app relies on sessions, then it's going to be more difficult to scale to support more users, so we'll look at a different solution.

Solution

Sessions are a quick and easy way to maintain information about a user in memory on the server, but now we're building applications that no longer require frequent page refreshes, and now we don't need to maintain the view state on the server, so it makes sense to make some adjustments.

Here is a breakdown of one possible solution:

  1. A user submits their username and password inside a Flex form.
  2. Server receives the credentials and verifies them against the users in a database.
  3. If the user is valid, a key is created, stored in the database with a time stamp, then sent back to the user.
  4. The key is stored in a local variable inside the Flex application.
  5. Now, any time the application needs to retrieve data from a service that requires the user to be logged in, it will pass the key with the request. So, instead of a method like getUserInfo(), now it will look like getUserInfo(key).
  6. The service will use the key to determine if the user is authenticated, and if they are, it will send back the appropriate data.

Obviously, if security is a priority, then SSL is a must, but that's always the case. You'll also want to make sure each key is unique in the database, and that the key is an encrypted string that someone could not easily guess (or generate).

This approach accomplishes a couple of things. First, load balancing becomes easier. It removes the need for a temporary session to be created on the server, so any web server can accept a request from the client, and can verify it against the database. Second, we don't have to worry about the risk of our session expiring unnecessarily.

If you'd like to see code or more detail about what the solution might look like, let me know, and I'll assemble an example in a future post.



You can follow any responses to this entry through the RSS 2.0 feed. You can leave a response, or trackback from your own site.

11 Responses

March 5, 2009
wobagi

Thanks for the explanation. Some example would be great, showing how the key should be used on the server side to retrieve, say, some database records for a given user and sent back to the flex app. Thanks.


March 5, 2009

I’ll see if I can get an example posted soon. Thanks Wobagi.


May 13, 2009
Latesh

Hi,
Thanks this blog is really usefull.but you have not mentioned any solution about first problem that server side session expires even if there is user active on flex client. Any solution of this problem would be great.


July 22, 2009
abdul rahman

Hi,
The solution provided was really good. Adding to Latesh, any solution to the above problem along with some code snippet would be welcomed and appreciated.
Thanks


October 4, 2009
ashil

This is a very interresting problem. Your solution sounds fine, but is not detailed at all. How about role-base requests to the server? A user has, say, administrator priviledges. He sends requests with a valid key, but how the server knows about his rights? Maybe a type of key/role? I look forward to hearing more from you about this topic. I’m currently facing the same choices, and I didn’t find a lot of resources about it on the Net.

Cheers


October 7, 2009
Derek Adams

This is great if the flex app works within it self 100% of the time. Actually, the app my company has made uses this idea exactly.

But what if the user logs in to a web page, and then clicks a link to launch the flex app in the browser? How can the browser access the login information that the user has already entered? I’ve tried to store the values in a cookie just to pull them down into the flex app, but IE (really, a problem with IE?) recently added a restriction on cross domain cookies. This presents my problem.

Suggestions?

thanks :]


November 10, 2009

Seems this approach will solve the session problem for flex ria application.

But at downside every request need to checked against database and database calls are always going to impact application response time and in case you have used encrpted key than it may take more time to get compared.

Probably, this solution will solve the problem but from performance point of view it needs some improvements.

My two cent thougts.


November 14, 2009
Eric

Didn’t think of that sulotion. Thanks!


December 10, 2009
Harshil

Great Post.
I also have a requirement for role-based type requests. How would server make sure of the rights associated to that user?

The solution maybe to store both the key and Permission level associated with the user credentials. So all subsequent requests from the Flex Client app pass the key to the server, and server does 1) verfies the key 2) verifies the permission level to have access for the requested service.

Comments appreciated.


January 11, 2010
Camille

Hi,

I’ve been searching for a good Login/Authentication outline using Flex and CF for a while, and yours is the best.

Could you please send some examples and/or a zip file.

Thanks.


February 1, 2010
flexbee

I guess, its a big performance hit not just becauz of the DB calls involved but also with the SSL for every request. There must be a better wrapper..!