繁体   English   中英

处理大型下载网站的最佳方式?

[英]Best way to handle a large download site?

我目前在我的学校有一个基于.net的下载站点。 我们提供防病毒,autocad,spss,办公室以及许多大型应用程序供学生下载的任何内容。 它目前设置为以两种方式之一处理它们; 任何超过800兆的东西都可以通过一个单独的网站直接访问,而800兆以下的数据是使用文件流在.net代码后面保护的,以10000字节的形式将其提供给用户。 我有这种方式提供下载的各种问题......我希望能够保证大量下载,但.net网站无法处理它,而较小的文件通常会失败。 有更好的方法吗?

编辑 - 我只想更新我最终如何解决这个问题:我最终将我的下载目录添加为iis中的虚拟目录并指定了自定义http处理程序。 处理程序从请求中获取文件名并根据该权限检查权限,然后将用户重定向到错误/登录页面,或让下载继续。 我对这个解决方案没有任何问题,我已经使用了大概7个月了,为文件提供了几个大小的演出。

如果您遇到性能问题并且正在提供文件系统上存在的文件(而不是数据库),请使用HttpResponse.TransmitFile函数。

至于失败,你可能有一个错误。 如果你发布代码,你可能会有更好的回应。

看看比特洪流。 它专为此类设计而设计,非常灵活。

我有两个建议:

  • 增加缓冲区大小,以减少迭代次数

AND / OR

  • 不要在每次迭代时调用IsClientConnected。

原因是根据Microsoft指南

Response.IsClientConnected有一些成本,所以只能在至少花费500毫秒的操作之前使用它(如果你试图维持每秒几十页的吞吐量,那就很长了)。 作为一般经验法则,不要在紧密循环的每次迭代中调用它

使用强大的Web服务器(如Apache)并让它处理文件是错误的。 正如您现在将较大的文件分离到Web服务器一样,为什么不以相同的方式提供较小的文件?

是否有一些隐藏的要求来防止这种情况?

好的,这就是它目前的样子......

    Stream iStream = null;

// Buffer to read 10K bytes in chunk:
byte[] buffer = new Byte[10000];

// Length of the file:
int length;

// Total bytes to read:
long dataToRead;

if (File.Exists(localfilename))
{
    try
    {
        // Open the file.
        iStream = new System.IO.FileStream(localfilename, System.IO.FileMode.Open, System.IO.FileAccess.Read, System.IO.FileShare.Read);

        // Total bytes to read:
        dataToRead = iStream.Length;

        context.Response.Clear();
        context.Response.Buffer = false;
        context.Response.ContentType = "application/octet-stream";
        Int64 fileLength = iStream.Length;
        context.Response.AddHeader("Content-Length", fileLength.ToString());
        context.Response.AddHeader("Content-Disposition", "attachment; filename=" + originalFilename);

        // Read the bytes.
        while (dataToRead > 0)
        {
            // Verify that the client is connected.
            if (context.Response.IsClientConnected)
            {
                // Read the data in buffer.
                length = iStream.Read(buffer, 0, 10000);

                // Write the data to the current output stream.
                context.Response.OutputStream.Write(buffer, 0, length);

                // Flush the data to the HTML output.
                context.Response.Flush();

                buffer = new Byte[10000];
                dataToRead = dataToRead - length;
            }
            else
            {
                //prevent infinite loop if user disconnects
                dataToRead = -1;
            }
        }
        iStream.Close();
        iStream.Dispose();
    }
    catch (Exception ex)
    {
        if (iStream != null)
        {
            iStream.Close();
            iStream.Dispose();
        }
        if (ex.Message.Contains("The remote host closed the connection"))
        {
            context.Server.ClearError();
            context.Trace.Warn("GetFile", "The remote host closed the connection");
        }
        else
        {
            context.Trace.Warn("IHttpHandler", "DownloadFile: - Error occurred");
            context.Trace.Warn("IHttpHandler", "DownloadFile: - Exception", ex);
        }
        context.Response.Redirect("default.aspx");
    }
}

存在许多许可限制......例如,我们有Office 2007许可协议,该协议表明校园内的任何技术人员都可以下载和安装Office,但不能学生。 所以我们不要让学生下载它。 所以我们的解决方案是将这些下载隐藏在.net之后。

Amazon S3听起来非常适合您的需求,但它是商业服务,文件服务器提供服务。

您应该尝试联系亚马逊并要求学术定价。 即使他们没有。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM