首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 开发语言 > 编程 >

用 Servlet 进行下载的原理和实现

2012-08-25 
用 Servlet 进行上载的原理和实现? 在页面中显示如下(可能随浏览器不同而不同)可以直接在文本框中输入文件

用 Servlet 进行上载的原理和实现

?

在页面中显示如下(可能随浏览器不同而不同)

可以直接在文本框中输入文件名,也可以点击按钮后弹出供用户选择文件的对话框。

B)浏览器编码

在向服务器端提交请求时,浏览器需要将大量的数据一同提交给 Server端, 而提交前,浏览器需要按照 Server端可以识别的方式进行编码,对于普通的表单数据,这种编码方式很简单,编码后的结果通常是field1=value2&field2=value2&… 的形式,如name=aaaa&Submit=Submit。这种编码的具体规则可以在 rfc2231里查到, 通常使用的表单也是采用这种方式编码的,Servlet 的 API提供了对这种 编码方式解码的支持,只需要调用 ServletRequest类中的方法就可以得到 用户表单中的字段和数据。

这种编码方式( application/x-www-form-urlencoded)虽然简单,但对于传输大块的二进制数据显得力不从心,对于传输这类数据,浏览器采用了另一种编码方式,即 "multipart/form-data"的编码方式,采用这种方式,浏览器可以很容易的表单内的数据和文件一起。这种编码方式先定义好一个不可能在数据中出现的字符串作为分界符,然后用它将各个数据段分开,而对于每个数据段都对应着 HTML 页面表单中的一个 Input 区,包括一个 content-disposition属性,说明了这个数据段的一些信息,如果这个数据段的内容是一个文件,还会有 Content-Type属性,然后就是数据本身。 这里,我们可以编写一个简单的 Servlet来看到浏览器到底是怎样编码的。

实现流程:

重载 HttpServlet 中的 doPost 方法调用 request.getContentLength() 得到 Content-Length,并定义一个与 Content-Length 大小相等的字节数组 buffer 。从HttpServletRequest 的实例 request 中得到一个 InputStream,并把它读入 buffer 中。使用 FileOutputStream 将 buffer 写入指定文件。


代码清单

?

C)提交请求

提交请求的过程由浏览器完成的,并且遵循 HTTP 协议,每一个从浏览器端到服务器端的一个请求,都包含了大量与该请求有关的信息, 在Servlet 中,HttpServletRequest 类将这些信息封装起来,便于我们提取使用。在文件上载和表单提交的过程中,有两个指的关心的问题,一是上载的数据是是采用的那种方式的编码,这个问题的可以从 Content-Type中得到答案,另一个是问题是上载的数据量有多少即 Content-Length ,知道了它,就知道了 HttpServletRequest 的实例中有多少数据可以读取出来。这两个属性,我们都可以直接从 HttpServletRequest 的一个实例中获得,具体调用的方法是 getContentType() 和 getContentLength()。

Content-Type 是一个字符串,在上面的例子中,增加

具体解码过程也可以分为两个步骤:

将上载的数据分解成数据段,每个数据段对应着表单中的一个 Input区。对每个数据段,再进行分解,提出上述要求得到的内容。

这两个步骤主要的操作有两个,一个是从一个数组中找出另一个数组的位置,类似于 String 类中的 indexOf 的功能,另一个是从一个数组中提取出另一个数组, 类似于 String 类中的 substring 的功能,为此我们可以专门写两个方法,实现这种功能。

假设我们已经将数据存入字节数组 buffer 中,分界符存入 Stringboundary 中

byte[] getBytes ()
返回一个文件内容的字节数组 java.lang.String getContentType () 返回该文件的 Content-Type java.lang.String getFileName ()
返回该文件在文件上载前在客户端的名称 java.lang.String getParameterName ()
返回上载该文件时,Html 页面窗体中 file 控件的 name 属性 void saveTo (java.io.Filefile)
把文件的内容存到指定的文件中 void saveTo (java.lang.Stringname)
把文件的内容存到指定的文件中

ContentFactoryException
在 ContentFactory.getContentFactory 方法中可能抛出。
各类的源文件详解代码清单。

四、使用示例

附录中包含了一个 Servlet 示例,该示例重载了 HttpServlet的两个方法 ( doGet, doPost ),在浏览器发送 GET请求时,产生一个表单,在用户提交表单时,将文件和数据上载,并在浏览器端显示出上载文件存盘后的 URL ,以及页面中的各字段的 name 和 value。该示例及各类在Windows98、jdk1.3和tomcat3.1,浏览器为IE5和Opera3.6的环境下调试通过。

热点排行