Servlet之Filter详细讲解

Java Servlet之Filte(过滤器)详解 提示:这里对文章进行总结:以上就是今天要讲的内容. 阅读详情

https://www.cnblogs.com/zlbx/p/4888312.html   

Filter,过滤器,顾名思义,即是对数据等的过滤,预处理过程。为什么要引入过滤器呢?在平常访问网站的时候,有时候发一些敏感的信息,发出后显示时 就会将敏感信息用*等字符替代,这就是用过滤器对信息进行了处理。这只是一个简单的例子,当然,过滤器那么强大,它的功能也不可能局限于此,它不仅能预处 理数据,只要是发送过来的请求它都是可以预处理的,同时,它还可以对服务器返回的响应进行预处理,这样,大大减轻了服务器的压力。例如,实现URL级别的 权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。下面来详细介绍一下过滤器。

一、定义

  学习一个东西,我们首先要理解它的定义。

 

 

1.概念

   过滤作用,对从客户端向服务器端发送的请求进行过滤,也可以对服务器端返回的响应进行处理。它使用户可以改变一个request和修改一个 response.。Filter 不是一个servlet,它不能产生一个response,但是它能够在一个request到达servlet之前预处理request,也可以在 response离开servlet时处理response。换句话说,filter其实是客户端与servlet中间的一个传递者,并且它可以对要传递 的东西进行修改。

  注意:过滤器是用来拦截请求和响应的,不能产生响应,而servlet是用来处理请求并产生响应的。

 

 

2.适用场合

  实现URL级别的权限访问控制,过滤敏感词汇,压缩响应信息等。

 

 

3.过滤器如何实现拦截

  • 当客户端发生请求后,在HttpServletRequest 到达Servlet 之前,过滤器拦截客户的HttpServletRequest 。 
  • 根据需要检查HttpServletRequest ,也可以修改HttpServletRequest 头和数据。 
  • 在过滤器中调用doFilter方法,对请求放行。请求到达Servlet后,对请求进行处理并产生HttpServletResponse发送给客户端。
  • 在HttpServletResponse 到达客户端之前,过滤器拦截HttpServletResponse 。 
  • 根据需要检查HttpServletResponse ,可以修改HttpServletResponse 头和数据。
  • 最后,HttpServletResponse到达客户端。

 

 

4.Filter接口

  Servlet API提供了一个Filter接口,编写的过滤器必须实现该接口。

 

 

5.Filter的生命周期

(1)Filter接口中有三个重要的方法。

  • init()方法:初始化参数,在创建Filter时自动调用。当我们需要设置初始化参数的时候,可以写到该方法中。
  • doFilter()方法:拦截到要执行的请求时,doFilter就会执行。这里面写我们对请求和响应的预处理。
  • destroy()方法:在销毁Filter时自动调用。

 

(2)Filter的生命周期

    Filter的创建和销毁由web服务器控制。

  • 服务器启动的时候,web服务器创建Filter的实例对象,并调用其init方法,完成对象的初始化功能。filter对象只会创建一次,init方法也只会执行一次。
  • 拦截到请求时,执行doFilter方法。可以执行多次。
  • 服务器关闭时,web服务器销毁Filter的实例对象。

 

 

6.Filter对象——FilterConfig

  用 户在配置filter时,可以使用<init-param>为filter配置一些初始化参数,当web容器实例化Filter对象,调用其 init方法时,会把封装了filter初始化参数的filterConfig对象传递进来。因此开发人员在编写filter时,通过 filterConfig对象的方法,就可获得:

  • String getFilterName():得到filter的名称。
  • String getInitParameter(String name): 返回在部署描述中指定名称的初始化参数的值。如果不存在返回null.
  • Enumeration getInitParameterNames():返回过滤器的所有初始化参数的名字的枚举集合。
  • public ServletContext getServletContext():返回Servlet上下文对象的引用。

 

 

7.过滤器链——FilterChain

  一组过滤器对某些web资源进行拦截,那么这组过滤器就称为过滤器链。过滤器的执行顺序和<filter-mapping>有关(谁在前先执行谁)。

二、开发步骤

  了解了过滤器的相关概念,接下来进行实例开发。

 

1.编写步骤

  • 编写java类实现Filter接口,并实现其doFilter方法。
  • 在 web.xml 文件中使用<filter>和<filter-mapping>元素对编写的filter类进行注册,并设置它所能拦截的资源。

 

2.示例

