【问题标题】:How to get a valid HttpContextBase inside of a Task如何在任务中获取有效的 HttpContextBase
【发布时间】:2013-01-21 04:25:13
【问题描述】:

以下代码在访问对应的url时会抛出异常。 StartNew() 中的对象 stateProcessRequest 中的 ctx 不同。为什么会这样?如何在StartNew() 旁边获取有效的HttpContextBase 对象?

using System.Web;
using System.Web.Routing;

namespace AsyncUseHttpContextBaseWillFail
{
    public class FooHandler : IHttpHandler
    {
        public void ProcessRequest(HttpContext context)
        {
            var ctx = new HttpContextWrapper(context);
            System.Threading.Tasks.Task.Factory.StartNew(state =>
            {
                //ArgumentException: Value does not fall within the expected range.
                var ip = ((HttpContextBase)state).Request.UserHostAddress;
            }, ctx);
        }

        public bool IsReusable
        {
            get { return false; }
        }
    }

    public class RouteConfig
    {
        public static void RegisterRoutes(RouteCollection routes)
        {
            routes.Add(new Route(string.Empty, new FooRoute()));
        }
    }

    public class FooRoute : IRouteHandler
    {
        public virtual IHttpHandler GetHttpHandler(RequestContext context)
        {
            return new FooHandler();
        }
    }
}

【问题讨论】:

标签: .net asp.net-mvc .net-4.0 task-parallel-library


【解决方案1】:

Steve 上面的评论是让这项工作正常工作的最佳选择。使用 IHttpAsyncHandler 或 HttpTaskAsyncHandler。即使您确实设法将有效的 HttpContext[Base] 传递到您的回调中,如果 ProcessRequest 已经返回,那么 ASP.NET 运行时可能已经清理了 HttpContext 实例,并且您将尝试使用已释放的对象。异步工作应始终由异步处理程序执行,以避免此问题。

【讨论】:

    【解决方案2】:

    将所需数据从HttpContext 复制到局部变量并在您的 lambda 中使用这些变量。从第二个线程访问HttpContext 是不安全的。

    【讨论】:

      猜你喜欢
      • 2014-04-29
      • 2011-07-04
      • 1970-01-01
      • 2010-12-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-09-21
      • 1970-01-01
      相关资源
      最近更新 更多