HttpServletResponse的应用

 准备实验环境

  1. 为支持Servlet 2.4和JSP 2.0 ,使用Tomcat 5.5.12作为运行环境。
  2. 在Tomcat 5.5.12的\webapps目录中创建一个名为it315的子目录。
  3. 在it315目录中创建一个名为test.html的网页文件,在该文件中写上“中文测试页面”这几个字符。
  4. \webapps\it315目录中创建一个名为WEB-INF的子目录。
  5. 在保存Servlet源文件的目录中编写compile.bat编译工具

set PATH=C:\jdk1.5.0_01\bin;%path%

set CLASSPATH=C:\tomcat-5.5.12\common\lib\servlet-api.jar;%CLASSPATH%    

javac -d C:\tomcat-5.5.12\webapps\it315\WEB-INF\classes %1

pause

HttpServletResponse的简介

WEB服务器回送给WEB客户端的HTTP响应消息分为三个部分:

ü  状态行

ü  响应消息头

ü  消息正文(也叫实体内容)

Servlet API中定义的ServletResponse接口类用于创建响应消息。

HttpServletResponse是专用于HTTP协议的ServletResponse子接口,它用于封装HTTP响应消息。

HttpServletResponse定义了一系列用于描述各种HTTP状态码的常量。

在service()方法内部调用HttpServletResponse对象的各种方法来创建响应消息。

产生响应状态行

HTTP响应消息的响应状态行包括HTTP版本、状态代码和一条相关的提示信息:

       HTTP/1.1 200 OK

HttpServletResponse中定义了若干与状态码数值对应的常量,每个常量的名称以前缀SC(Status Code的简写)开头,然后是状态码在HTTP 1.1规范中所表示的状态信息的英文单词的组合,每个单词之间用下划线连接,且所有字母都大写。

       状态码404 对应的常量为HttpServletResponse.SC_NOT_FOUND 

setStatus方法用于设置HTTP响应消息的状态码,并生成响应状态行。

sendError方法用于发送表示错误信息的状态码(一般是404,找不到客户机所请求的资源)到客户端,并清除缓冲区中的内容。

(用常量便于记忆,说实在话,英文单词也记不住,但是,用开发工具的提示功能,我们可以挑选出来,这就像指证罪犯时,自己回忆不出罪犯的像貌,但可以从一堆嫌疑人中指出来。)

构建响应消息头

addHeader与setHeader方法

addIntHeader与setIntHeader方法

addDateHeader与setDateHeader方法

setContentLength方法

setContentType方法  (*)

setCharacterEncoding方法   (*)

setLocale方法

      

              zh_CN

              GB2312

      

containsHeader方法

响应消息头的实用案例

Servlet的中文输出问题

让浏览器定时刷新网页

禁止浏览器缓存当前文档内容

使用标签模拟响应消息头

(printWriter用于把unicode字符串转换成某种编码的字节流,jdk1.4中的PrintWriter的设计缺陷,嘿嘿!故意不加charsert=GB2312,显示的结果立马为?

setContentType方法有两个作用:一个是把字符以什么码输出,iso里就没有汉字,所以,不能以iso输出汉字;一个告诉浏览器,输出的内容是什么码。)

Servlet的中文输出问题à原理

浏览器接收到的中文字符并不是中文符号本身,而是它的某种字符集编码的数据。

浏览器必须使用正确的字符集编码进行查看,才能将它所接收到的数据显示为正确的中文字符。

当Servlet程序仅仅需要输出纯文本格式的响应正文时,通常应调用ServletResponse对象的getWriter方法返回一个PrintWriter对象,然后使用这个PrintWriter对象将文本内容写入到客户端。

Java程序中的字符文本在内存中是以unicode编码的形式存在的,PrintWriter对象在输出字符文本时,需要先将它们转换成其他某种字符集编码的字节数组后输出。

ServletResponse对象的getWriter方法返回的PrintWriter对象默认使用ISO8859-1字符集编码进行Unicode字符串到字节数组的转换,由于ISO8859-1字符集中根本就没有中文字符,Unicode编码的中文字符将被转换成无效的字符编码后输出给客户端。 

Servlet的中文输出问题à解决办法

ServletResponse接口中定义了setCharacterEncoding、setContentType和setLocale等方法来指定ServletResponse.getWriter方法返回的PrintWriter对象所使用的字符集编码。

调用ServletResponse接口中定义的setContentType方法,在HTTP响应消息的Content-Type头字段中指定响应正文的字符集编码。  

getOutputStream与getWriter方法

getOutputStream方法用于返回Servlet引擎创建的字节输出流对象,Servlet程序可以按字节形式输出响应正文。

getWriter方法用于返回Servlet引擎创建的字符输出流对象,Servlet程序可以按字符形式输出响应正文。

getOutputStream和getWriter这两个方法互相排斥,调用了其中的任何一个方法后,就不能再调用另一方法。 

getOutputStream方法返回的字节输出流对象的类型为ServletOutputStream,它可以直接输出字节数组中的二进制数据。

getWriter方法将Servlet引擎的数据缓冲区包装成PrintWriter类型的字符输出流对象后返回,PrintWriter对象可以直接输出字符文本内容。

Servlet程序向ServletOutputStream或PrintWriter对象中写入的数据将被Servlet引擎获取,Servlet引擎将这些数据当作响应消息的正文,然后再与响应状态行和各响应头组合后输出到客户端。

