javaweb中Filter(过滤器)的常见应用

一、统一全站字符编码

通过配置参数charset指明使用何种字符编码,以处理Html Form请求参数的中文问题

package me.gacl.web.filter;

import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
import javax.servlet.http.HttpServletResponse;

/**
* @ClassName: CharacterEncodingFilter
* @Description: 此过滤器用来解决全站中文乱码问题
*/
public class CharacterEncodingFilter implements Filter {

  private FilterConfig filterConfig = null;
  //设置默认的字符编码
  private String defaultCharset = "UTF-8";

  public void doFilter(ServletRequest req, ServletResponse resp,
      FilterChain chain) throws IOException, ServletException {

    HttpServletRequest request = (HttpServletRequest) req;
    HttpServletResponse response = (HttpServletResponse) resp;
    String charset = filterConfig.getInitParameter("charset");
    if(charset==null){
      charset = defaultCharset;
    }
    request.setCharacterEncoding(charset);
    response.setCharacterEncoding(charset);
    response.setContentType("text/html;charset="+charset);

    MyCharacterEncodingRequest requestWrapper = new MyCharacterEncodingRequest(request);
    chain.doFilter(requestWrapper, response);
  }

  public void init(FilterConfig filterConfig) throws ServletException {
    //得到过滤器的初始化配置信息
    this.filterConfig = filterConfig;
  }

  public void destroy() {

  }
}

/*
1.实现与被增强对象相同的接口
2、定义一个变量记住被增强对象
3、定义一个构造器,接收被增强对象
4、覆盖需要增强的方法
5、对于不想增强的方法,直接调用被增强对象(目标对象)的方法
 */

class MyCharacterEncodingRequest extends HttpServletRequestWrapper{

  private HttpServletRequest request;
  public MyCharacterEncodingRequest(HttpServletRequest request) {
    super(request);
    this.request = request;
  }
  /* 重写getParameter方法
   * @see javax.servlet.ServletRequestWrapper#getParameter(java.lang.String)
   */
  @Override
  public String getParameter(String name) {

    try{
      //获取参数的值
      String value= this.request.getParameter(name);
      if(value==null){
        return null;
      }
      //如果不是以get方式提交数据的,就直接返回获取到的值
      if(!this.request.getMethod().equalsIgnoreCase("get")) {
        return value;
      }else{
        //如果是以get方式提交数据的,就对获取到的值进行转码处理
        value = new String(value.getBytes("ISO8859-1"),this.request.getCharacterEncoding());
        return value;
      }
    }catch (Exception e) {
      throw new RuntimeException(e);
    }
  }
}

web.xml文件中的配置如下:

<filter>
   <filter-name>CharacterEncodingFilter</filter-name>
   <filter-class>me.gacl.web.filter.CharacterEncodingFilter</filter-class>
   <init-param>
     <param-name>charset</param-name>
     <param-value>UTF-8</param-value>
   </init-param>
 </filter>

 <filter-mapping>
   <filter-name>CharacterEncodingFilter</filter-name>
   <url-pattern>/*</url-pattern>
 </filter-mapping>

二、禁止浏览器缓存所有动态页面
  有3 个HTTP 响应头字段都可以禁止浏览器缓存当前页面,它们在 Servlet 中的示例代码如下:

  • response.setDateHeader("Expires",-1);
  • response.setHeader("Cache-Control","no-cache");
  • response.setHeader("Pragma","no-cache");

  并不是所有的浏览器都能完全支持上面的三个响应头,因此最好是同时使用上面的三个响应头。

  • Expires数据头:值为GMT时间值,为-1指浏览器不要缓存页面
  • Cache-Control响应头有两个常用值:
  • no-cache指浏览器不要缓存当前页面。
  • max-age:xxx指浏览器缓存页面xxx秒。
package me.gacl.web.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
* @ClassName: NoCacheFilter
* @Description: 禁止浏览器缓存所有动态页面
* @author: 孤傲苍狼
* @date: 2014-8-31 下午11:25:40
*
*/
public class NoCacheFilter implements Filter {

