What's the difference between HttpSession object and HttpContext object? - servlets

I am learning Servlet. But don't understand the major difference between HttpSession object and HttpContext object ? As both are used to keep track of the user. But I don't understand , are both of them being accessible across the user or servlet ?
Can anyone provide me an example for this, so I can have clear understanding of it...

Request - Normally used for passing data from jsp to your servlet when you submit the form. When you get redirected to another jsp, your request dies. ie: this attribute lives per user request.please note that http is stateless protocol.so the server will treat every http request as a new request.
Session -session object is basically used to store the values in the session.the data will be preserved until the user terminates the program or closes the browser.Good example will be for storing user credentials. once user is authenticated, Sometimes you may want to check if the user has right access to do on some database operations like add/delete/edit. Once user closes the browser or the session goes idle for x amount minutes (depending on your server setup), the session dies and all info in it will be gone.
Context -context object can be used for multiple users and across multiple browsers.
If it is application specific, consider using context.
If it is user specific, consider using session.
If it is request specific (ex: jsp form submission), consider using request.
Hope this helps.

Related

Could we save and load the ASP.NET InProc session (hence releasing the lock) around long running external calls

In ASP.NET when you have 2 AJAX requests on the same web page calling 2 controller actions, if they use the session then one will lock out the other
You can get readonly access to the session which can help, but not if you want to write to the session
You can override the session class, e.g.
https://www.red-gate.com/simple-talk/dotnet/asp-net/single-asp-net-client-makes-concurrent-requests-writeable-session-variables/, but this doesn't really help for the same reason
In my case the controller action calls a long running external server call. While this is happening ideally the session would be released and saved back to memory, and then when the call is finished the session would be read back in, possibly being blocked if another call is still proceeding
NB Whether or not the external server call is called in an async manner makes no difference unfortunately
Is there any way of doing this? Possibly by overriding some internal classes?

Why do we need request.getSession(true)?

When I first started learning J2EE, I was told that, we need to call request.getSession(true) to create a new session. But when I started testing HttpSessionListener, I found that the servlet container will create a HttpSession as soon as it receives a Http request from the client - before I explicitly try to create any session. Is the servlet container implicitly calling request.getSession() or request.getSessioin(true) to create a new session from me?
The only scenario where I found the getSession(true) to be useful is when I want to explicitly invalidate the existing session and create a new one. Is this the only real world scenario or are there any other examples?
But when I started testing HttpSessionListener, I found that the servlet container will create a HttpSession as soon as it receives a Http request from the client - before I explicitly try to create any session
I don't know how you tested it, but unfortunately it is not true. Try to create very simple servlet and put there:
System.out.println("Session: " + request.getSession(false));
you will see that session is null. Container doesn't create sessions, if it is not requested by your application.
You probably got that impression testing jsp pages, or some framework, which by default create session. But this can also be disabled using <%# page session="false" %>, if your page doesn't need session.
And regarding need of request.getSession(true) - you could say it is not needed as request.getSession() does exactly the same, however request.getSession(false) is needed to check, if there is a valid session associated with request.

Session state access in Web API across domains

I have a ASP.Net API implementation, where to store and access the data / variables across consecutive calls, I am using a session state object as shown below and it can be successfully accessed in the multiple calls to separate calls by a browser:
// Access the current session object
var blSession = HttpContext.Current.Session;
// create the BL object using the user id
BL accessBL = new BL(userID);
// Store the Bl object in the session object dictionary
blSession["UserBL"] = accessBL;
I have to enable the following setting in the Global.asax, for the Session object to be accessible:
protected void Application_PostAuthorizeRequest()
{
// Enable session state in the web api post authorization
HttpContext.Current.SetSessionStateBehavior(SessionStateBehavior.Required);
}
Issue comes in when the WebAPI shown above has to be accessed via another ASP.Net MVC client, which is separately hosted on a different machine, at that time same consecutive calls do not maintain the state as shown above and thus it leads to an exception, since the consecutive calls rely on session data to proceed.
I have seen a similar issue when I seen the similar issue when I use the Fiddler Debugger, as it gets hosted as a web proxy, so consecutive calls through that too fails, since it does not maintain the state. In my understanding, issue is due to setting the Cookie across domain, which doesn't seem to work across domains due to security reason
I know a workaround is to use an application wide variable like Cache, but please suggest if you have a way to get the SessionState work. Let me know if you need more details.
If you have not setup an alternative way to do SessionState, then the default behavior is to do it InMemory on the server. This is why you are seeing issues when the request is handled by a different ASP.NET server.
Web API calls are meant to be stateless. That is, they should not perform like a classic ASP.NET application that relies on the framework to store user specific information in Session variables across HTTP requests. For each call, pass in a user-specific identifier or token that you can then use to lookup information stored in your backend. You can store this information in your database or a distributed cache like MemCache for faster retrieval.

Is there a way to get the HttpContext.User.Identity from the Session?

I want to run some database processing when a user's session expires, but I need to know what user it was whose session expired.
I was considering simply setting the Session["CurrentUserId"] upon login which could then be accessed when the session expires, but thought there might be a way of getting the HttpContext.User.Identity directly from the Session?
Well, looking at the class definition on MSDN, it doesn't looks like you can access it right from a Session's property / member.
However, They are both properties of the same object, which in your case is going to be the current HttpContext. So when the session ends for one context (understand : one http request), the current user of the context is the same as the one you are looking for.
Otherwise, you could always use a hashtable stored in cache where the key would be the Session.SessionId and the value would be the User identity.

ASP.NET MVC: how to prevent a session lock?

I've an application which has some controller's actions calling slow 3rd party web services. These actions are called using AJAX calls from the page.
I can use async controllers to free ASP.NET thread pool, that's great. But what about session? If I use InProc session and a request made to "slow action" the particular user can't make any request to the application because his session is locked by first "slow" call.
In PHP there is a method session_write_close() which I can use as following:
Accept user's request to slow action
Check rights of the user to access controller/action based on session data
Write something to the session if needed
Call session_write_close(). From this point session is closed by this request and any other request from the same user can access it
Make my slow call (maybe in some async way)
I know that I can disable session state on the controller level using [SessionState] attribute, but that's not the solution.
Any ideas?
I think it could be several scenarios.
1) make changes in controller factory and change it to produce contorllers without session or with some custome session implementation
2) try to read this article about sessionless controllers

Resources