Filter/Listener

本文深入讲解了Filter过滤器和Listener监听器的概念、创建步骤及在Web应用中的使用。包括过滤器的执行原理、生命周期,以及如何配置多个Servlet,监听器的实现方式和监听内容等。

Filter&Listener
第一章 Filter 过滤器
1-1 过滤器概述_画图说明过滤器执行原理
过滤字符编码
在这里插入图片描述

1-2编写过滤器的步骤_使用过滤器过滤字符编码
见代码注释
package com.buvu.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;

/*
*

  • 过滤器的创建步骤:
  • 1.创建一个普通的java类,实现javax.servlet.Filter接口
  • 2.重写doFilter方法
  •  该方法就是过滤中的用来处理过滤器业务的方法
    
  •  相当于servlet中的doGet/doPost方法
    
  • 3.修改方法中的变量名
  •  req resp chain
    
  • 4.完成过滤业务
  • 5.在web.xml中对过滤器进行配置工作
  •  配置在所有servlt的上方
    
  • 6.在执行完过滤业务之后,需要对请求进行放行操作

*/
public class Filter1 implements Filter{

/*@Override
public void init(FilterConfig filterConfig) throws ServletException {
	
	System.out.println("filter1对象创建了");
	
}*/

@Override
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain)
		throws IOException, ServletException {
	
	//完成字符编码的过滤
	System.out.println("进入到了Filter1");
	
	/*req.setCharacterEncoding("UTF-8");
	resp.setContentType("text/html;charset=utf-8");*/
	
	//将请求放行
	chain.doFilter(req, resp);
	
	//servlet响应回来  又经过了过滤器
	System.out.println("响应回来又经过了filter1");
	
}

/*@Override
public void destroy() {
	
	System.out.println("filter1对象销毁了");
	
}*/

}


package com.bh.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;

public class Filter2 implements Filter{

@Override
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain)
		throws IOException, ServletException {
	
	System.out.println("进入到了Filter2");
	
	
	//将请求放行
	chain.doFilter(req, resp);
	
	System.out.println("响应回来又经过了Filter2");
	
}

}

1-3 过滤器的生命周期(了解)
创建:启动服务器
销毁:关闭服务器

1-4过滤器中配置多个servlet的方式
在这里插入图片描述
1-5过滤器的url-pattern
与servlet一样,也有4种表现形式.
与servlet不同的是,如果我们发出的请求与多个filter的url-pattern都匹配,那么这些匹配的filter都执行(servlet只选择一个优先级高的执行),执行的顺为按照web.xml的上下的配置顺序来执行.

1-6过滤器链的作用
过滤器链:chain
执行过滤器链:chain.doFilter(req,resp)
过滤器链的作用是,当我们执行了过滤器链(执行放行代码),将请求放行的地点在于下面还有没有匹配的过滤器,如果有,则将请求放行到下一个匹配的过滤器,如果没有匹配的过滤器了,则将请求放行到目标servlet.

1-7 实战:使用过滤器拦截请求
拦截请求
在这里插入图片描述package com.wuwu.util;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

public class DBUtil {

private DBUtil(){}

static{
	
	try {
		Class.forName("com.mysql.jdbc.Driver");
	} catch (ClassNotFoundException e) {
		e.printStackTrace();
	}
	
}

private static final String url = "jdbc:mysql://localhost:3306/test";
private static final String user = "root";
private static final String password = "root";

//创建连接 返回连接
public static Connection getConn() throws SQLException{
	
	Connection conn = DriverManager.getConnection(url, user, password);
	
	return conn;
	
}


//关闭相关资源
public static void myClose(Connection conn,PreparedStatement ps,ResultSet rs) throws SQLException{
	
	//关闭资源的顺序为  按照创建的顺序 逆序关闭
	if(rs!=null){
		rs.close();
	}
	
	if(ps!=null){
		ps.close();
	}
	
	if(conn!=null){
		conn.close();
	}
	
}

}


package com.uu.filter;

import java.io.IOException;

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

