ASP.NET 在服务器端创建缩略图

发布于 2024-08-04 09:05:41 字数 1412 浏览 2 评论 0原文

使用 System.Drawing 在 ASP.NET 应用程序中创建缩略图看起来非常容易。但是 MSDN 告诉您

不支持在 Windows 或 ASP.NET 服务中使用 System.Drawing 命名空间中的类。尝试在这些应用程序类型之一中使用这些类可能会产生意外的问题,例如服务性能下降和运行时异常。

我在这种类型的 GDI+ 代码中看到间歇性的“内存不足”错误。我开始怀疑这就是原因。

人们如何进行服务器端图像处理?任何人都可以推荐任何不会炸毁我的服务器的替代方案吗?

相关代码如下。该异常间歇性地发生在 System.Drawing.Graphics.DrawImage 中。我刚刚继承了这个项目,所以我需要检查日志以了解发生此问题的频率/我们获得异常的频率...

public byte[] Resize(int newWidth, int newHeight, Image orignalImage)
{
    Bitmap bitmap = new Bitmap(newWidth, newHeight);
    Graphics g = Graphics.FromImage(bitmap);
    g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;

    Rectangle r = new Rectangle(0, 0, newWidth, newHeight);
    g.DrawImage(orignalImage, r, r.X, r.Y, orignalImage.Width, orignalImage.Height, GraphicsUnit.Pixel);

    MemoryStream stream = new MemoryStream();
    bitmap.Save(stream, ImageFormat.Jpeg);

    // clean up memory leaks
    if (bitmap != null)
    {
        bitmap.Dispose();
        bitmap = null;
    }
    if (g != null)
    {
        g.Dispose();
        g = null;
    }


    return stream.ToArray();
}

更新:我已经搜索过整个项目中我们使用 GDI+ 的任何地方,并将 using() { } 放在所有 IDisposable 周围。自从我这样做以来,我还没有见过任何“内存不足”的异常。

It look desceptively easy to use System.Drawing to create thumbnails in your ASP.NET application. But MSDN tells you:

Classes within the System.Drawing namespace are not supported for use within a Windows or ASP.NET service. Attempting to use these classes from within one of these application types may produce unexpected problems, such as diminished service performance and run-time exceptions.

I'm seeing intermittented 'out of memory' errors within this type of GDI+ code. I'm beginning to suspect this is the cause.

How ARE people doing server side image manipulation? Can anyone recommend any alternative that WON'T blow up my server?

The relevant code below. The exception intermittently happens in System.Drawing.Graphics.DrawImage. I've just inherited this project, so I'd need to check the logs to see how often this is being hit / how often we get an exception...

public byte[] Resize(int newWidth, int newHeight, Image orignalImage)
{
    Bitmap bitmap = new Bitmap(newWidth, newHeight);
    Graphics g = Graphics.FromImage(bitmap);
    g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;

    Rectangle r = new Rectangle(0, 0, newWidth, newHeight);
    g.DrawImage(orignalImage, r, r.X, r.Y, orignalImage.Width, orignalImage.Height, GraphicsUnit.Pixel);

    MemoryStream stream = new MemoryStream();
    bitmap.Save(stream, ImageFormat.Jpeg);

    // clean up memory leaks
    if (bitmap != null)
    {
        bitmap.Dispose();
        bitmap = null;
    }
    if (g != null)
    {
        g.Dispose();
        g = null;
    }


    return stream.ToArray();
}

UPDATE: I've searched thru the whole project for anywhere we are using GDI+ and put using() { } around everything that's IDisposable. I haven't seen one 'out of memory' exception since I did this.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

梦断已成空 2024-08-11 09:05:41

假设您将对每个请求执行“操作”,问题可能是

  1. 处理器密集型操作:图像操作,这可能需要时间。

  2. 如果您正在保存文件,它将导致磁盘问题。

  3. 您可以考虑使用HTTP 处理程序,

  4. 处置 System.Drawing 对象应优先考虑(使用(){} 语句)

  5. 异步页面可以在此处探索。

Assuming you will be doing "stuff" per request, the issues might be

  1. Processor intensive operation: manipulation of images, which could take time.

  2. In case you are saving the file, it will lead to disk issues.

  3. You can consider using HTTP handlers,

  4. Disposing System.Drawing objects should be a priority(using(){} statement )

  5. Asynchronous Pages can be explored here.

爱给你人给你 2024-08-11 09:05:41

为什么不设置一个通过 Web 服务公开的单独工作服务器。

Why don't you set up a separate work server that is exposed through a web service.

天涯离梦残月幽梦 2024-08-11 09:05:41

我建议您在这些操作周围放置一些异常处理代码,以便保证您可以处理 GDI+ 对象。关闭流的好习惯...尽管据我所知 MemoryStream 对象是托管的,因此在 GC 时应该关闭自身。

I would recommend you put some exception handling code around these operations so that you're guaranteed to dispose of your GDI+ objects. Good practice to close your streams too ... although to my knowledge MemoryStream object is managed so should close itself when GC'd.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文