  public void doFilter(ServletRequest req, ServletResponse resp,
      FilterChain chain) throws IOException, ServletException {
    //把ServletRequest强转成HttpServletRequest
    HttpServletRequest request = (HttpServletRequest) req;
    //把ServletResponse强转成HttpServletResponse
    HttpServletResponse response = (HttpServletResponse) resp;
    //禁止浏览器缓存所有动态页面
    response.setDateHeader("Expires", -1);
    response.setHeader("Cache-Control", "no-cache");
    response.setHeader("Pragma", "no-cache");

    chain.doFilter(request, response);
  }

  public void init(FilterConfig filterConfig) throws ServletException {

  }

  public void destroy() {

  }
}

web.xml文件中的配置如下:

<filter>
   <filter-name>NoCacheFilter</filter-name>
   <filter-class>me.gacl.web.filter.NoCacheFilter</filter-class>
 </filter>

 <filter-mapping>
   <filter-name>NoCacheFilter</filter-name>
    <!--只拦截Jsp请求-->
   <servlet-name>*.jsp</servlet-name>
 </filter-mapping>

三、控制浏览器缓存页面中的静态资源

  有些动态页面中引用了一些图片或css文件以修饰页面效果,这些图片和css文件经常是不变化的,所以为减轻服务器的压力,可以使用filter控制浏览器缓存这些文件,以提升服务器的性能。

package me.gacl.web.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
* @ClassName: CacheFilter
* @Description: 控制缓存的filter
*/
public class CacheFilter implements Filter {

  private FilterConfig filterConfig;

  public void doFilter(ServletRequest req, ServletResponse resp,
      FilterChain chain) throws IOException, ServletException {

    HttpServletRequest request = (HttpServletRequest) req;
    HttpServletResponse response = (HttpServletResponse) resp;

    //1.获取用户想访问的资源
    String uri = request.getRequestURI(); 

    //2.得到用户想访问的资源的后缀名
    String ext = uri.substring(uri.lastIndexOf(".")+1);

    //得到资源需要缓存的时间
    String time = filterConfig.getInitParameter(ext);
    if(time!=null){
      long t = Long.parseLong(time)*3600*1000;
      //设置缓存
      response.setDateHeader("expires", System.currentTimeMillis() + t);
    }

    chain.doFilter(request, response);

  }

  public void init(FilterConfig filterConfig) throws ServletException {
    this.filterConfig = filterConfig;
  }

  public void destroy() {

  }
}

web.xml文件中的配置如下:

<!-- 配置缓存过滤器 -->
  <filter>
   <filter-name>CacheFilter</filter-name>
   <filter-class>me.gacl.web.filter.CacheFilter</filter-class>
    <!-- 配置要缓存的web资源以及缓存时间,以小时为单位 -->
   <init-param>
     <param-name>css</param-name>
     <param-value>4</param-value>
   </init-param>
   <init-param>
     <param-name>jpg</param-name>
     <param-value>1</param-value>
   </init-param>
   <init-param>
     <param-name>js</param-name>
     <param-value>4</param-value>
   </init-param>
   <init-param>
     <param-name>png</param-name>
     <param-value>4</param-value>
   </init-param>
 </filter>
 <!-- 配置要缓存的web资源的后缀-->
 <filter-mapping>
   <filter-name>CacheFilter</filter-name>
   <url-pattern>*.jpg</url-pattern>
 </filter-mapping>

 <filter-mapping>
   <filter-name>CacheFilter</filter-name>
   <url-pattern>*.css</url-pattern>
 </filter-mapping>

 <filter-mapping>
   <filter-name>CacheFilter</filter-name>
   <url-pattern>*.js</url-pattern>
 </filter-mapping>
  <filter-mapping>
   <filter-name>CacheFilter</filter-name>
   <url-pattern>*.png</url-pattern>
 </filter-mapping>

四、实现用户自动登陆

思路是这样的:

  1、在用户登陆成功后,发送一个名称为user的cookie给客户端,cookie的值为用户名和md5加密后的密码。
  2、编写一个AutoLoginFilter,这个filter检查用户是否带有名称为user的cookie来,如果有,则调用dao查询cookie的用户名和密码是否和数据库匹配,匹配则向session中存入user对象(即用户登陆标记),以实现程序完成自动登陆。

核心代码如下:

处理用户登录的控制器:LoginServlet

package me.gacl.web.controller;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import me.gacl.dao.UserDao;
import me.gacl.domain.User;
import me.gacl.util.WebUtils;

public class LoginServlet extends HttpServlet {

