Disable on-demand session state in ASP.Net MVC

I am creating an ActionResult in ASP.Net MVC for serving images. When session state is turned on, IIS will only process one request at a time from the same user. (This is not only true in MVC.)

Therefore, on a page with multiple images returning this action, only one image request can be processed at a time. It is synchronous.

I would like this image to act asynchronously - I would like several image requests to be executed without having to complete the previous one. (If the images were only static files, IIS will serve them this way.)

So, I would like to disconnect a session only for calls to this action or indicate that certain requests do not have session state. Does anyone know how to do this in MVC? Thank!

+37
asynchronous asp.net-mvc actionresult session-state
Sep 23 '09 at 6:07
source share
8 answers

Instead of using an action filter for this, why don't you implement RouteHandler ?

Here's the deal - IRouteHandler has one method - GetHttpHandler . When you send an ASP.Net MVC request to the controller, by default, the routing engine processes the request, creating a new instance of MvcRouteHandler , which returns MvcHandler . MvcHandler is an implementation of IHttpHandler , which is marked by the interface (surprise!) IRequiresSessionState . This is why a regular request uses Session.

If you follow my blog post on how to implement a custom RouteHandler (instead of using MvcRouteHandler) for serving images - you can skip the return with the IHttpHandler tag.

This should free IIS from syncing up on you. It will also probably be more productive as it skips all layers of MVC code associated with filters.

+33
Sep 23 '09 at 6:29
source share
β€” -

If someone is in the situation I was in, where your graphics controller really needs read-only access to the session, you can put the SessionState attribute on your controller

 [SessionState(SessionStateBehavior.ReadOnly)] 

See http://msdn.microsoft.com/en-us/library/system.web.mvc.sessionstateattribute.aspx for details.

Thanks to https://stackoverflow.com/a/3186263

+46
Jan 09 '12 at 23:16
source share

Try using images from a different domain. So something like images.mysite.com.

This will give you two advantages: one, sessions are tracked by cookies, so images.mysite.com will not have a cookie. Two, this will give you two additional simultaneous image requests.

Have you considered setting up an HttpHandler to process your images?

+6
Sep 23 '09 at 6:11
source share

The SessionState attribute is very useful if you are using mvc3. How to achieve this using mvc2 requires a bit more coding.

The idea is to tell asp.net that the particular request is not using a session object.

So, create your own route handler for specific requests.

 public class CustomRouteHandler : IRouteHandler { public System.Web.IHttpHandler GetHttpHandler(RequestContext requestContext) { requestContext.HttpContext.SetSessionStateBehavior(System.Web.SessionState.SessionStateBehavior.ReadOnly); return new MvcHandler(requestContext); } } 

SessionStateBehavior enum has 4 members, you must use the "disabled" or "readonly" modes to get asynchronous behavior.

After creating this custom route handler, make sure your specific requests go through that handler. This can be done by defining new routes in Global.asax

 routes.Add("Default", new Route( "{controller}/{action}", new RouteValueDictionary(new { controller = "Home", action = "Index"}), new CustomRouteHandler() )); 

Adding this route makes all your requests handled by your route handler class. You can do this in a specific way by defining different routes.

+4
Feb 11 2018-12-12T00:
source share

Change the DefaultCOntrollerFactory to a custom ControllerFactory class. Default Controller.TempDataProvider uses SessionStateTempDataProvider. you can change it.

1. Set web.config / system.web / sessionState: mode = "Off".

2.create a DictionaryTempDataProvider class.

  public class DictionaryTempDataProvider : ITempDataProvider { public IDictionary<string, object> LoadTempData(ControllerContext controllerContext) { return new Dictionary<string, object>(); } public void SaveTempData(ControllerContext controllerContext, IDictionary<string, object> values) { } } 

3.Create a dictionaryTempDataControllerFactory

  public class DictionaryTempDataControllerFactory : DefaultControllerFactory { public override IController CreateController(System.Web.Routing.RequestContext requestContext, string controllerName) { var controller = base.CreateController(requestContext, controllerName) as Controller; if (controller!=null) controller.TempDataProvider = new DictionaryTempDataProvider(); return controller; } } 

4.In global.asax.cs Event Set Apprication_Start DictionaryTempDataControllerFactory.

 protected void Application_Start() { RegisterRoutes(RouteTable.Routes); ControllerBuilder.Current.SetControllerFactory( new DictionaryTempDataControllerFactory() ); } 
+3
Sep 23 '09 at 15:29
source share

I also ran into the same problem, and after doing R&D, this link worked for me. Help: https://techatfingers.wordpress.com/2016/06/14/session-state-on-action/

  • Create custom attribute
  • Override the GetControllerSessionBehavior method present in the DefaultControllerFactory class.
  • Register it in global.aspx

1> Create custom attribute

 public sealed class ActionSessionStateAttribute : Attribute { public SessionStateBehavior SessionBehavior { get; private set; } public ActionSessionStateAttribute(SessionStateBehavior sessionBehavior) { SessionBehavior = sessioBehavior; } } 

2. Override

 public class SessionControllerFactory : DefaultControllerFactory { protected override SessionStateBehavior GetControllerSessionBehavior(RequestContext requestContext, Type controllerType) { if (controllerType == null) return SessionStateBehavior.Default; var actionName = requestContext.RouteData.Values["action"].ToString(); Type typeOfRequest=requestContext.HttpContext.Request.RequestType.ToLower() =="get"?typeof(HttpGetAttribute):typeof(HttpPostAttribute); // [Line1] var cntMethods = controllerType.GetMethods() .Where(m => m.Name == actionName && ( ( typeOfRequest == typeof(HttpPostAttribute) && m.CustomAttributes.Where(a => a.AttributeType == typeOfRequest).Count()>0 ) || ( typeOfRequest == typeof(HttpGetAttribute) && m.CustomAttributes.Where(a => a.AttributeType == typeof(HttpPostAttribute)).Count() == 0 ) ) ); MethodInfo actionMethodInfo = actionMethodInfo = cntMethods != null && cntMethods.Count() == 1 ? cntMethods.ElementAt(0):null; if (actionMethodInfo != null) { var sessionStateAttr = actionMethodInfo.GetCustomAttributes(typeof(ActionSessionStateAttribute), false) .OfType<ActionSessionStateAttribute>() .FirstOrDefault(); if (sessionStateAttr != null) { return sessionStateAttr.Behavior; } } return base.GetControllerSessionBehavior(requestContext, controllerType); } 

3. Register a class in Global.asax

 public class MvcApplication : System.Web.HttpApplication { protected void Application_Start() { // --- other code --- ControllerBuilder.Current.SetControllerFactory(typeof(SessionControllerFactory)); } } 
+3
Jun 15 '16 at 8:13
source share

On our server, IIS does not even know about sessions - it is an ASP.NET stack that processes one request per session at a time. Static files, such as images, are never affected.

Is it possible that your ASP.NET application serves files instead of IIS?

+1
Sep 23 '09 at 6:36
source share

Create a new controller

Decorate the controller with [SessionState (SessionStateBehavior.Disabled)]

The refactoring code for which you want readings to be disabled for this controller.

0
Sep 27 '13 at 12:58 on
source share



All Articles