public class LoginFilter implements Filter{

@Override
public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain)
		throws IOException, ServletException {
	
	System.out.println("在此过滤器中验证有没有登录过");
	
	/*
	 * 取得session对象
	 * 从session对象中取username
	 * 根据username是否为null,判断有没有登陆过
	 * 		不为null:登录过
	 * 		为null:没登录过
	 */
	
	/*
	 * 我们现在要用的是HttpServletRequest
	 * 我们现在有的是ServletRequest
	 * 
	 * 以上二者为子父接口的关系
	 * ServletRequest是父亲
	 * HttpServletRequest是儿子
	 * 
	 * 我们现在要用的是儿子
	 * 我们现在有的是父亲
	 * 
	 * 父亲转儿子的过程
	 * 
	 */
	HttpServletRequest request = (HttpServletRequest) req;
	HttpServletResponse response = (HttpServletResponse) resp;
	
	/*
	 * 判断请求路径
	 * 如果请求路径为/login.do,则自动放行请求
	 * 如果请求路径为其他xxx.do,则验证有没有登陆过
	 */
	
	//如何取得请求路径  url-pattern
	String path = request.getServletPath();
	System.out.println(path);
	if("/login.do".equals(path)){
		
		chain.doFilter(req, resp);
		
	}else{
		
		HttpSession session = request.getSession();
		String username = (String)session.getAttribute("username");
		
		//登录过
		if(username!=null){
			
			//将请求放行到目标servlet
			chain.doFilter(req, resp);
			
		//没登录过
		}else{
			
			//重定向到登录页
			response.sendRedirect(request.getContextPath() + "/login.jsp");
			
		}
		
		
	}
	
	
	
	
	
	
}

}


package com.wkcto.servlet;

import java.io.IOException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

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

import com.wkcto.util.DBUtil;

public class LoginServlet extends HttpServlet {

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	
	System.out.println("执行登录操作");
	
	response.setContentType("text/html;charset=utf-8");
	
	String username = request.getParameter("username");
	String password = request.getParameter("password");
	
	System.out.println(username);
	System.out.println(password);
	
	/*
	 * 账号密码成功的接收到了
	 * 接下来,连jdbc,去表中查看账号密码是否正确
	 */
	
	/*
	 * 将需要的变量事先都声明好
	 * 搭建jdbc相关的try catch finally 结构
	 * 在以上结构中填充代码
	 * 
	 */
	Connection conn = null;
	PreparedStatement ps = null;
	ResultSet rs = null;
	//查询一个东西有没有 使用查询条数count(*)是最快的
	String sql = "select count(*) from tbl_user where username=? and password=?";
	boolean flag = true;
	
	try{
		conn = DBUtil.getConn();
		ps = conn.prepareStatement(sql);
		/*
		 * ps对象创建完毕后,养成好习惯,观察你的sql语句,如果有?,需要使用ps对象为?赋值
		 */
		ps.setString(1,username);
		ps.setString(2,password);
		
		//执行sql语句 返回结果集
		rs = ps.executeQuery();
		
		if(rs.next()){
			
			//表示取得的是select关键字后面查询的第一项信息
			int count = rs.getInt(1);
			
			/*
			 * count:0 表示没有查询出来对应的账号和密码  登录失败
			 * count:1 表示查询出来了一条对应的账号和密码  登录成功
			 * count>1 表示查询到了,但是表中有多余的垃圾数据  登录失败
			 * 
			 */
			if(count!=1){
				flag = false;
			}
			
			
		}
		
		
	}catch(SQLException e){
		e.printStackTrace();
	}finally{
		
		try {
			DBUtil.myClose(conn, ps, rs);
		} catch (SQLException e) {
			e.printStackTrace();
		}
		
	}
	
	/*
	 * 以上就是完成了登录的业务逻辑,根据账号密码的正确与否来决定标记位flag是true还是false
	 * 以下我们就根据flag,来决定登录成功还是失败
	 */
	
	//登录成功
	if(flag){
		
		request.getSession().setAttribute("username",username);
	
		response.sendRedirect(request.getContextPath() + "/student/list.do");
		
	//登录失败	
	}else{
		
		
		response.sendRedirect(request.getContextPath() + "/login.jsp");
		
	}
	
	
}

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

}


package com.wkcto.servlet;

import java.io.IOException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import com.wkcto.util.DBUtil;

public class StudentAddServlet extends HttpServlet {

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	
	
	request.getRequestDispatcher("/WEB-INF/html/student/add.html").forward(request, response);
		
	
}

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

}


package com.wkcto.servlet;

import java.io.IOException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import com.wkcto.util.DBUtil;

public class StudentEditServlet extends HttpServlet {

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	
	