  public void doGet(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {

    String username = request.getParameter("username");
    String password = request.getParameter("password");

    UserDao dao = new UserDao();
    User user = dao.find(username, password);
    if(user==null){
      request.setAttribute("message", "用户名或密码不对!!");
      request.getRequestDispatcher("/message.jsp").forward(request, response);
      return;
    }
    request.getSession().setAttribute("user", user);
    //发送自动登陆cookie给客户端浏览器进行存储
    sendAutoLoginCookie(request,response,user);
    request.getRequestDispatcher("/index.jsp").forward(request, response);
  }

  /**
  * @Method: sendAutoLoginCookie
  * @Description: 发送自动登录cookie给客户端浏览器
  * @param request
  * @param response
  * @param user
  */
  private void sendAutoLoginCookie(HttpServletRequest request, HttpServletResponse response, User user) {
    if (request.getParameter("logintime")!=null) {
      int logintime = Integer.parseInt(request.getParameter("logintime"));
      //创建cookie,cookie的名字是autologin,值是用户登录的用户名和密码,用户名和密码之间使用.进行分割,密码经过md5加密处理
      Cookie cookie = new Cookie("autologin",user.getUsername() + "." + WebUtils.md5(user.getPassword()));
      //设置cookie的有效期
      cookie.setMaxAge(logintime);
      //设置cookie的有效路径
      cookie.setPath(request.getContextPath());
      //将cookie写入到客户端浏览器
      response.addCookie(cookie);
    }
  }

  public void doPost(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {

    doGet(request, response);
  }

}

处理用户自动登录的过滤器:AutoLoginFilter

package me.gacl.web.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import me.gacl.dao.UserDao;
import me.gacl.domain.User;
import me.gacl.util.WebUtils;

public class AutoLoginFilter implements Filter {

  public void doFilter(ServletRequest req, ServletResponse resp,
      FilterChain chain) throws IOException, ServletException {

    HttpServletRequest request = (HttpServletRequest) req;
    HttpServletResponse response = (HttpServletResponse) resp;
    //如果已经登录了,就直接chain.doFilter(request, response)放行
    if(request.getSession().getAttribute("user")!=null){
      chain.doFilter(request, response);
      return;
    }

    //1.得到用户带过来的authlogin的cookie
    String value = null;
    Cookie cookies[] = request.getCookies();
    for(int i=0;cookies!=null && i<cookies.length;i++){
      if(cookies[i].getName().equals("autologin")){
        value = cookies[i].getValue();
      }
    }

    //2.得到 cookie中的用户名和密码
    if(value!=null){
      String username = value.split("\\.")[0];
      String password = value.split("\\.")[1];

      //3.调用dao获取用户对应的密码
      UserDao dao = new UserDao();
      User user = dao.find(username);
      String dbpassword = user.getPassword();

      //4.检查用户带过来的md5的密码和数据库中的密码是否匹配,如匹配则自动登陆
      if(password.equals(WebUtils.md5(dbpassword))){
        request.getSession().setAttribute("user", user);
      }
    }

    chain.doFilter(request, response);
  }

  public void destroy() {

  }

  public void init(FilterConfig filterConfig) throws ServletException {

  }
}

如果想取消自动登录,那么可以在用户注销时删除自动登录cookie,核心代码如下:

package me.gacl.web.controller;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class CancelAutoLoginServlet extends HttpServlet {

  public void doGet(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {
    //移除存储在session中的user
    request.getSession().removeAttribute("user");
    //移除自动登录的cookie
    removeAutoLoginCookie(request,response);
    //注销用户后跳转到登录页面
    request.getRequestDispatcher("/login.jsp").forward(request, response);
  }

  /**
  * @Method: removeAutoLoginCookie
  * @Description: 删除自动登录cookie,
  * JavaWeb中删除cookie的方式就是新创建一个cookie,新创建的cookie与要删除的cookie同名,
  * 设置新创建的cookie的cookie的有效期设置为0,有效路径与要删除的cookie的有效路径相同
  * @param request
  * @param response
  */
  private void removeAutoLoginCookie(HttpServletRequest request, HttpServletResponse response) {
    //创建一个名字为autologin的cookie
    Cookie cookie = new Cookie("autologin","");
     //将cookie的有效期设置为0,命令浏览器删除该cookie
    cookie.setMaxAge(0);
    //设置要删除的cookie的path
    cookie.setPath(request.getContextPath());
    response.addCookie(cookie);
  }

  public void doPost(HttpServletRequest request, HttpServletResponse response)
      throws ServletException, IOException {
    doGet(request, response);
  }
}

以上就是过滤器的几个常见应用场景,希望对大家的学习有所帮助。

(0)

相关推荐

  • java web过滤器处理乱码

    我们在servlet页面中读取前台的数据时  经常会出现乱码问题 而自己每次都要在servlet中使用 String encoding="utf-8"; request.setCharacterEncoding(enconding); response.setCharacterEncoding(enconding); 来进行编码的转换  会很麻烦 所以使用过滤器 我们可以避免这些重复的工作 web.xml配置 <filter> <filter-name>enco

  • Java Web过滤器详解

    过滤器是什么玩意? 所谓过滤器,其实就是一个服务端组件,用来截取用户端的请求与响应信息. 过滤器的应用场景: 1.对用户请求进行统一认证,保证不会出现用户账户安全性问题 2.编码转换,可在服务端的过滤器中设置统一的编码格式,避免出现乱码 3.对用户发送的数据进行过滤替换 4.转换图像格式 5.对响应的内容进行压缩 其中,第1,2场景经常涉及. login.jsp <%@ page language="java" import="java.util.*" con

  • 传智播客java web 过滤器

    根本不利于使用,Servlet应该本是为简化工作而创造的啊!我当时觉得是我的设计框架产生了问题.第二天我便问方老师,确实是使用上有些问题.比如,显示访问计数,我把它单独写成了一个Servlet,什么地方需要它时,便由那个Servlet.include引用计数的Servlet.但这样总会产生一些问题和使用上的不便.比如include的Servlet必须使用相同的流,如果使用forward后任何输出都无效了. 方老师当时建议,把有些功能写到一起.但最后提到了过滤器,那时我便对过滤器产生了兴趣,今日也

  • Java Web Filter 过滤器学习教程(推荐)

    一.Filter简介 Filter也称之为过滤器,它是Servlet技术中最激动人心的技术,WEB开发人员通过Filter技术,对web服务器管理的所有web资源:例如Jsp, Servlet, 静态图片文件或静态 html 文件等进行拦截,从而实现一些特殊的功能.例如实现URL级别的权限访问控制.过滤敏感词汇.压缩响应信息等一些高级功能. Servlet API中提供了一个Filter接口,开发web应用时,如果编写的Java类实现了这个接口,则把这个java类称之为过滤器Filter.通过F

  • Java web过滤器验证登录防止未登录进入界面

    今天用ssh2写了个简单的系统,发现了一个问题,我这系统必须先登录成功才能进入主页,但我在浏览器里直接输入主页地址,发现也能进入,这个肯定不好,毫无安全性可言,后经查资料发现需要登录过滤器,就试了下,发现果然可以避免未经登录即可进入主页的危险,下面是我整理出的详细步骤: 1.首先写一个权限过滤filter类,实现Filter接口 import java.io.IOException; import javax.servlet.Filter; import javax.servlet.Filter

  • JavaWeb之Filter过滤器详解

    原本计划这一篇来总结JSP,由于JSP的内容比较多,又想着晚上跑跑步减减肥,所以今天先介绍Filter以及它的使用举例,这样的话还有些时间可以锻炼锻炼.言归正传,过滤器从字面理解她的话有拦网.过滤的功能,可以算是JavaWeb的拦精灵. 一.由来 客户端发起请求,那服务器不能什么请求都做出响应,做拦截处理,不仅能减轻服务器的压力,还能保护数据的安全,同样服务端做出响应给客户端时有时也需要进行过滤,比如我们常见的图片添加水印.为了处理这些问题,于是过滤器出现了.有时不仅仅对请求与响应进行一层的过滤

  • javaweb中Filter(过滤器)的常见应用

    一.统一全站字符编码 通过配置参数charset指明使用何种字符编码,以处理Html Form请求参数的中文问题 package me.gacl.web.filter; import java.io.IOException; import javax.servlet.Filter; import javax.servlet.FilterChain; import javax.servlet.FilterConfig; import javax.servlet.ServletException;

  • 详解JavaWeb中的过滤器Filter

    一.什么是过滤器 1.Filter过滤器的作用:拦截请求 2.拦截请求常见场景: (1)权限检查 (2)日记操作 (3)事务管理 1.1 使用步骤 Filter 过滤器的使用步骤: 1.编写一个类去实现Filter 接口 2.实现过滤方法doFilter() 3.到web.xml 中去配置Filter 的拦截路径 二.初体验 web工程下新建一个admin目录,作为需要权限才能访问的目录,其中有两个文件 2.1 mynav.html <!DOCTYPE html> <html lang=

  • JavaWeb Servlet中Filter过滤器的详解

    JavaWeb Servlet中Filter过滤器的详解 1.简述 Filter过滤器,对web服务器所有web资源进行过滤,从而实现一些特殊的功能(权限访问控制.过滤敏感词汇.压缩响应信息).Filter能够对Servlet容器的请求和响应进行检查和修改,其本身不能生成请求request和响应response,只提供过滤作用(Servlet被调用之前检查Request对象修改其相关信息,Servlet被调用后检查Response修改其相关信息),Filter对象常驻服务器. 2.Lifecyc

  • Yii控制器中filter过滤器用法分析

    本文实例讲述了Yii控制器中filter过滤器用法.分享给大家供大家参考,具体如下: 指定过滤动作,(如下projectContext()方法在新建,列表,管理页面调用时使用) public function filters() { return array( 'accessControl', // perform access control for CRUD operations 'postOnly + delete', // we only allow deletion via POST

  • 详解AngularJS中$filter过滤器使用(自定义过滤器)

    1.内置过滤器 * $filter 过滤器,是angularJs中用来处理数据以更好的方式展示给我用户.比如格式化日期,转换大小写等等. * 过滤器即有内置过滤器也支持自定义过滤器.内置过滤器很多,可以百度.关键是如何使用: * 1.在HTML中直接使用内置过滤器 * 2.在js代码中使用内置过滤器 * 3.自定义过滤器 * * (1)常用内置过滤器 * number 数字过滤器,可以设置保留数字小数点后几位等 * date 时间格式化过滤器,可自己设置时间格式 * filter 过滤的数据一般

  • Quarkus中filter过滤器跨域cors问题解决方案

    目录 前言 web依赖 过滤器filter开发 resteasy的filter vertx的filter Quarkus中的跨域 前言 Quarkus中的web模块是基于java标准web规范jax-rs构建的,实现则选用了jboss的resteasy.这部分只是请求路由转发部分实现.真正的请求接收则使用了eclipse开源的vert.x框架,底层也是基于netty的一个响应式开发框架.Quarkus将vert.x和resteasy集成在了一起,所以支持响应式和非响应式应用混合开发,这也是Qua

  • java中Filter过滤器处理中文乱码的方法

    注意问题:在学习用selvert的过滤器filter处理中文乱码时,在filter配置初始化时用了utf-8处理中文乱码,而在提交的jsp页面中却用了gbk.虽然两种都可以出来中文乱码,但是却造成了处理乱码的格式不一致.所以编译出错. 解决方法:所有地方都用utf-8或gbk 复制代码 代码如下: //过滤器类CharactorFilter.jsppackage cn.com.Filter; import java.io.IOException; import javax.servlet.Fil

  • Java中filter用法完整代码示例

    本文研究的主要是Java中filter过滤器的相关用法,具体实现代码如下. filter过滤器主要使用于前台向后台传递数据是的过滤操作.程度很简单就不说明了,直接给几个已经写好的代码: 一.使浏览器不缓存页面的过滤器 import javax.servlet.*; import javax.servlet.http.HttpServletResponse; import java.io.IOException; /** * 用于的使 Browser 不缓存页面的过滤器 */ public cla

  • JavaWeb中过滤器Filter的用法详解

    目录 过滤器Filter 处理顺序 使用场景 自定义过滤器 源码分析 FilterDef FilterMap 初始化过滤器 创建过滤器链 ApplicationFilterChain 执行过滤器链 过滤器Filter 过滤器通常对一些web资源进行拦截,做完一些处理器再交给下一个过滤器处理,直到所有的过滤器处理器,再调用servlet实例的service方法进行处理.过滤器可以对request进行处理也可以对response进行处理. 处理顺序 如果过滤器链顺序如上图所示,那么对request请

随机推荐