Serlvet的service方法结束后,Servlet引擎将检查getWriter或getOutputStream方法返回的输出流对象是否已经调用过close方法,如果没有,Servlet引擎将调用close方法关闭该输出流对象。   

选择getOutputStream和getWriter方法的要点

PrintWriter对象输出字符文本内容时,它内部还是将字符串转换成了某种字符集编码的字节数组后再进行输出,使用PrintWriter对象的好处就是不用编程人员自己来完成字符串到字节数组的转换。

使用ServletOutputStream对象也能输出内容全为文本字符的网页文档,但是,如果网页文档内容是在Servlet程序内部使用文本字符串动态拼凑和创建出来的,则需要先将字符文本转换成字节数组后输出。

如果一个网页文档内容全部为字符文本,但是这些内容可以直接从一个字节输入流中读取出来,然后再原封不动地输出到客户端,那么就应该使用ServletOutputStream对象直接进行输出,而不要使用PrintWriter对象进行输出。    

输出缓冲区

Servlet程序输出的HTTP消息的响应正文首先被写入到Servlet引擎提供的一个输出缓冲区中,直到输出缓冲区被填满或者Servlet程序已经写入了所有的响应内容,缓冲区中的内容才会被Servlet引擎发送到客户端。

使用输出缓冲区后,Servlet引擎就可以将响应状态行、各响应头和响应正文严格按照HTTP消息的位置顺序进行调整后再输出到客户端。

如果在提交响应到客户端时,输出缓冲区中已经装入了所有的响应内容,Servlet引擎将计算响应正文部分的大小并自动设置Content-Length头字段。

如果在提交响应到客户端时,输出缓冲区中装入的内容只是全部响应内容的一部分, Servlet引擎将使用HTTP 1.1的chunked编码方式(通过设置Transfer-Encoding头字段来指定)传输响应内容。

输出缓冲区à有关方法

setBufferSize方法

getBufferSize方法

flushBuffer方法

reset方法

isCommitted方法

 

如何实现动态文件内容的下载

需要通过HttpServletResponse.setContentType方法设置Content-Type头字段的值为浏览器无法使用某种方式或激活某个程序来处理的MIME类型,例如,“application/octet-stream”或“application/x-msdownload”等。

需要通过HttpServletResponse.setHeader方法设置Content-Disposition头的值为“attachment; filename =文件名”。

应该调用HttpServletResponse.getOutputStream方法返回的ServletOutputStream对象来向客户端写入附件文件内容,而不应使用HttpServletResponse.getWriter方法返回的PrintWriter对象。

(下载文件的名称为中文时,会出现乱码,要将文件名进行utf-8编码再进行URL编码。

在rfc2183中搜索encode,要求查rfc2184

查看urlencoder的帮助,建议用UTF-8编码,和一个连接到w3c的超连接,该超连接指向内容如下:

B.2 Special characters in URI attribute values

B.2.1 Non-ASCII characters in URI attribute values

Although URIs do not contain non-ASCII values (see [URI], section 2.1) authors sometimes specify them in attribute values expecting URIs (i.e., defined with %URI; in the DTD). For instance, the following href value is illegal:

... We recommend that user agents adopt the following convention for handling non-ASCII characters in such cases:

Represent each character in UTF-8 (see [RFC2279]) as one or more bytes.

Escape these bytes with the URI escaping mechanism (i.e., by converting each byte to %HH, where HH is the hexadecimal notation of the byte value).

This procedure results in a syntactically legal URI (as defined in [RFC1738], section 2.2 or [RFC2141], section 2) that is independent of the character encoding to which the HTML document carrying the URI may have been transcoded.

Note. Some older user agents trivially process URIs in HTML using the bytes of the character encoding in which the document was received. Some older HTML documents rely on this practice and break when transcoded. User agents that want to handle these older documents should, on receiving a URI containing characters outside the legal set, first use the conversion based on UTF-8. Only if the resulting URI does not resolve should they try constructing a URI based on the bytes of the character encoding in which the document was received.

Note. The same conversion based on UTF-8 should be applied to values of the name attribute for the A element.

MIME邮件中的附件名的中文,会出乱码吗?用outlook做个实验,结果是这样的:

Content-Disposition: attachment;

  filename="=?gb2312?B?0MK9qCDOxLG+zsS1tS50eHQ=?=")

图像访问计数器à介绍

网页每次被访问时,页面的访问次数都要发生改变,所以这个功能必须通过服务器端的程序来实现。

一些WEB站点只能输出静态页面内容,没有开放运行服务器端程序的功能,无法直接在这些只支持静态内容的WEB站点上编写服务器端程序来实现页面访问次数的统计和显示功能。 

一些具有执行服务器端程序功能的WEB站点推出了免费的页面访问计数器,只要在位于任何站点的一个静态HTML页面中增加一条该站点提供的HTML语句,该语句就能显示出该静态页面的访问次数。

一个站点要想能统计另外一个站点上的某个HTML页面的访问次数,必须让任何一个浏览器在每次访问那个HTML页面都通知这个一下站点,这可以通过在静态HTML页面中增加两种特殊的标签来实现:标签和设置src属性的

你可能感兴趣的:(servlet,浏览器,html,引擎,url,报表)