	request.getRequestDispatcher("/WEB-INF/html/student/edit.html").forward(request, response);
	
	
}

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

}


package com.wkcto.servlet;

import java.io.IOException;

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

public class StudentListServlet extends HttpServlet {

protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
	
	
	request.getRequestDispatcher("/WEB-INF/html/student/index.html").forward(request, response);
		
	
}

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

}


第二章 Listener 监听器(了解)
2-1什么是监听器
监听器就是一个java类,用来起到监听作用,当java中的其他组件或功能在发生变化时,所作出的提醒或操作。
2-2监听器都能监听什么
监听域对象的创建与销毁
监听域对象属性值创建更换与销毁
2-3 监听器的创建步骤
监听三个域对象的创建和销毁
ServletContextListener
ServletRequestListener
HttpSessionListener


package com.wkcto.listener;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;

/*
*

  • 创建监听器的步骤:
  • 1.创建一个普通的java类,实现监听接口
  •  监听什么就需要实现响应的接口
    
  •  比如我们现在要监听上下文对象的创建与销毁,那么我们就需要实现ServletContextListener这个接口
    
  • 2.重写监听方法
  • 3.将方法中的参数修改为event
  •  event的作用是可以取得监听到的域对象
    
  • 4.完成方法体
  • 5.将监听器在web.xml中进行配置
  •  配置的位置通常是在servlet的上面,filter的下面
    

*/
public class Listener1 implements ServletContextListener{

/*
 * 该方法用来监听上下文对象的创建
 * 如果上下文对象创建了,则马上执行该方法
 */
@Override
public void contextInitialized(ServletContextEvent event) {
	
	System.out.println("上下文对象创建了");
	
	
}

/*
 * 该方法用来监听上下文对象的销毁
 * 如果上下文对象销毁了,则马上执行该方法
 */
@Override
public void contextDestroyed(ServletContextEvent event) {
	
	System.out.println("上下文对象销毁了");
	
}

}


package com.wkcto.listener;

import javax.servlet.ServletRequestEvent;
import javax.servlet.ServletRequestListener;

public class Listener2 implements ServletRequestListener{

@Override
public void requestInitialized(ServletRequestEvent event) {
	
	System.out.println("request对象创建了");
	
}

@Override
public void requestDestroyed(ServletRequestEvent event) {
	
	System.out.println("request对象销毁了");
	
}

}


package com.wkcto.listener;

import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;

public class Listener3 implements HttpSessionListener{

@Override
public void sessionCreated(HttpSessionEvent event) {
	
	System.out.println("session对象创建了");
	
	
}

@Override
public void sessionDestroyed(HttpSessionEvent event) {
	
	System.out.println("session对象销毁了");
	
	
}

}

第二章 Listener 监听器(了解)
2-1什么是监听器
监听器就是一个java类,用来起到监听作用,当java中的其他组件或功能在发生变化时,所作出的提醒或操作。
2-2监听器都能监听什么
监听域对象的创建与销毁
监听域对象属性值创建更换与销毁
2-3 监听器的创建步骤
监听三个域对象的创建和销毁
ServletContextListener
ServletRequestListener
HttpSessionListener

