ASP.NET初学笔记:FileUpload控件

  • FileUpLoad控件用于用户向Web应用程序上传文件。文件上传后,可以把文件保存在任意地方,通常把文件保存在文件系统或数据库。向页面添加FileUpLoad控件会自动地为服务器的
    标签添加enctype="multipart/form-data"属性。

1.  把文件保存到文件系统

  • 以下代码页面展示了如何使用FileUpLoad控件把图片上传到应用程序。
    <%@ Page Language="C#" %> <%@ Import Namespace="System.IO" %> 无标题页



    <%# Eval("Name") %>
    效果:

    为在系统中保存文件,asp.net页面关联的Windows帐户必须有足够的权限来保存文件。

2.  把文件保存到数据库

  • 也可以用FileUpload控件把文件保存到数据库表。在数据库中保存和检索文件会给服务器增加更多压力。但是它也有些优点,首先,可以避免系统权限问题,其次,能更方便地备份信息。下面演示的是如何把Word文档保存到数据库表中。
    <%@ Page Language="C#" %> <%@ Import Namespace="System.IO" %> 无标题页


  • 效果:

    页面显示了当前在数据库中Word文档的列表。可以点击其中的文件查看文件内容。点击文档名会链接到FileHandler.ashx页面,这个文件是一个普通的HTTP处理程序文件。当有人用特定的路径请求文件时,HTTP处理程序用于执行代码。下面是FileHandler.ashx文件的代码。<%@ WebHandler Language="C#" Class="FileHandler" %> using System; using System.Web; using System.Data; using System.Data.SqlClient; public class FileHandler : IHttpHandler { const string conString = @"Server=./SQLExpress;Integrated Security=True; AttachDbFileName=|DataDirectory|FilesDB.mdf;User Instance=True"; public void ProcessRequest (HttpContext context) { context.Response.ContentType = "application/msword"; SqlConnection con = new SqlConnection(conString); SqlCommand cmd = new SqlCommand("SELECT FileBytes FROM Files WHERE Id=@Id", con); cmd.Parameters.AddWithValue("@Id", context.Request["Id"]); using (con) { con.Open(); byte[] file = (byte[])cmd.ExecuteScalar(); context.Response.BinaryWrite(file); } } public bool IsReusable { get { return false; } } } 当请求FileHandler.ashx页面时,执行了ProcessRequest()方法。该方法取得名为Id的查询字符串项,并从数据库表Files中获取匹配的记录。数据库记录包含Word文档内容字节数组。再用Response.BinaryWrite()方法把字节数组发送到浏览器。
    关于HTTP处理程序,现在还没学,上面的FileHandler.ashx页面的代码大部分都不太理解,等以后学到之方面的内容了,再回来解析一下吧。

3.  上传大文件

  • 上传大文件时,需要做一些额外工作。你可能不希望把服务器端的所有内存都消耗在容纳整个文件上。处理大文件时,需要使用多个可托管(manageable)内存块来处理文件。
    首先,为了处理大文件需要配置应用程序。有两个配置项影响着向服务器提交大文件:httpRuntime maxRequestLength和httpRuntime requestLengthDiskThreshold。maxRequestLength指定提交的表单能被服务器端接收的最大值。默认不能提交大于4MB的表单,否则会得到一个异常。如果要上传超过4MB的文件就需要更改该配置。requestLengthDiskThreshold决定如何把上表单缓存在文件系统。asp.net framework可以把大的文件缓存在文件系统中,当文件大小超过requestLengthDiskThreshold设置后,文件的余下部分被缓存在文件系统(asp.net临时文件夹中)。默认情况下,把超过80KB的提交数据缓存到文件缓存器中,可以修改requestLengthDiskThreshold来设置新的阈值(requestLengthDiskThreshold设置的值必须小于maxRequestLength设置值)。下面代码的Web配置文件设置为可以上传不超过10MB的文件,并把缓存阈值改为100kB。

     
       
     


    下面代码演示如何高效地把一个大文件存储到数据库表中。<%@ Page Language="C#" %> <%@ Import Namespace="System.IO" %> <%@ Import Namespace="System.Data" %> <%@ Import Namespace="System.Data.SqlClient" %> 无标题页

  • 在上面代码中,首先调用了AddFile()方法,该方法在包含文件名字段的数据库表Files中新增一行。然后调用StoreFile()方法,该方法把上传文件的实际字节添加到数据库中。上传文件被分成8040字节大小的块。注意在更新数据库字段FileBytes时,SQL UPDATE语句包含.WRITE字句。该代码中的页面不会在内存中装整个上传文件,上传文件以8040字节大小的块从文件系统中取出,产一块一块存入SQL Server中。
    点击文件名将执行FileHandle.aspx HTTP处理程序,该项处理程序从数据库中获取先中的文件并把它发送到浏览器。下面代码包含了这个处理程序。<%@ WebHandler Language="C#" Class="FileHandlerLarge" %> using System; using System.Web; using System.Data; using System.Data.SqlClient; public class FileHandlerLarge : IHttpHandler { const string conString = @"Server=./SQLExpress;Integrated Security=True; AttachDbFileName=|DataDirectory|FilesDB.mdf;User Instance=True"; public void ProcessRequest (HttpContext context) { context.Response.Buffer = false; context.Response.ContentType = "application/msword"; SqlConnection con = new SqlConnection(conString); SqlCommand cmd = new SqlCommand("SELECT FileBytes FROM Files WHERE Id=@Id", con); cmd.Parameters.AddWithValue("@Id", context.Request["Id"]); using (con) { con.Open(); SqlDataReader reader = cmd.ExecuteReader(CommandBehavior.SequentialAccess); if (reader.Read()) { int bufferSize = 8040; byte[] chunk = new byte[bufferSize]; long retCount; long startIndex = 0; retCount = reader.GetBytes(0, startIndex, chunk, 0, bufferSize); while (retCount == bufferSize) { context.Response.BinaryWrite(chunk); startIndex += bufferSize; retCount = reader.GetBytes(0, startIndex, chunk, 0, bufferSize); } byte[] actualChunk = new Byte[retCount - 1]; Buffer.BlockCopy(chunk, 0, actualChunk, 0, (int)retCount - 1); context.Response.BinaryWrite(actualChunk); } } } public bool IsReusable { get { return false; } } } 上面代码中的HTTP处理程序使用SqlDataReader从数据库中获取文件。注意,SqlDataReader使用CommandBehavior.SequentialAccess参数获取数据。这个参数使SqlDataReader以流的方式加载数据。数据库字段的内容以8040字节大小的块取入内存中,这些内容块用Response.BinaryWrite()方法写入浏览器。另外注意这个处理程序禁止用了响应缓存,Response.Buffer属性的值被设成False。由于禁用了缓存,处理程序输出就不会在传输到浏览器前缓在服务器端的内存中。

你可能感兴趣的:(ASP.NET学习笔记)