Servlet技术
生命周期
Servlet构造方法
构造方法只有首次调用Servlet时,会被执行,后续请求不在执行 例如:
public HelloServlet() {
//只有首次会执行
System.out.println("创建HelloServlet对象");
}
init()方法
init方法被设计成只调用一次 它在第一次创建Servelt时,被调用,在后续每次用户请求时,不再调用。因此,它是用于一次性初始化。
@Override
public void init(ServletConfig config) throws ServletException {
//只有首次会执行
System.out.println("开始初始化");
super.init(config);
}
service方法
service()方法是执行实际任务的主要方法 Servlet容器(即Web服务器)调用service()方法来处理来自客户端(浏览器)的请求,并把格式化的响应写回给客户端。
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException,IOException {
/*
每次刷新都执行
处理get/post请求(或者说校验请求类型,然后分发给doGet和doPost等)
通常不需要重写,除非需要实现一些统一的预处理或后处理逻辑
例如,进行权限验证、日志记录、统一异常处理等
*/
System.out.println("service方法执行");
super.service(req, resp);
}
每次服务器接收到一个 Servlet 请求时,服务器会产生一个新的线程并调用服务。 service() 方法检查 HTTP 请求类型(GET、POST、PUT、DELETE 等),并在适当的时候调用 doGet、doPost、doPut,doDelete 等方法。
doGet()方法
get请求来自于一个URL的正常请求,或者来自于一个未指定Method的HTML表单(表单默认提交方式为GET),它由doGet()方法处理。
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {...}
doPost()方法
post请求来自于一个特别指定了Method为POST的HTML表单,它由doPost()方法处理。
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {...}
destroy()方法
destroy() 方法只会被调用一次,在 Servlet 生命周期结束时被调用。destroy() 方法可以让您的 Servlet 关闭数据库连接、停止后台线程、把 Cookie 列表或点击计数器写入到磁盘,并执行其他类似的清理活动。 在调用 destroy() 方法之后,servlet 对象被标记为垃圾回收。destroy 方法定义如下所示:
@Override
public void destroy() {
//销毁时,执行
System.out.println("destroy方法执行");
super.destroy();
}
GET和POST的区别
get方式的安全性较Post方式要差些,包含机密信息的话,建议用post数据提交方式。 在做数据查询时,建议用Get方式;而在做数据添加、修改或删除时,建议用Post方式。
一个简单的servlet
public class Test implements Servlet {
@Override
public void init(ServletConfig servletConfig) throws ServletException {
//初始化方法
}
@Override
public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {
/*
处理get/post请求(或者说校验请求类型,然后分发给doGet和doPost等)
通常不需要重写,除非需要实现一些统一的预处理或后处理逻辑
例如,进行权限验证、日志记录、统一异常处理等
*/
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException{
//处理get请求
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//处理post请求
}
@Override
public void destroy() {
//销毁的方法
}
}
web.xml映射Servlet
在web.xml中添加如下代码完成请求路径到servlet的映射配置。
<servlet>
<servlet-name>test</servlet-name> <!-- 3 -->
<servlet-class>com.servlet.Test</servlet-class> <!-- 4 -->
</servlet>
<servlet-mapping>
<servlet-name>test</servlet-name> <!-- 2 -->
<url-patten>/test</url-patten> <!-- 1 -->
</servlet-mapping>
配置注解映射Servlet
在类上添加@WebSerevlet注解即可,效果等同于上述xml配置。
package com.servlet
@WebServlet("/test")
public class Test extends HttpServlet{...}
请求路径的几种匹配方式
全路径匹配
以 / 开始,格式为 : /a /aa/bb
@WebServlet("/a /aa/bb")
部分路径匹配
以 / 开始 , 但是以 * 结束 ,格式为 :/ a / * / *
@WebServlet("/ a / * / *")
后缀匹配
不以/ 而是以 * 开始 ,* . 扩展名,格式为: * . aa, * . bb
@WebServlet("* . aa")
特殊匹配
仅有 " / ",而没有其他任何内容,该类是缺省的servlet,若当前访问资源地址的所有 Servlet 都不匹配时,就由缺省的 Servlet 进行处理
@WebServlet("/")
Servlet的三种作用域
每一种数据范围数据都有相同的操作方法
setAttribute( ):用来设置指定的key对应的值对象;
getAttribute( ):根据指定的key取得对应值对象;
removeAttribute( ):用来删除指定的key对应的值对象;
getAttributeName( ):用来取得所有值对象的key的集合;
实现机制是一个Map。
applicationScope
-
描述:Application作用域(也称为ServletContext作用域)的数据在整个Web应用的生命周期内都有效,从Web应用启动开始,直到Web应用停止。这意味着所有用户、所有会话和所有请求都可以访问到这个范围内的数据。ServletContext对象代表了整个Web应用,并且是唯一的。
-
应用场景:适合存储全局配置信息、共享的资源路径等不需要特定于会话或请求的数据,如数据库连接池配置、系统级的缓存信息等。
sessionScope
-
描述:Session作用域的数据在一次用户会话期间有效。当用户首次访问Web应用时,服务器会为该用户创建一个HttpSession对象,这个对象代表了用户与服务器之间的一次会话。在会话期间,用户与服务器进行的多次请求响应都可以访问到这个Session中存储的数据。会话通常在用户长时间未活动后过期或被显式销毁。
-
应用场景:适用于保存登录用户的状态信息、购物车信息等,需要跨多个请求持久化的数据。
requestScope
-
描述:Request作用域的数据只在一次HTTP请求过程中有效。当Web容器接收到一个请求时,它会创建一个新的HttpServletRequest对象,该对象用来封装请求的信息。在这个请求范围内设置的属性,只对当前请求可见,请求结束时,这些属性将被销毁。
-
应用场景:适合用于传递请求参数、错误信息等,仅需在请求处理期间使用的数据。
Filter
通过Filter技术,可以对web服务器管理的所有web资源:例如Jsp, Servlet, 静态图片文件或静态 html 文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。
当存在过滤器的时候,对于来自客户端的请求来说,请求必须先经过滤器,放行之后,才能到达Web资源;对于返回的响应来说,响应同样会经过滤器,才能到达Web服务器,进而响应给客户端。
例如:
package com;
import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import java.io.IOException;
//@WebFilter("/*") <--这就是注解配置
public class FilterDemo2 implements Filter {
//初始化
public void init(FilterConfig config) throws ServletException {...}
//过滤方法
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
//放行,调用下一个过滤器或者访问资源
chain.doFilter(req, resp);
//响应从此处开始继续执行
System.out.println("响应了");
}
//销毁
public void destroy() {...}
}
写完过滤器之后,还需要配置,分为xml配置和注解配置两种。
xml配置
<filter>
<filter-name>FilterDemo2</filter-name>
<filter-class>com.FilterDemo2</filter-class>
</filter>
<filter-mapping>
<filter-name>FilterDemo2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
注解配置
将注解打在Filter上即可,效果等同于上述xml配置。
@WebFilter("/*")