Servlet
Java Servlet 是运行在 web 服务器或应用服务器上的程序, 它是作为来自 Web 浏览器或其他 HTTP 客户端的请求和 HTTP 服务器上的数据库或应用程序之间的中间层.
使用 Servlet, 您可以收集来自网页表单的用户输入, 呈现来自数据库或者其他源的记录, 还可以动态创建网页.
Servlet 任务
Servlet 执行以下主要任务:
? 读取客户端 (浏览器) 发送的显式的数据. 这包括网页上的 html 表单, 或者也可以是来自 applet 或自定义的 HTTP 客户端程序的表单.
? 读取客户端 (浏览器) 发送的隐式的 HTTP 请求数据. 这包括 cookies, 媒体类型和浏览器能理解的压缩格式等等.
? 处理数据并生成结果. 这个过程可能需要访问数据库, 执行 RMI 或 CORBA 调用, 调用 Web 服务, 或者直接计算得出对应的响应.
? 发送显式的数据 (即文档) 到客户端(浏览器). 该文档的格式可以是多种多样的, 包括文本文件(HTML 或 xml), 二进制文件(GIF 图像),Excel 等.
? 发送隐式的 HTTP 响应到客户端(浏览器). 这包括告诉浏览器或其他客户端被返回的文档类型(例如 HTML), 设置 cookies 和缓存参数, 以及其他类似的任务.
Servlet 生命周期
Servlet 生命周期可被定义为从创建直到毁灭的整个过程. 以下是 Servlet 遵循的过程:
? Servlet 通过调用 init () 方法进行初始化.
? Servlet 调用 service() 方法来处理客户端的请求.
service() 方法是执行实际任务的主要方法. Servlet 容器 (即 Web 服务器) 调用 service() 方法来处理来自客户端 (浏览器) 的请求, 并把格式化的响应写回给客户端.
每次服务器接收到一个 Servlet 请求时, 服务器会产生一个新的线程并调用服务. service() 方法检查 HTTP 请求类型(GET,POST,PUT,DELETE 等), 并在适当的时候调用 doGet,doPost,doPut,doDelete 等方法.
? Servlet 通过调用 destroy() 方法终止(结束).
? 最后, Servlet 是由 JVM 的垃圾回收器进行垃圾回收的.
架构图
Servlet 在 Web 应用程序中的位置.
下图显示了一个典型的 Servlet 生命周期方案.
? 第一个到达服务器的 HTTP 请求被委派到 Servlet 容器.
? Servlet 容器在调用 service() 方法之前加载 Servlet.
? 然后 Servlet 容器处理由多个线程产生的多个请求, 每个线程执行一个单一的 Servlet 实例的 service() 方法.
Servlet 客户端 HTTP 请求
Servlet 容器对于接受到的每一个 Http 请求, 都会创建一个 ServletRequest 对象, 并把这个对象传递给 Servlet 的 Sevice( )方法
常用方法:
- String getContextPath();// 返回请求上下文的请求 URI 部分
- Cookie[] getCookies();// 返回一个 cookie 对象数组
- String getHeader(String var1);// 返回指定 HTTP 标题的值
- String getMethod();// 返回生成这个请求 HTTP 的方法名称
- String getQueryString();// 返回请求 URL 中的查询字符串
- HttpSession getSession();// 返回与这个请求相关的会话对象
Servlet 服务器 HTTP 响应
在调用 Servlet 的 Service( )方法前, Servlet 容器会先创建一个 ServletResponse 对象, 并把它作为第二个参数传给 Service( )方法. ServletResponse 隐藏了向浏览器发送响应的复杂过程.
常用方法:
- void addCookie(Cookie var1);// 给这个响应添加一个 cookie
- void addHeader(String var1, String var2);// 给这个请求添加一个响应头
- void sendRedirect(String var1) throws IOException;// 发送一条响应码, 讲浏览器跳转到指定的位置
- void setStatus(int var1);// 设置响应行的状态码
- PrintWriter getWriter();// 获得字符流, 通过字符流的 write(String s)方法可以将字符串设置到 response 缓冲区中, 随后 Tomcat 会将 response 缓冲区中的内容组装成 Http 响应返回给浏览器端.
- ServletOutputStream getOutputStream();// 获得字节流, 通过该字节流的 write(byte[] bytes)可以向 response 缓冲区中写入字节, 再由 Tomcat 服务器将字节内容组成 Http 响应返回给浏览器.
Servlet 过滤器
Servlet 过滤器可以动态地拦截请求和响应, 以变换或使用包含在请求或响应中的信息.
可以将一个或多个 Servlet 过滤器附加到一个 Servlet 或一组 Servlet.Servlet 过滤器也可以附加到 JavaServer Pages (JSP) 文件和 HTML 页面. 调用 Servlet 前调用所有附加的 Servlet 过滤器.
在 javax.servlet.Filter 接口中定义了 3 个方法:
void init(FilterConfig filterConfig) 用于完成过滤器的初始化
void destroy() 用于过滤器销毁前, 完成某些资源的回收
void doFilter(ServletRequest request, ServletResponse response,FilterChain chain) 实现过滤功能, 该方法对每个请求增加额外的处理
监听器
Web 监听器是一种 Servlet 中的特殊的类, 它们能帮助开发者监听 Web 中的特定事件, 比如 ServletContext,HttpSession,ServletRequest 的创建和销毁; 变量的创建, 销毁和修改等.
可以在某些动作前后增加处理, 实现监控. 例如可以用来统计在线人数等.
监听器有三类 8 种:
监听 Context,Request,Session 对象的创建和销毁, 需要在 Web.xml 中配置
- ServletContextListener
- ,
- ServletRequestListener
- ,HttpSessionListener
需要实现的方法:
- public void contextInitialized(ServletContextEvent e); // 在 application 创建时就调用
- public void contextDestroyed(ServletContextEvent e); // 当 application 销毁时调用
监听 Context,Request,Session 对象属性的变化, 需要在 Web.xml 中配置
- ServletContextAttributeListener
- ,
- ServletRequestAttributeListener
- ,
- HttpSessionAttributeListener
需要实现的方法:
- public void attributeAdded(ServletContextAttributeEvent e); // 当调用 application.setAttribute()时调用
- public void attributeRemoved(ServletContextAttributeEvent e); // 当调用 applcaition.removeAttribute()时调用
- public void attributeReplaced(ServletContextAttributeEvent e); // 当调用两次 application.setAttribute()赋予相同属性时调用
监听 Session 内部的对象, 不需要再 Web.xml 中配置
- HttpSessionActivationListener
- ,
- HttpSessionBindingListener
需要实现的方法:
- public void sessionCreated(HttpSessionEvent e); // 当打开一个浏览器时, 就会触发这个方法;
- public void sessionDestroyed(HttpSessionEvent e); // 当调用 session.invalidate(); 或超时时调用
Servlet 转发和重定向
转发, forward()
request.getRequestDispatcher ("/url"). forward(request, response);// 转发到 url
转发在服务器端完成, 浏览器并不知道这个操作, 浏览器的地址栏不改变, 并且转发和转发到的界面可以共享 request 里的数据.
重定向, sendRedirect()
response.sendRedirect("request.getContextPath()+/url"); // 重定向到 url, 客户端第二次发送请求会直接请求服务器根目录, 所以需要 getContextPath 得到当前容器目录
服务器返回一个重定向路径, 客户端重新发出请求, 浏览器的地址栏改变, request 中的变量全部失效, 两个界面不能共享数据.
Servlet3.x 新特性
注解式开发支持
Servlet3.x 之前开发 Servlet 需要在 Web.xml 中配置对应的映射地址, 但是从 3.x 之后这样的配置将不再是必须的了.
常用注解:@WebServlet,@WebListener,@WebFilter,@WebInitParam
Servlet3.x 支持的注解都在 javax.servlet.annotation 包下.
异步处理支持
Servlet3.x 之前的针对每个请求都是阻塞的, 只要服务器没有处理完任务时不会响应客户端的, 这样的体验并不好.
解决方法可以是借组消息中间件来异步处理, Servlet3.x 开始支持开启新线程异步处理, 无需等待新线程处理完成即可响应客户端.
文件上传下载新方式支持
Servlet3.x 之前对于文件上传并不友好, 编写相对麻烦. Servlet3.x 之后提供了 Part 类来表示上传文件对象, 完全可以借助该对象实现上传功能.
来源: http://www.bubuko.com/infodetail-3325888.html