代码之家  ›  专栏  ›  技术社区  ›  IrishChieftain

使用HttpHandler对基于数据库的图像进行流式处理

  •  3
  • IrishChieftain  · 技术社区  · 15 年前

    很长一段时间以来,当我在本地机器上处理涉及数据库图像的Web应用程序项目时,我注意到了一些恼人的事情。说到本地,我的意思是它是一个典型的环境,在我的工作站上有VS2008和SQLServer2005。每当我使用HttpHandler在本地上显示图像时,每次加载页面时都只呈现部分图像。

    但是,当我将应用程序推送到托管环境时,问题通常会消失。然而,我刚刚将一个新项目推出到托管环境中,遇到了与本地项目相同的问题——这次站点和数据库位于托管环境中的同一台服务器上。有人知道这里发生了什么吗?

    [WebService(Namespace = "http://tempuri.org/")]
    [WebServiceBinding(ConformsTo = WsiProfiles.BasicProfile1_1)]
    public class FeaturedHandler : IHttpHandler
    {
        Business biz = new Business();
    
        public void ProcessRequest(HttpContext context)
        {
            if (context.Request.QueryString["ListingID"] != null)
            {
                int listingID = Convert.ToInt32(context.Request.QueryString["ListingID"]);
    
                DataSet ds = biz.GetFeaturedImageByID(listingID);
                DataRow row = ds.Tables[0].Rows[0];
                byte[] featureImage = (byte[])row["Photo"];
                context.Response.ContentType = "image/jpeg";
                context.Response.OutputStream.Write(featureImage, 0, featureImage.Length);
            }
            else
                throw new ArgumentException("No ListingID parameter specified");
        }
    
        public bool IsReusable
        {
            get
            {
                return false;
            }
        }
    } 
    

    更新 因为我正在读取二进制数据,所以一开始我应该使用DataReader。

    3 回复  |  直到 13 年前
        1
  •  4
  •   IrishChieftain    15 年前

    通过更改 可中断 财产 :

        public bool IsReusable
        {
            get
            {
                return true;
            }
        }
    

    显然,这会将处理程序保留在内存中,并能够处理多个请求。当设置为false时,它必须为每个传入请求创建处理程序的新实例。

        2
  •  3
  •   Branislav Abadjimarinov Ivan Choo    13 年前

    在“我的本地”上显示图像,仅在 页面加载。

    在您的情况下,通过切换来消除差异 isReusable 这是真的吗 new Business(); 可中断 新业务(); 将为每个图像调用一次。这意味着,如果每页有多个图像 新业务();

    if (context.Request.QueryString["ListingID"] != null)
    {
        int listingID = Convert.ToInt32(context.Request.QueryString["ListingID"]);
    

    与:

    string listingIdParam = context.Request.QueryString["ListingID"];
    if (listingIdParam != null)
    {
        int listingID = Convert.ToInt32(listingIdParam);
    

    这将为您保存空引用异常,这些异常通常仅在重载情况下出现。此外,上述功能还可以防止向请求提供错误的映像,尤其是在isReusable为true时。

    Business 类及其构造函数可以提供一些信息。

        3
  •  0
  •   Taliesin    15 年前

    如果您直接为图像提供服务,请不要忘记设置正确的缓存头,即etag和expires。如果你不这样做,你真的会狠狠地打击你的数据库,耗尽你的带宽。

    您将需要处理以下http头:

    • 最后修改
    • 如果没有匹配
    • 如果未修改自
    • 除非修改自

    http://code.google.com/p/talifun-web/wiki/StaticFileHandler