servlet 提供的 service 方法实现了 GenericServlet 的 service 方法,在 HttpServlet 对象的 doMethod(Get, Delete, Options, Post, Put, or Trace)方法中,或者在其他实现了 Servlet 接口的类的方法中。术语 service method 用来描述 Servlet 类中的任何能提供给客户端调用的方法的。通常,service 方法用来从请求中读取信息,访问外部资源,然后基于这些信息填充相应数据。对 HTTP Servlet 来说,正确的填充相应的步骤如下:
获取响应数据流
填充响应头
编写响应数据流的内容
响应头必须在响应提交之前设置,web 容器将忽略响应提交之后设置响应头或添加响应头的操作。下两节描述如何从请求中获取信息和生成响应。
从请求中获取信息
请求携带数据从客户端传到服务端。所有请求都实现了 ServletRequest 接口。这个接口定义的方法可以访问下面的信息:
参数,通常用来在客户端与服务端之间传递参数
对象属性,通常用来在 web 容器与 servlet 之间、多个 servlet 之间传递信息
有关用于传达请求的协议以及请求中涉及的客户端和服务器的信息
本地化的相关信息
当然你也可以直接获取输入流,并手工解析数据。读取这些数据,最好使用 BufferedReader 对象获取请求的 getReader 方法。读取字节流数据,需要使用 getInputStream 方法返回的 ServletInputStream 对象。Http servlet 传递一个 Http 请求对象,HttpServletRequest,它包含请求 URL、Http 头信息、查询字符串等等。Http URL 包含下列信息:
http://[host]:[port][request-path]?[query-string]
请求路径还包括一下元素:
上下文路径:使用 / 符号与 web 应用程序的跟路径分隔
Servlet 路径:请求此路径的别名所对应的路径。路径以 / 开始。
path 路径:请求路径中不属于上下文路径和 servlet 上下文的路径
你可以使用 HttpServletRequest 接口的 getContextPath, getServletPath, and getPathInfo 方法访问这些信息。除 url 编码与请求路径有区别外,请求路径总是等于上下文路径 +servlet 路径 +path 路径。查询字符串由一组参数和值组成。单个参数可以通过请求的 getParameter 方法获取。有下面两种方式生成查询字符串:
查询字符串可以在 web 页面上直观的显示
当以 get 方式提交 Http 请求时,查询字符串附加在了请求后面。
构造响应
响应包含从服务端传到客户端的数据。所有的响应都实现了 ServletResponse 接口。这个接口定义的方法支持做下面的工作:
发送输出流数据到客户端。发送字符数据,使用 getWriter 方法返回的 PrintWriter 对象;发送 MIME 类型的二进制数据,使用 getOutputStream 方法返回的 ServletOutputStream。混合二进制和字符数据,存在多重响应,需要使用 ServletOutputStream 类并手动管理字符部分。
可以使用 setContentType 方法指定包含的类型(如 text/html)。这个方法必须在响应提交之前调用。缓冲区允许在响应提交之前写入数据,从而允许 servlet 有更多时间去设置状态代码和响应头或者转发到其他 web 资源。这个方法必须在任何内容被写入前或响应被提交前。
设置本地化信息,比如区域位置和编码,在 Chapter 20, “Internationalizing and Localizing Web Applications” 有更详尽的描述。
Http 响应对象,javax.servlet.http.HttpServletResponse,有表示 Http 头的属性,如下:
状态代码 用于指示不满足请求或请求已重定向的原因。
cookies 用来在客户端保存服务器的信息。通常,cookies 用户维持单一用户登陆或者是跟踪一个用户的 session(查看 Session Tracking 章节)。