<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" version="3.0"> <display-name></display-name> <context-param> <param-name>contextConfigLocation</param-name> <param-value> classpath*:applicationContext*.xml classpath*:*Context.xml </param-value> </context-param> <context-param> <param-name>webAppRootKey</param-name> <param-value>rms.root</param-value> </context-param> <context-param> <param-name>log4jConfigLocation</param-name> <param-value>/WEB-INF/classes/log4j.properties</param-value> </context-param> <context-param> <param-name>log4jRefreshInterval</param-name> <param-value>60</param-value> </context-param> <listener> <listener-class>org.springframework.web.util.Log4jConfigListener</listener-class> </listener> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <listener> <listener-class>com.hg.filter.UrlAuthListen</listener-class> </listener> <listener> <listener-class>com.hg.filter.WebConfigListener</listener-class> </listener> <filter> <filter-name>openSessionInViewFilter</filter-name> <filter-class>org.springframework.orm.hibernate4.support.OpenSessionInViewFilter </filter-class> <init-param> <param-name>singleSession</param-name> <param-value>true</param-value> </init-param> </filter> <filter-mapping> <filter-name>openSessionInViewFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> <filter> <filter-name>XssFilter</filter-name> <filter-class>com.hg.aop.XssFilter</filter-class> </filter> <filter-mapping> <filter-name>XssFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> <!-- dwr 配置 --> <servlet> <servlet-name>dwr-invoker</servlet-name> <servlet-class>org.directwebremoting.servlet.DwrServlet</servlet-class> <init-param> <param-name>debug</param-name> <param-value>true</param-value> </init-param> <init-param> <param-name>activeReverseAjaxEnabled</param-name> <param-value>true</param-value> </init-param> <init-param> <param-name>crossDomainSessionSecurity</param-name> <param-value>false</param-value> </init-param> <init-param> <description>How quickly do scriptSessions timeout?</description> <param-name>scriptSessionTimeout</param-name> <param-value>1800000</param-value> </init-param> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>dwr-invoker</servlet-name> <url-pattern>/dwr/*</url-pattern> </servlet-mapping> <listener> <listener-class>org.directwebremoting.servlet.EfficientShutdownServletContextAttributeListener</listener-class> </listener> <!-- dwr 配置 --> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app>具体解释一下web.xml的配置
最新发布
07-08
<think>好的,我现在需要解释用户提供的web.xml配置文件的具体内容。首先,我需要回忆一下web.xml的基本结构和各个元素的作用。用户提供的这个配置文件是一个标准的Java Web应用的部署描述符,版本是3.0,所以可能使用了一些Servlet 3.0的特性,但这里主要是传统的配置方式。 首先看根元素<web-app>,它的命名空间和schemaLocation指定了使用的规范版本,这里是3.0。接下来是<display-name>,这里为空,可能是应用的显示名称。 接下来是多个<context-param>元素,这些是上下文参数,由Servlet容器(如Tomcat)加载,供应用中的组件使用。第一个context-param的param-name是contextConfigLocation,param-value指定了Spring应用上下文的配置文件位置,这里包括classpath下所有以applicationContext开头的XML文件和所有以Context结尾的XML文件,这样Spring的ContextLoaderListener会加载这些配置来初始化ApplicationContext。 第二个context-param是webAppRootKey,设置为rms.root,这通常用于将Web应用的根路径(如Tomcat的webapps下的应用目录)设置为一个系统属性,方便其他组件(如日志配置)引用,例如log4j中可能用${rms.root}获取路径。 第三个和第四个context-param是log4j的配置,log4jConfigLocation指定log4j的配置文件路径在/WEB-INF/classes/log4j.properties,log4jRefreshInterval设置为60秒,即每隔60秒自动刷新log4j的配置,这样修改日志配置后不需要重启应用。 接下来是<listener>元素,定义了多个监听器。第一个是Log4jConfigListener,用于初始化log4j的配置,读取前面的log4j相关context-param。第二个是ContextLoaderListener,这是Spring的监听器,负责根据contextConfigLocation加载Spring的应用上下文,是Spring Web应用的核心监听器。后面两个监听器是自定义的,com.hg.filter.UrlAuthListen和WebConfigListener,可能用于URL权限验证和Web配置初始化。 然后是<filter>和<filter-mapping>配置。第一个filter是openSessionInViewFilter,类是Spring ORM Hibernate4的OpenSessionInViewFilter,用于解决Hibernate的“延迟加载在视图层失败”的问题。设置singleSession为true,表示每个请求使用一个Hibernate Session,通常在Web应用中用于在请求处理期间保持Session打开,直到视图渲染完成。 第二个filter是struts2的StrutsPrepareAndExecuteFilter,这是Struts 2的核心过滤器,负责处理所有请求,解析Action、执行拦截器链等,url-pattern为/*,表示所有请求都由Struts处理。 第三个filter是自定义的XssFilter(跨站脚本攻击过滤器),类是com.hg.aop.XssFilter,用于过滤请求中的XSS攻击,例如转义特殊字符,保护应用安全,同样映射到所有URL。 接下来是dwr(Direct Web Remoting)的配置,这是一个用于Java和JavaScript互操作的库。定义了一个名为dwr-invoker的Servlet,类是DwrServlet,配置了debug模式(允许调试)、activeReverseAjaxEnabled(启用反向Ajax,服务器向客户端推送)、crossDomainSessionSecurity(跨域会话安全,这里设为false)、scriptSessionTimeout(脚本会话超时时间,1800000毫秒即30分钟)。load-on-startup设置为1,表示Servlet容器启动时立即加载这个Servlet。servlet-mapping将/dwr/*的请求映射到这个Servlet,处理DWR相关的请求。同时还有一个EfficientShutdownServletContextAttributeListener监听器,用于DWR的高效关闭,释放资源。 最后是<welcome-file-list>,指定默认的欢迎文件为index.jsp,当访问应用根路径时,会默认访问这个文件。 现在需要检查是否有遗漏的部分,比如各个元素的作用是否解释清楚,特别是监听器、过滤器、Servlet的配置目的。另外,需要注意一些细节,比如openSessionInViewFilter的作用,Struts2过滤器的职责,XssFilter的用途,DWR的配置参数含义等。确保每个配置项的解释准确,并且符合Web应用开发的常见实践。 </think> 这个`web.xml`是Java Web应用的部署描述符(Servlet 3.0版本),定义了应用的初始化参数、监听器、过滤器、Servlet及欢迎文件等配置。以下是各部分的详细解释: ### **1. 根元素基本信息** ```xml <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" version="3.0"> ``` - 声明使用Servlet 3.0规范,`xsi:schemaLocation`指定了XML模式文件的位置,用于验证配置格式。 ### **2. 上下文参数(`<context-param>`)** 上下文参数由Servlet容器(如Tomcat)加载,供全局组件(如监听器、过滤器)使用。 #### (1)`contextConfigLocation` ```xml <context-param> <param-name>contextConfigLocation</param-name> <param-value> classpath*:applicationContext*.xml classpath*:*Context.xml </param-value> </context-param> ``` - **作用**:指定Spring应用上下文(`ApplicationContext`)的配置文件路径。 - **含义**:加载类路径(`classpath`)下所有以`applicationContext`开头或包含`Context`的XML文件(如`applicationContext-datasource.xml`、`springContext.xml`),用于初始化Spring IoC容器。 #### (2)`webAppRootKey` ```xml <context-param> <param-name>webAppRootKey</param-name> <param-value>rms.root</param-value> </context-param> ``` - **作用**:将Web应用的根路径(如`/usr/local/tomcat/webapps/应用名/`)设置为系统属性,供其他组件(如日志框架)引用。 - **示例**:在`log4j.properties`中可通过`${rms.root}`获取应用根路径。 #### (3)`log4jConfigLocation` `log4jRefreshInterval` ```xml <context-param> <param-name>log4jConfigLocation</param-name> <param-value>/WEB-INF/classes/log4j.properties</param-value> </context-param> <context-param> <param-name>log4jRefreshInterval</param-name> <param-value>60</param-value> </context-param> ``` - **作用**:配置Log4j日志框架的属性文件路径及自动刷新间隔。 - **含义**: - `log4jConfigLocation`:指定Log4j配置文件路径为`/WEB-INF/classes/log4j.properties`(通常存放类路径下的资源)。 - `log4jRefreshInterval`:设置日志配置的自动刷新间隔为60秒,修改`log4j.properties`后无需重启应用即可生效。 ### **3. 监听器(`<listener>`)** 监听器用于监听Servlet容器的生命周期事件(如应用启动/销毁)。 #### (1)`Log4jConfigListener` ```xml <listener> <listener-class>org.springframework.web.util.Log4jConfigListener</listener-class> </listener> ``` - **作用**:初始化Log4j日志框架,读取前面定义的`log4jConfigLocation`和`log4jRefreshInterval`参数,完成日志配置的加载和定时刷新。 #### (2)`ContextLoaderListener` ```xml <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> ``` - **作用**:Spring的核心监听器,负责根据`contextConfigLocation`参数加载Spring应用上下文(`ApplicationContext`),是SpringWeb容器集成的关键。 #### (3)自定义监听器(`UrlAuthListen`、`WebConfigListener`) ```xml <listener> <listener-class>com.hg.filter.UrlAuthListen</listener-class> </listener> <listener> <listener-class>com.hg.filter.WebConfigListener</listener-class> </listener> ``` - **作用**:用户自定义的监听器,可能用于: - `UrlAuthListen`:URL权限校验(如应用启动时加载权限规则)。 - `WebConfigListener`:Web应用初始化配置(如加载全局参数、缓存初始化)。 #### (4)DWR的`EfficientShutdownServletContextAttributeListener` ```xml <listener> <listener-class>org.directwebremoting.servlet.EfficientShutdownServletContextAttributeListener</listener-class> </listener> ``` - **作用**:DWR(Direct Web Remoting)库的监听器,用于在应用销毁时高效释放DWR相关资源(如反向Ajax连接)。 ### **4. 过滤器(`<filter>``<filter-mapping>`)** 过滤器用于拦截请求/响应,执行预处理或后处理逻辑。 #### (1)`OpenSessionInViewFilter`(Hibernate会话管理) ```xml <filter> <filter-name>openSessionInViewFilter</filter-name> <filter-class>org.springframework.orm.hibernate4.support.OpenSessionInViewFilter</filter-class> <init-param> <param-name>singleSession</param-name> <param-value>true</param-value> </init-param> </filter> <filter-mapping> <filter-name>openSessionInViewFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> ``` - **作用**:解决Hibernate的“延迟加载在视图层失败”问题(`LazyInitializationException`)。 - **原理**:在HTTP请求开始时打开Hibernate `Session`,请求结束时关闭,确保视图渲染(如JSP)时仍可访问延迟加载的关联对象。 - `singleSession=true`:每个请求使用一个共享的`Session`(默认行为)。 #### (2)Struts 2核心过滤器(`StrutsPrepareAndExecuteFilter`) ```xml <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> ``` - **作用**:Struts 2框架的核心过滤器,负责处理所有HTTP请求,完成以下任务: - 解析请求URL,匹配对应的Action。 - 执行拦截器链(如参数绑定、验证)。 - 调用Action的业务逻辑。 - 转发到结果视图(如JSP、Freemarker)。 - `url-pattern=/*`:所有请求(包括静态资源)都由Struts处理(需注意静态资源过滤配置,避免被错误拦截)。 #### (3)自定义XSS过滤器(`XssFilter`) ```xml <filter> <filter-name>XssFilter</filter-name> <filter-class>com.hg.aop.XssFilter</filter-class> </filter> <filter-mapping> <filter-name>XssFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> ``` - **作用**:防御跨站脚本攻击(XSS),对请求参数、请求体中的恶意脚本(如`<script>`标签)进行转义或过滤。 - **实现逻辑**:通常通过重写`HttpServletRequest`的`getParameter()`等方法,对输入内容进行安全处理。 ### **5. DWR Servlet配置** DWR(Direct Web Remoting)是一个允许Java代码在浏览器端通过JavaScript调用的库,用于简化前后端交互。 #### (1)`dwr-invoker` Servlet定义 ```xml <servlet> <servlet-name>dwr-invoker</servlet-name> <servlet-class>org.directwebremoting.servlet.DwrServlet</servlet-class> <init-param> <param-name>debug</param-name> <param-value>true</param-value> </init-param> <init-param> <param-name>activeReverseAjaxEnabled</param-name> <param-value>true</param-value> </init-param> <init-param> <param-name>crossDomainSessionSecurity</param-name> <param-value>false</param-value> </init-param> <init-param> <param-name>scriptSessionTimeout</param-name> <param-value>1800000</param-value> </init-param> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>dwr-invoker</servlet-name> <url-pattern>/dwr/*</url-pattern> </servlet-mapping> ``` - **核心参数解释**: - `debug=true`:启用DWR调试模式(开发阶段使用,生产环境应关闭)。 - `activeReverseAjaxEnabled=true`:启用反向Ajax(服务器主动向客户端推送消息)。 - `crossDomainSessionSecurity=false`:关闭跨域会话安全校验(允许跨域请求)。 - `scriptSessionTimeout=1800000`:设置DWR脚本会话的超时时间为30分钟(单位:毫秒)。 - `load-on-startup=1`:Servlet容器启动时立即加载此Servlet(优先级较高)。 - **映射路径**:所有`/dwr/*`的请求由`DwrServlet`处理(如`/dwr/engine.js`用于加载DWR客户端脚本)。 ### **6. 欢迎文件列表(`<welcome-file-list>`)** ```xml <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> ``` - **作用**:当访问应用根路径(如`http://localhost:8080/应用名/`)时,默认跳转的页面为`index.jsp`。 ### 总结 此`web.xml`整合了Spring、Struts 2、Hibernate、Log4j、DWR等框架,定义了应用的初始化参数、监听器(用于框架启动和资源管理)、过滤器(用于请求处理和安全防护)、Servlet(用于DWR交互)及默认访问页面,是传统Java EE Web应用的典型配置。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值