抓住上传到大文件

时间:2009-11-27 10:50:02

标签: asp.net error-handling file-upload

Asp.Net有文件上传的上限。我试图在服务器端捕获这种情况。根据我发现的文档,应该可以覆盖Global.asax中的Application_Error,但它对我不起作用。第二个选项是覆盖接收页面的OnError,但这也不起作用。

任何人都可以在服务器端显示一些有关如何捕获此错误的工作代码吗?

5 个答案:

答案 0 :(得分:2)

将以下内容放入Global.asax.cs:

void Application_Error(Object sender, EventArgs e)
        {
            HttpException ex = Server.GetLastError() as HttpException;
            if (ex != null)
            {
                if ((ex.GetHttpCode() == 500 || ex.GetHttpCode() == 400) && ex.ErrorCode == -2147467259)
                {
                    Server.ClearError();
                    Response.Redirect("~/MaximumFileError.aspx", false);
                }
            }
        }

这对我有用,但我不确定它是否适用于所有情况。

答案 1 :(得分:1)

Uploadify是一个jquery和flash上​​传器,允许您指定要下载的文件的最大大小。通过这种方式,您可以防止用户首先下载文件,而不必担心在以后删除文件。

答案 2 :(得分:0)

而不是捕获错误,你不能检查文件的大小是否符合web.config文件中指定的最大大小?您可以使用以下内容获取最大尺寸:

System.Configuration.Configuration config = WebConfigurationManager.OpenWebConfiguration("~");
HttpRuntimeSection section = config.GetSection("system.web/httpRuntime") as HttpRuntimeSection;
double maxFileSize = section.MaxRequestLength;

答案 3 :(得分:0)

  

“任何人都可以展示一些工作代码   如何在服务器上捕获此错误   侧?“

不。使用代码来捕获此错误是不可能的,因为它发生在任何代码启动之前。

据我所知,您甚至无法为此错误指定备用错误页面,Web服务器只是在它太大时拒绝接受请求。

答案 4 :(得分:0)

首先,你应该了解一些关于maxRequestLength的事情。使用服务器端方法验证,您无法预测文件大小。将值设置为高会增加DoS攻击的风险。 我将web.config maxRequestLength设置为8MB:

 <httpRuntime maxRequestLength="8192" executionTimeout="3600" />

如果用户文件上传的内容不超过maxRequestLength中给出的一半,我会检查表单的代码隐藏,但如果上传文件的大小超过web中指定的最大RequestLength,则可能永远不会发生此检查.config,因为会抛出异常。这种例外应该是Global.asax的水平。在那里,我检查Exception是否包含识别我们问题的单词,因为在许多其他情况下可能会抛出System.Web.HttpUnhandledException!好的提示可能是检查异常来自哪个页面,以确保我们处理某种形式,重要的是将用户重新定向到表单。

void Application_Error(object sender, EventArgs e){  
Exception wyjatek = Server.GetLastError();
        if (wyjatek.InnerException != null && wyjatek.InnerException.Message.Contains("Maximum request length exceeded"))
        {
            Server.ClearError();
            Response.Redirect("FormWithFile.aspx?alert=Za-duzy-plik");
        }  
    }

如果我在Global.asax中识别此异常,我会将用户重定向到带有警报的页面(在GET中给出)。

在ASPX页面的代码隐藏中:

首先,我通过这个树线从web.config中检索MaxRequestLength的值,并将其一半:

static System.Configuration.Configuration config = WebConfigurationManager.OpenWebConfiguration("~");
static HttpRuntimeSection section = config.GetSection("system.web/httpRuntime") as HttpRuntimeSection;
int maxFileSize = (section.MaxRequestLength/2)*1024; 

然后在与插入按钮连接的Action中,我按以下步骤操作:

  protected void InsertButton_Click(object sender, EventArgs e)
        {
            if (((FileUpload)FormView1.FindControl("FileUpload1")).HasFile) // WHEN USER WANT TO UPLOAD FORM WITH FILE (its, optional)
            {
                HttpPostedFile file = (HttpPostedFile)(((FileUpload)FormView1.FindControl("FileUpload1")).PostedFile);
                int iFileSize = file.ContentLength;
                if ((file != null) && (file.ContentLength > 0))
                {
                   if (iFileSize > maxFileSize) // checking image SIZE!
                    { 
                        MessageForUser.Text = "<h1 class=error>Bad File! File is to big!</h1>";
                    }
                    else
                    {
                        byte[] plik = ((FileUpload)FormView1.FindControl("FileUpload1")).FileBytes;
              // HERE COMES CODE FOR INSERT OF FORM WITH FILE
                        MessageForUser.Text = "<h1>Insert was sucessfull</h2>";
                    }
                }
            }
            else
            {
              // HERE COMES CODE FOR INSERT OF FORM WITHOUT FILE
                MessageForUser.Text = "<h1>Insert was sucessfull</h2>";
        }
    }

在Page_Load中,我还定义了如何从Global.asax中检索GET给出的通信,以告知用户发生了什么。

 if (Request.QueryString["alert"]!=null)
            {
                string temp =  Request.QueryString["alert"].Replace('-',' ');
                MessageForUser.Visible = true;
                MessageForUser.Text = "<h1 class=error>ERROR: " + temp + "</h1>";
            }   

这个解决方案当然有它的缺点:

  1. 但是,我们可以使用8MB文件进行DoS攻击,我们首先在服务器级别识别,已经很晚了。
  2. 在从Global.asax重定向的情况下,用户表单的状态会丢失,但可以克服一些代码。
  3. 用户经验相当差,因为服务器端的检查,以及许多用户的负载,应用程序可能会变慢。
  4. 临时到服务器来的文件甚至大于8MB,但是这样管理在executionTimeout
  5. 可能的替代方案:

    1. 使用某些闪存技术在客户端检查文件大小
    2. 使用一些流技术,以小数据包传输叮咬,此时,当达到阈值时,抛出自己的异常并处理它。 适当的阅读:Sending File in Chunks to HttpHandler