【问题标题】:HTTP Handler async issue .NET 4.5.2HTTP 处理程序异步问题 .NET 4.5.2
【发布时间】:2016-12-16 12:49:16
【问题描述】:

我正在将 .NET 4.5.2 用于 Web 应用程序,并且我有一个返回处理后图像的 HTTP 处理程序。我正在使用 jQuery 对进程处理程序进行异步调用,并且开始出现以下错误:

此时无法启动异步操作。异步操作只能在异步处理程序或模块内或在页面生命周期中的某些事件期间启动。如果在执行页面时发生此异常,请确保将页面标记为 。此异常还可能表示尝试调用“async void”方法,在 ASP.NET 请求处理中通常不支持该方法。相反,异步方法应该返回一个 Task,调用者应该等待它。

这是处理程序代码:

       public void ProcessRequest(HttpContext context)
    {
        string CaseID = context.Request.QueryString["CaseID"].ToString();
        int RotationAngle = Convert.ToInt16(context.Request.QueryString["RotationAngle"].ToString());
        string ImagePath = context.Request.QueryString["ImagePath"].ToString();

        applyAngle = RotationAngle;

        string ImageServer = ConfigurationManager.AppSettings["ImageServerURL"].ToString();
        string FullImagePath = string.Format("{0}{1}", ImageServer, ImagePath);

        WebClient wc = new WebClient();
        wc.DownloadDataCompleted += wc_DownloadDataCompleted;
        wc.DownloadDataAsync(new Uri(FullImagePath));
    }

    private void wc_DownloadDataCompleted(object sender, DownloadDataCompletedEventArgs e)
    {
        Stream BitmapStream = new MemoryStream(e.Result);

        Bitmap b = new Bitmap(BitmapStream);
        ImageFormat ImageFormat = b.RawFormat;

        b = RotateImage(b, applyAngle, true);

        using (MemoryStream ms = new MemoryStream())
        {
            if (ImageFormat.Equals(ImageFormat.Png))
            {
                HttpContext.Current.Response.ContentType = "image/png";
                b.Save(ms, ImageFormat.Png);
            }

            if (ImageFormat.Equals(ImageFormat.Jpeg))
            {
                HttpContext.Current.Response.ContentType = "image/jpg";
                b.Save(ms, ImageFormat.Jpeg);
            }
            ms.WriteTo(HttpContext.Current.Response.OutputStream);
        }
    }

知道这意味着什么,我可以做些什么来克服它吗?

提前致谢。

【问题讨论】:

  • 克服什么?代码在哪里?你是怎么做的?
  • 你的 handler 代码。 jQuery 与 HTTP 处理程序无关,它只在浏览器上运行。
  • 已添加代码,请查看。
  • 请提供完整的例外情况。错误发生在哪里?在哪条线上?你试过调试这个吗?您可以使用Exception.ToString() 获取完整的异常和调用堆栈。如果您没有日志记录,请添加它。我怀疑一旦你找到哪条线抛出你自己就会发现问题
  • 您是否尝试在服务器端代码中使用本地 Web 客户端和事件?这个变量将在ProcessRequest 完成后立即释放!无论如何,即使是 WebClient 也有真正的异步方法,即DownloadDataTaskAsync。你不应该将事件用于异步操作,这是 .NET 2 的遗留物

标签: asp.net httphandler


【解决方案1】:

您的代码不会按原样工作,因为您在 ProcessRequest 方法中创建了一个 WebClient,但不要等待它完成。因此,一旦方法完成,客户端将成为孤立的。当响应到达时,请求本身已经完成。没有可以写入响应的上下文或输出流。

要创建异步 HTTP 处理程序,您需要从 HttpTaskAsyncHandler 类派生并实现 ProcessRequestAsync 方法:

public class MyImageAsyncHandler : HttpTaskAsyncHandler
{

   public override async Task ProcessRequestAsync(HttpContext context)
   {
      //...
      using(WebClient wc = new WebClient())
      {
          var data=await wc.DownloadDataTaskAsync(new Uri(FullImagePath));        
          using(var BitmapStream = new MemoryStream(data))
          {
              //...
              ms.WriteTo(context.Response.OutputStream);
             //...
          }
      }
   }
}

【讨论】:

  • 感谢 Panagiotis Kanavos
猜你喜欢
  • 2011-10-29
  • 2010-10-07
  • 1970-01-01
  • 2021-02-18
  • 1970-01-01
  • 1970-01-01
  • 2018-09-28
  • 1970-01-01
相关资源
最近更新 更多