(1)简单的Filter示例

  •  编写FilterDemo1类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 12 public class FilterDemo1 implements Filter{ 13 14 /* 15  * 对Filter的整个生命周期了解的一个案例 16  * 注意事项: 17  * 1.实现Filter接口时导入的是javax.servlet.Filter包 18  * 2.方法均有web服务器自动调用,不需我们手动调用 19  * 3.init方法中一般写初始化参数,这里先不用,后面的例子再使用。 20  * 4.destroy方法一般不需要写任何代码 21  * 5.重写doFilter方法,可以写我们对拦截的请求和响应的处理动作。 22  * 6.写完该类后配置filter,在web.xml中配置。 23  * @see javax.servlet.Filter#init(javax.servlet.FilterConfig) 24 */ 25  @Override 26 public void init(FilterConfig filterConfig) throws ServletException { 27 // TODO Auto-generated method stub 28 System.out.println("FilterDemo1的init方法被调用"); 29  } 30 31  @Override 32 public void doFilter(ServletRequest request, ServletResponse response, 33 FilterChain chain) throws IOException, ServletException { 34 // TODO Auto-generated method stub 35 System.out.println("我是FilterDemo1,客户端向Servlet发送的请求被我拦截到了"); 36  chain.doFilter(request, response); 37 System.out.println("我是FilterDemo1,Servlet向客户端发送的响应被我拦截到了"); 38  } 39 40  @Override 41 public void destroy() { 42 // TODO Auto-generated method stub 43 System.out.println("FilterDemo1的destroy方法被调用"); 44  } 45 46 }
复制代码
  • 配置filter,在web.xml文件中加入下面这段代码
复制代码
1 <filter>
2       <filter-name>filterDemo1</filter-name> 3 <filter-class>com.oracle.filter.FilterDemo1</filter-class> 4 </filter> 5 <filter-mapping> 6 <filter-name>filterDemo1</filter-name> 7 <url-pattern>/*</url-pattern> 8 <!-- /*是对所有的文件进行拦截 --> 9 </filter-mapping>
复制代码
  • 控制台结果

  • 分 析:从上面结果可以看出,在服务器启动时,就调用了init方法,当访问页面时,该过滤器拦截到请求执行doFilter方法,在该方法中,使用 doFilter方法,当返回响应后,继续执行剩下的代码,执行完成后将响应传给客户端。当关闭服务器时,服务器就调用了destroy方法。

 

(2)Filter链示例

  • 编写FilterDemo1类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 12 public class FilterDemo1 implements Filter{ 13 14 /* 15  * @see javax.servlet.Filter#init(javax.servlet.FilterConfig) 16 */ 17  @Override 18 public void init(FilterConfig filterConfig) throws ServletException { 19 // TODO Auto-generated method stub 20  } 21 22  @Override 23 public void doFilter(ServletRequest request, ServletResponse response, 24 FilterChain chain) throws IOException, ServletException { 25 // TODO Auto-generated method stub 26 System.out.println("我是FilterDemo1,客户端向Servlet发送的请求被我拦截到了"); 27 //对请求放行,进入下一个过滤器FilterDemo2 28  chain.doFilter(request, response); 29 System.out.println("我是FilterDemo1,Servlet向客户端发送的响应被我拦截到了"); 30  } 31 32  @Override 33 public void destroy() { 34 // TODO Auto-generated method stub 35  } 36 37 }
复制代码
  •  编写FilterDemo2类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 12 public class FilterDemo2 implements Filter{ 13 14  @Override 15 public void init(FilterConfig filterConfig) throws ServletException { 16 // TODO Auto-generated method stub 17 18  } 19 20  @Override 21 public void doFilter(ServletRequest request, ServletResponse response, 22 FilterChain chain) throws IOException, ServletException { 23 // TODO Auto-generated method stub 24 System.out.println("我是FilterDemo2,客户端向Servlet发送的请求被我拦截到了"); 25 //对请求放行,进入Servlet 26  chain.doFilter(request, response); 27 System.out.println("我是FilterDemo2,Servlet向客户端发送的响应被我拦截到了"); 28  } 29 30  @Override 31 public void destroy() { 32 // TODO Auto-generated method stub 33 34  } 35 36 }
复制代码
  •  配置filter,在web.xml文件中加入下面这段代码
复制代码
 1 <filter>
 2       <filter-name>filterDemo1</filter-name>  3 <filter-class>com.oracle.filter.FilterDemo1</filter-class>  4 </filter>  5 <filter>  6 <filter-name>filterDemo2</filter-name>  7 <filter-class>com.oracle.filter.FilterDemo2</filter-class>  8 </filter>  9 10 <filter-mapping> 11 <filter-name>filterDemo1</filter-name> 12 <url-pattern>/*</url-pattern> 13 <!-- /*是对所有的文件进行拦截 --> 14 </filter-mapping> 15 <filter-mapping> 16 <filter-name>filterDemo2</filter-name> 17 <url-pattern>/*</url-pattern> 18 <!-- /*是对所有的文件进行拦截 --> 19 </filter-mapping>
复制代码
  •  控制台结果

  • 分 析:当有多个过滤器对同一个请求进行拦截时,根据web.xml文件中<filter-mapping>的配置顺序,谁在前,先执行谁。当第 一过滤器拦截成功后,会执行doFilter方法,该方法中,调用chain.doFilter方法,会将该请求放行给下一个过滤器,依次执行,直到执行 到最后一个过滤器,当最后一个过滤器调用chain.doFilter方法时,请求会被放行给Servlet,当Servlet处理返回响应信息时,先返 回到最后执行的过滤器,继续执行该过滤器剩下的代码。依次返回,直到返回到第一个过滤器,最后返回给客户端。

 

 (3)禁用所有动态页面的缓存过滤器

  • 编写FilterDemo3类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 import javax.servlet.http.HttpServletResponse; 12 13 public class FilterDemo3 implements Filter{ 14 15  @Override 16 public void init(FilterConfig filterConfig) throws ServletException { 17 // TODO Auto-generated method stub 18 19  } 20 21  @Override 22 public void doFilter(ServletRequest request, ServletResponse response, 23 FilterChain chain) throws IOException, ServletException { 24 // 在response的头部设置Cache-Control、Pragma和Expires即可取消缓存 25 HttpServletResponse resp = (HttpServletResponse)response; 26 resp.setHeader("Cache-Control", "no-cache"); 27 resp.setHeader("Pragma", "no-cache"); 28 resp.setDateHeader("Expires", -1); 29  chain.doFilter(request, resp); 30  } 31 32  @Override 33 public void destroy() { 34 // TODO Auto-generated method stub 35 36  } 37 38 }
复制代码
  •  配置filter,在web.xml文件中加入下面这段代码
复制代码
1 <filter>
2       <filter-name>filterDemo3</filter-name> 3 <filter-class>com.oracle.filter.FilterDemo3</filter-class> 4 </filter> 5 6 <filter-mapping> 7 <filter-name>filterDemo3</filter-name> 8 <url-pattern>/*</url-pattern> 9 </filter-mapping>
复制代码

 

(4) 分IP统计网站的访问次数过滤器

  • 编写FilterDemo4类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4 import java.util.HashMap;  5 import java.util.Map;  6  7 import javax.servlet.Filter;  8 import javax.servlet.FilterChain;  9 import javax.servlet.FilterConfig; 10 import javax.servlet.ServletContext; 11 import javax.servlet.ServletException; 12 import javax.servlet.ServletRequest; 13 import javax.servlet.ServletResponse; 14 15 public class FilterDemo4 implements Filter{ 16 17 private FilterConfig filterConfig; 18  @Override 19 public void init(FilterConfig filterConfig) throws ServletException { 20 // TODO Auto-generated method stub 21 22 //初始化参数,ipCount用来存放ip及访问次数 23 ServletContext application = filterConfig.getServletContext(); 24 Map<String,Integer> ipCount = new HashMap<String,Integer>(); 25 application.setAttribute("ipCount",ipCount); 26 this.filterConfig = filterConfig; 27  } 28 29 30  @Override 31 public void doFilter(ServletRequest request, ServletResponse response, 32 FilterChain chain) throws IOException, ServletException { 33 // TODO Auto-generated method stub 34 ServletContext application = filterConfig.getServletContext(); 35 Map<String,Integer> ipCount = (HashMap<String,Integer>)application.getAttribute("ipCount"); 36 String ip = request.getRemoteAddr(); 37 Integer count = ipCount.get(ip); 38 if(count != null){ 39 //Map中存在该ip 40 count = count + 1; 41 }else{ 42 count = 1; 43  } 44  ipCount.put(ip, count); 45 application.setAttribute("ipCount",ipCount); 46  chain.doFilter(request, response); 47  } 48 49  @Override 50 public void destroy() { 51 // TODO Auto-generated method stub 52 53  } 54 55 }
复制代码
  • 编写index.jsp页面
复制代码
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
 2 <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
 3 <%
 4 String path = request.getContextPath();  5 String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";  6 %>  7  8 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">  9 <html> 10 <head> 11 <base href="<%=basePath%>"> 12 13 <title>My JSP 'index.jsp' starting page</title> 14 <meta http-equiv="pragma" content="no-cache"> 15 <meta http-equiv="cache-control" content="no-cache"> 16 <meta http-equiv="expires" content="0"> 17 <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> 18 <meta http-equiv="description" content="This is my page"> 19 <!-- 20 <link rel="stylesheet" type="text/css" href="styles.css"> 21 --> 22 </head> 23 24 <body> 25 <h1>分IP统计网站浏览次数</h1> 26 <table border="1" width="400"> 27 <tr> 28 <th>IP地址</th> 29 <th>浏览次数</th> 30 </tr> 31 <c:forEach items="${ipCount}" var="m"> 32 <tr> 33 <td>${m.key}</td> 34 <td>${m.value}</td> 35 </tr> 36 </c:forEach> 37 </table> 38 </body> 39 </html>
复制代码
  • 配置filter,在web.xml文件中加入下面这段代码
复制代码
1 <filter>
2       <filter-name>filterDemo4</filter-name> 3 <filter-class>com.oracle.filter.FilterDemo4</filter-class> 4 </filter> 5 6 <filter-mapping> 7 <filter-name>filterDemo4</filter-name> 8 <url-pattern>/*</url-pattern> 9 </filter-mapping>
复制代码
  •  网页结果

 

 

(5)自动登录

  • 编写AutoLoginFilter类
复制代码
 1 package com.oracle.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 import javax.servlet.http.Cookie; 12 import javax.servlet.http.HttpServletRequest; 13 import javax.servlet.http.HttpSession; 14 15 import com.oracle.biz.UserInfoBiz; 16 import com.oracle.biz.impl.UserInfoBizImpl; 17 import com.oracle.entity.UserInfo; 18 import com.oracle.util.CookieUtil; 19 20 public class AutoLoginFilter implements Filter{ 21 22  @Override 23 public void init(FilterConfig filterConfig) throws ServletException { 24 // TODO Auto-generated method stub 25 26  } 27 28  @Override 29 public void doFilter(ServletRequest request, ServletResponse response, 30 FilterChain chain) throws IOException, ServletException { 31 // TODO Auto-generated method stub 32 //先判断session中是否存在,存在则放行,不存在则判断cookie中是否存在用户名密码,存在则到数据库中查询是否正确,正确则存入session并放行,不正确则放行 33 HttpServletRequest req = (HttpServletRequest)request; 34 HttpSession session = req.getSession(); 35 UserInfo user = (UserInfo)session.getAttribute("user"); 36 if(user != null){ 37  chain.doFilter(req, response); 38 }else{ 39 //session中不存在用户 40 Cookie[] cookies = req.getCookies(); 41 Cookie cookie = CookieUtil.findCookie(cookies, "autoLogin"); 42 if(cookie!=null){ 43 //在cookie中找到该用户 44 UserInfoBiz ubiz = new UserInfoBizImpl(); 45 String name = cookie.getValue().split("#oracle#")[0]; 46 String pwd = cookie.getValue().split("#oracle#")[1]; 47 String msg = ubiz.login(name, pwd); 48 if("登陆成功!".equals(msg)){ 49 user = ubiz.getByName(name); 50 session.setAttribute("user", user); 51  chain.doFilter(req, response); 52 }else{ 53  chain.doFilter(req, response); 54  } 55 }else{ 56 //没有找到该客户 57  chain.doFilter(req, response); 58  } 59  } 60  } 61 62  @Override 63 public void destroy() { 64 // TODO Auto-generated method stub 65 66  } 67 68 69 }
复制代码

 

  • 编写DoLoginServlet
复制代码
 1 package com.oracle.servlet;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.ServletException;  6 import javax.servlet.http.Cookie;  7 import javax.servlet.http.HttpServlet;  8 import javax.servlet.http.HttpServletRequest;  9 import javax.servlet.http.HttpServletResponse; 10 import javax.servlet.http.HttpSession; 11 12 import com.oracle.biz.UserInfoBiz; 13 import com.oracle.biz.impl.UserInfoBizImpl; 14 import com.oracle.entity.UserInfo; 15 16 public class DoLoginServlet extends HttpServlet { 17 18 /** 19  * Constructor of the object. 20 */ 21 public DoLoginServlet() { 22 super(); 23  } 24 25 /** 26  * Destruction of the servlet. <br> 27 */ 28 public void destroy() { 29 super.destroy(); // Just puts "destroy" string in log 30 // Put your code here 31  } 32 33 /** 34  * The doGet method of the servlet. <br> 35  * 36  * This method is called when a form has its tag value method equals to get. 37  * 38  * @param request the request send by the client to the server 39  * @param response the response send by the server to the client 40  * @throws ServletException if an error occurred 41  * @throws IOException if an error occurred 42 */ 43 public void doGet(HttpServletRequest request, HttpServletResponse response) 44 throws ServletException, IOException { 45 46  doPost(request,response); 47  } 48 49 /** 50  * The doPost method of the servlet. <br> 51  * 52  * This method is called when a form has its tag value method equals to post. 53  * 54  * @param request the request send by the client to the server 55  * @param response the response send by the server to the client 56  * @throws ServletException if an error occurred 57  * @throws IOException if an error occurred 58 */ 59 public void doPost(HttpServletRequest request, HttpServletResponse response) 60 throws ServletException, IOException { 61 62 HttpSession session = request.getSession(); 63 request.setCharacterEncoding("UTF-8"); 64 response.setCharacterEncoding("UTF-8"); 65 String name = request.getParameter("myname"); 66 String pwd = request.getParameter("pwd"); 67 String autoLogin = request.getParameter("autoLogin"); 68 UserInfoBiz ubiz = new UserInfoBizImpl(); 69 //ubiz.login(name, pwd):判断用户是否登陆成功,返回一个字符串。成功则返回"登陆成功!",不成功则返回对应的错误提示。 70 String msg = ubiz.login(name, pwd); 71 if("登陆成功!".equals(msg)){ 72 UserInfo user = ubiz.getByName(name); 73 session.setAttribute("user", user); 74 if("true".equals(autoLogin)){ 75 //利用cookie记住用户名和密码 76 Cookie cookie = new Cookie("autoLogin",user.getUserName()+"#oracle#"+user.getPassword()); 77 //设置有效时间 78 cookie.setMaxAge(60*60*24); 79 //将cookie回写到浏览器 80 response.addCookie(cookie); 81 } 82 response.sendRedirect("success.jsp"); 83 }else{ 84 request.setAttribute("msg", msg); 85 request.getRequestDispatcher("login.jsp").forward(request, response); 86 } 87 } 88 89 /** 90 * Initialization of the servlet. <br> 91 * 92 * @throws ServletException if an error occurs 93 */ 94 public void init() throws ServletException { 95 // Put your code here 96 } 97 98 }
复制代码
  •  编写CookieUtil
复制代码
 1 package com.oracle.util;
 2 
 3 import javax.servlet.http.Cookie;  4  5  6  7 public class CookieUtil {  8  9 public static Cookie findCookie(Cookie[] cookies,String name){ 10 if(cookies==null){ 11 return null; 12 }else{ 13 for(Cookie cookie:cookies){ 14 if(cookie.getName().equals(name)){ 15 return cookie; 16  } 17  } 18 return null; 19  } 20  } 21 }
复制代码
  • 编写login.jsp
复制代码
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>  2 <%  3 String path = request.getContextPath();  4 String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";  5 %>  6  7 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">  8 <html>  9 <head> 10 <base href="<%=basePath%>"> 11 12 <title>My JSP 'login.jsp' starting page</title> 13 14 <meta http-equiv="pragma" content="no-cache"> 15 <meta http-equiv="cache-control" content="no-cache"> 16 <meta http-equiv="expires" content="0"> 17 <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> 18 <meta http-equiv="description" content="This is my page"> 19 <!-- 20  <link rel="stylesheet" type="text/css" href="styles.css"> 21 --> 22 23 </head> 24 25 <body> 26 <form action="doLogin" method="post"> 27 用户名<input name="myname"><br/> 28 密&nbsp;码<input type="password" name="pwd"><br/> 29 <input type="checkBox" name="autoLogin" value="true">自动登录<br/> 30 <input type="submit" value="登陆"> 31 </form> 32 </body> 33 </html>
复制代码
  • 编写success.jsp
复制代码
 1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>  2 <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>  3 <%  4 String path = request.getContextPath();  5 String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/";  6 %>  7  8 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">  9 <html> 10 <head> 11 <base href="<%=basePath%>"> 12 13 <title>My JSP 'success.jsp' starting page</title> 14 15 <meta http-equiv="pragma" content="no-cache"> 16 <meta http-equiv="cache-control" content="no-cache"> 17 <meta http-equiv="expires" content="0"> 18 <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> 19 <meta http-equiv="description" content="This is my page"> 20 <!-- 21  <link rel="stylesheet" type="text/css" href="styles.css"> 22 --> 23 24 </head> 25 26 <body> 27 <c:if test="${empty user}"> 28 <h2>您还未登陆,请去<a href="login.jsp">登陆</a></h2> 29 </c:if> 30 <c:if test="${not empty user}"> 31 <h2>欢迎你${user.userName}</h2> 32 </c:if> 33 </body> 34 </html>
复制代码
  • 配置filter和servlet,在web.xml文件中加入下面的代码
复制代码
 1 <servlet>
 2     <description>This is the description of my J2EE component</description>  3 <display-name>This is the display name of my J2EE component</display-name>  4 <servlet-name>DoLoginServlet</servlet-name>  5 <servlet-class>com.oracle.servlet.DoLoginServlet</servlet-class>  6 </servlet>  7  8 <servlet-mapping>  9 <servlet-name>DoLoginServlet</servlet-name> 10 <url-pattern>/doLogin</url-pattern> 11 </servlet-mapping> 12 13 <filter> 14 <filter-name>AutoLoginFilter</filter-name> 15 <filter-class>com.oracle.filter.AutoLoginFilter</filter-class> 16 </filter> 17 <filter-mapping> 18 <filter-name>AutoLoginFilter</filter-name> 19 <url-pattern>/*</url-pattern> 20 </filter-mapping>
复制代码

 

(6)处理网站的Get和Post请求乱码

  • 思 路:增强request对象的getParameter方法等方法。编写一个类MyHttpServletRequest实现 HttpServletRequestWrapper,重写它的getParameter方法等方法,在这些方法中对不同方式提交的数据进行转码。在过滤 器中,将request强制转换成MyHttpServletRequest类型的对象,这样,当再次使用getParameter等方法时其实调用的是 你重写后的getParametr方法,也就是已经处理过的数据,这样就不用再担心乱码的问题了。
  • MyHttpServletRequest类
复制代码
 1 package com.oracle.bookshop.filter;
 2 
 3 import java.io.UnsupportedEncodingException;  4 import java.util.Map;  5  6 import javax.servlet.http.HttpServletRequest;  7 import javax.servlet.http.HttpServletRequestWrapper;  8  9 10 public class MyHttpServletRequest extends HttpServletRequestWrapper { 11 /* 12  * 该类重写 13 */ 14 private HttpServletRequest request; 15 16 private boolean hasEncode; 17 18 public MyHttpServletRequest(HttpServletRequest request) { 19 super(request);// super必须写 20 this.request = request; 21  } 22 23 // 对需要增强方法进行覆盖 24  @Override 25 public Map getParameterMap() { 26 // 先获得请求方式 27 String method = request.getMethod(); 28 if (method.equalsIgnoreCase("post")) { 29 // post请求 30 try { 31 // 处理post乱码 32 request.setCharacterEncoding("utf-8"); 33 return request.getParameterMap(); 34 } catch (UnsupportedEncodingException e) { 35  e.printStackTrace(); 36  } 37 } else if (method.equalsIgnoreCase("get")) { 38 // get请求 39 Map<String, String[]> parameterMap = request.getParameterMap(); 40 if (!hasEncode) { // 确保get手动编码逻辑只运行一次 41 for (String parameterName : parameterMap.keySet()) { 42 String[] values = parameterMap.get(parameterName); 43 if (values != null) { 44 for (int i = 0; i < values.length; i++) { 45 try { 46 // 处理get乱码 47 values[i] = new String(values[i] 48 .getBytes("ISO-8859-1"), "utf-8"); 49 } catch (UnsupportedEncodingException e) { 50  e.printStackTrace(); 51  } 52  } 53  } 54  } 55 hasEncode = true; 56  } 57 return parameterMap; 58  } 59 60 return super.getParameterMap(); 61  } 62 63  @Override 64 public String getParameter(String name) { 65 Map<String, String[]> parameterMap = getParameterMap(); 66 String[] values = parameterMap.get(name); 67 if (values == null) { 68 return null; 69  } 70 return values[0]; // 取回参数的第一个值 71  } 72 73  @Override 74 public String[] getParameterValues(String name) { 75 Map<String, String[]> parameterMap = getParameterMap(); 76 String[] values = parameterMap.get(name); 77 return values; 78  } 79 80 }
复制代码
  • 编写CharacterEnodingFilter
复制代码
 1 package com.oracle.bookshop.filter;
 2 
 3 import java.io.IOException;  4  5 import javax.servlet.Filter;  6 import javax.servlet.FilterChain;  7 import javax.servlet.FilterConfig;  8 import javax.servlet.ServletException;  9 import javax.servlet.ServletRequest; 10 import javax.servlet.ServletResponse; 11 import javax.servlet.http.HttpServletRequest; 12 13 public class CharacterEnodingFilter implements Filter{ 14 15  @Override 16 public void destroy() { 17 // TODO Auto-generated method stub 18 19  } 20 21  @Override 22 public void doFilter(ServletRequest request, ServletResponse response, 23 FilterChain chain) throws IOException, ServletException { 24 // TODO Auto-generated method stub 25 HttpServletRequest req = (HttpServletRequest)request; 26 MyHttpServletRequest myreq = new MyHttpServletRequest(req); 27  chain.doFilter(myreq, response); 28 29  } 30 31  @Override 32 public void init(FilterConfig arg0) throws ServletException { 33 // TODO Auto-generated method stub 34 35  } 36 37 38 }
复制代码
Livox MID-360与FAST-LIO2实战:从驱动部署到参数调优的完整指南 激光雷达惯性里程计(LIO)是机器人定位与建图(SLAM)领域的核心技术,它通过紧耦合融合激光雷达点云与惯性测量单元(IMU)数据,实现高精度、低漂移的位姿估计。其核心原理在于利用IMU的高频数据预测运动,并用激光雷达的精确测距信息进行校正与优化,从而在快速运动或特征缺失场景下保持鲁棒性。这项技术的工程价值在于为自动驾驶、移动机器人及三维重建提供了可靠的前端里程计解决方案。针对Livox MID-360固态雷达与FAST-LIO2这一热门组合,其应用场景广泛覆盖了室内外导航与地图构建。本文聚焦于**驱动部署 阅读详情

相关推荐

浅谈Android MVI架构---大自然的搬运工~~~

浅谈 Android MVI架构

hong_world的博客 2152

vue:todolist Demo

TodoList.vue <template> <div> <div> <input v-model="inputValue"> <button @click="handleSubmit">提交</button> </div> <ul> &...

weixin_41143662的博客 2万+

本地部署ComfyUI:开源AI生图与视频生成完整实战指南

在生成式AI应用快速普及的今天,云端工具常受制于排队、积分和素材管理等问题,而本地化部署正成为开发者与创作者的高效替代方案。其核心思路是基于开源工作流引擎,将图像生成、视频生成与后期处理整合到同一套可离线运行的系统中。ComfyUI作为当前最受关注的节点式工作流平台,凭借灵活的模块组合和强大的自定义能力,降低了从图像模型调用到视频扩展的工程门槛。本文从环境配置与依赖安装入手,系统讲解如何部署ComfyUI、加载Checkpoint模型、跑通文生图基础流程,再通过自定义节点接入视频生成能力,同时介绍API批量

weixin_30985047的博客 555

todolist自定义界面

这是学习Android2高级编程上面的一个例子,效果图如下: public class ToDoList extends Activity { private EditText mEditText; private ListView mListView; private ArrayList&lt;String&gt; mList; private ArrayAdapter&lt;St...

bolutes 483

嵌入式面试|MCU+RTOS技术栈——面试八股文整理3:STM32

stm32

weixin_44800059的博客 1898

Surface Go 2 变身 Linux 开发本:保姆级 Ubuntu 20.04 双系统安装与驱动配置全攻略

本文详细介绍了如何将 Surface Go 2 变身为高效的 Linux 开发本,涵盖 Ubuntu 20.04 双系统安装、专用内核配置、驱动优化等全流程。通过 linux-surface 内核安装和硬件驱动优化,确保 Surface Go 2 的触控、笔输入、摄像头等功能完美运行,适合开发者打造便携生产力工具。

weixin_30596165的博客 616

todo

1.burnside定理,polya计数法     这个大家可以看brudildi的《组合数学》,那本书的这一章写的很详细也很容易理解。最好能完全看懂了,理解了再去做题,不要只记个公式。     *简单题:(直接用套公式就可以了)     *强烈推荐:(这题很不错哦,很巧妙)     pku2888 Magic Bracelet     http://162.105.81.212/Jud

On my fighting way 4776

有限差分法地震数据正演模拟(二)

正演模拟,是在地球物理勘探研究中,根据地质体的形状、产状和物性数据,通过构造数学模型计算得到其理论值(数学模拟),或通过构造实体模型来观测模型所产生的地球物理效应的数值(物理模拟)。p(t+1,x,z)即为下一时刻的波长信息,该波动方程的意义就是通过前一时刻(p(t-1,x,z))和现在时刻(p(t,x,z))预测下一时刻波的传播情况。声波波动方程:反应声波的传播规律,描述最简单的波现象的方程,p代表波场信息,v表示速度场信息因为速度只与速度场有关,所以只与x,z有关。其结果也可以作为反演的验证。

weixin_46285501的博客 3935

servlet-filter(过滤器)

是。

CUITAO2305532402的博客 3878

YOLOv11改进 | Mamba-YOLOv11-L:基于SSM的高效全局建模,精度与效率的双重突破

摘要: 本文提出Mamba-YOLOv11-L,通过集成状态空间模型(SSM)改进YOLOv11的全局建模能力。针对YOLOv11在复杂场景中全局依赖缺失、精度-效率矛盾等问题,SSM以$O(N)$计算复杂度实现长程语义捕捉。改进后的模型在工业缺陷检测(Recall↑12%)、边缘设备部署(内存↓16%)、多尺度目标检测(小目标mAP↑9%)等场景表现优异,推理速度保持>40 FPS。核心创新包括轻量化SSM模块设计(稀疏状态转移+局部上下文融合)及与YOLOv11骨干的深度集成,代码实现展示了SSM

走向CTO的路上... 566

动态视频目标追踪系统:基于YOLOv11+DeepSORT的从入门到实战全流程指南

仅保留车辆类别(假设车辆类别ID为2)if det.class_index == 2: # 车辆类别ID通过本指南,你已完成从环境搭建数据准备模型训练到追踪系统与UI界面的全流程,搭建了一套完整的动态视频目标追踪系统。该系统在安防监控、交通管理等场景中具有实用价值,可实现目标的实时稳定追踪。未来,你可尝试结合多模态特征(如目标外观+运动特征)提升追踪鲁棒性,或探索轻量化模型部署(如TensorRT加速),让系统在边缘设备上也能高效运行。

LXY_LOVE36的博客 142

Servlet之Filter深入讲解及实例研究

Filter相关Servlet过滤器是在Java Servlet规范2.3中定义的,它能够对Servlet容器的请求和响应对象进行检查和修改,它在Servlet被调用之前检查Request对象,修改Request Header和Request内容;在Servlet被调用之后检查Response对象,修改Response Header和Response内容。Servlet过滤器负责过滤的Web组件可

Evankaka的专栏 5805

Redhawk:什么是timing window?

STA timing file中timing window的作用和计算方式

m0_61544122的博客 1万+

java servlet filter_Servlet之Filter详细讲解

Filter,过滤器,顾名思义,即是对数据等的过滤,预处理过程。为什么要引入过滤器呢?在平常访问网站的时候,有时候发一些敏感的信息,发出后显示时 就会将敏感信息用*等字符替代,这就是用过滤器对信息进行了处理。这只是一个简单的例子,当然,过滤器那么强大,它的功能也不可能局限于此,它不仅能预处 理数据,只要是发送过来的请求它都是可以预处理的,同时,它还可以对服务器返回的响应进行预处理,这样,大大减轻了...

weixin_39759890的博客 798

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

【Servlet】Filter深入讲解及实例研究

一、Filter    1、过滤器的概念 Java中的Filter 并不是一个标准的Servlet ,它不能处理用户请求,也不能对客户端生成响应。 主要用于对HttpServletRequest 进行预处理,也可以对HttpServletResponse 进行后处理,是个典型的处理链。 优点:过滤链的好处是,执行过程中任何时候都可以打断,只要不执行chain.do

编程高手无捷径 1016

Data-Structures-and-Algorithm-Analysis-in-Java.pdf

作者: Weiss, Mark A. 出版社: Addison Wesley Data Structures and Algorithm Analysis in Java is an “advanced algorithms” book that fits between traditional CS2 and Algorithms Analysis courses. In the old ACM Curriculum Guidelines, this course was known as CS7. This text is for readers who want to learn good programming and algorithm analysis skills simultaneously so that they can develop such programs with the maximum amo...

关于Servlet中的Filter使用的简单讲解

什么是过滤器: 过滤器是JavaWeb的三大组件之一,其余两大组件分别是Servlet程序,Listener监听器 过滤器其实就是JavaEE的规范,它是接口,所以我们一般使用过滤器的时候,我们使用的是继承 我们知道,用户登录之后都会把用户登录的信息保存到Session域中,所以要检查用户是否登录,可以判断Session中是否有登录信息,以此来达到未登录的时候,不能访问我们内部的数据 先来说说过滤器的整个工作流程 过滤器的使用步骤: Filter过滤器的使用步骤 1、编写一个类去实现Filter接口

weixin_44281208的博客 660

Servlet之Filter详细讲解(转)

转自:https://www.cnblogs.com/zlbx/p/4888312.html Filter,过滤器,顾名思义,即是对数据等的过滤,预处理过程。为什么要引入过滤器呢?在平常访问网站的时候,有时候发一些敏感的信息,发出后显示时 就会将敏感信息用*等字符替代,这就是用过滤器对信息进行了处理。这只是一个简单的例子,当然,过滤器那么强大,它的功能也不可能局限于此,它不仅能预处 理数据,只要是...

四问四不知的博客 700

javax.servlet.Filter过滤器讲解

一 、javax.servlet.Filter过滤器 过滤器(Filter)位于客户端和web应用程序之间,用于检查和修改两者之间流过的请求和响应。 在请求到达Servlet/JSP之前,过滤器截获请求。 在响应送给客户端之前,过滤器截获响应。 多个过滤器形成一个过滤器链,过滤器链中不同过滤器的先后顺序由部署文件web.xml中过滤器映射&lt;filter-mapping&gt;的顺序决定...

王延 1100

servlet Filter(过滤器)讲解一

Servlet Filter(过滤器) Filter简介 Filter也称之为过滤器,它是Servlet技术中最激动人心的技术,WEB开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp,Servlet, 静态图片文件或静态html 文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感词汇、压缩响应信息等一些高级功能。 Servlet

chuyuqing的专栏 1135
上一篇: Spring MVC控制层redirect
下一篇: request.getScheme()的使用方法 路径常用方法(重要)
周末去看海
博客等级 码龄9年 50粉丝 5原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值