JavaWeb(Filter-全站乱码问题 Listener 注解-连接数据库)

Filter过滤器

web中的过滤器:
	当访问服务器的资源时,过滤器可以将请求拦截下来,完成一些特殊的功能
过滤器的作用:
    一般用于完成通用的操作
    如:登录验证、统一编码处理、敏感字符过滤...

快速入门

步骤:
    1. 定义一个类,实现接口Filter
    2. 复写方法
    3. 配置拦截路径
        web.xml
        注解

@WebFilter("/*")//访问所有资源之前,都会执行该过滤器
public class MyFilter implements Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
       //init:在服务器启动后,会创建Filter对象,然后调用init方法。
       //只执行一次。用于加载资源
    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        //做业务逻辑
        //放行
        filterChain.doFilter(servletRequest, servletResponse);
    }

    @Override
    public void destroy() {
        //destroy:在服务器关闭后,Filter对象被销毁。
        //如果服务器是正常关闭,则会执行destroy方法。
        //只执行一次。用于释放资源
    }
}

过滤器细节

1. web.xml配置	
    <filter>
     	<!-- 配置过滤器名称 -->
        <filter-name>myFilter</filter-name>
         <!-- 配置过滤器的全路径 -->
        <filter-class>com.edu.filter.MyFilter</filter-class>
    </filter>
    <filter-mapping>
        <filter-name>myFilter</filter-name>
        <!-- 拦截路径 -->
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    
2. 过滤器执行流程
    a. 执行过滤器
    b. 执行放行后的资源
    c. 回来执行过滤器放行代码下边的代码
    
3. 过滤器生命周期方法
    a. init
    	在服务器启动后,会创建Filter对象,然后调用init方法。
    	只执行一次。用于加载资源
    b. doFilter
    	每一次请求被拦截资源时,会执行。
    	执行多次
    c. destroy
    	在服务器关闭后,Filter对象被销毁。
    	如果服务器是正常关闭,则会执行destroy方法。
    	只执行一次。用于释放资源

4. 过滤器配置详解
    拦截路径配置:
        a. 具体资源路径:/index.jsp   
        	只有访问index.jsp资源时,过滤器才会被执行
        b. 拦截目录:/user/*	
        	访问/user下的所有资源时,过滤器都会被执行
        c. 后缀名拦截:*.jsp		
        	访问所有后缀名为jsp资源时,过滤器都会被执行
        d. 拦截所有资源:/*
        	访问所有资源时,过滤器都会被执行
        	
	拦截方式配置:
		资源被访问的方式
	
	注解配置:
		设置dispatcherTypes属性
            a. REQUEST:默认值。浏览器直接请求资源
            b. FORWARD:转发访问资源
            c. INCLUDE:包含访问资源
            d. ERROR:错误跳转资源
            e. ASYNC:异步访问资源
	web.xml配置
		设置<dispatcher></dispatcher>标签即可

5. 过滤器链(配置多个过滤器)
	执行顺序:如果有两个过滤器:过滤器1和过滤器2
        a. 过滤器1
        b. 过滤器2
        c. 资源执行
        d. 过滤器2
        e. 过滤器1 

	过滤器先后顺序问题:
        a. 注解配置:按照类名的字符串比较规则比较,值小的先执行
        	如:AFilter和BFilter,AFilter就先执行了
        b. web.xml配置:
        	<filter-mapping>谁定义在上边,谁先执行

解决全站乱码

@WebFilter(value = "/*", filterName = "CharCodeFilter")
public class CharCodeFilter implements Filter {
    public void destroy() {
    }

    public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws ServletException, IOException {
        //统一配置中文乱码问题

        //向下转型
        HttpServletRequest request = (HttpServletRequest) req;
        HttpServletResponse response = (HttpServletResponse) resp;

        //请求时
        //get请求不会中文乱码
        //post请求会出现中文乱码问题
        String method = request.getMethod();
        if ("POST".equalsIgnoreCase(method)){
            request.setCharacterEncoding("utf-8");
        }
        response.setContentType("text/html;charset=utf-8");

        chain.doFilter(req, resp);
    }

    public void init(FilterConfig config) throws ServletException {
    }
}

Listener监听器

事件监听机制
    事件:
    	一件事情
    事件源:
    	事件发生的地方
    监听器:
    	一个对象
    注册监听:
    	将事件、事件源、监听器绑定在一起。 
    	当事件源上发生某个事件后,执行监听器代码

快速入门

步骤:
    1. 定义一个类,实现ServletContextListener接口
    2. 复写方法
    3. 配置拦截路径
        a. web.xml配置
            <listener>
                <listener-class> </listener-class>
            </listener>
            <!-- 指定初始化参数 -->
            <context-param>
                <param-name> </param-name>
                <param-value> </param-value>
            </context-param>

		b. 注解
			@WebListener
    
public class MyListener implements ServletContextListener {
    @Override
    public void contextInitialized(ServletContextEvent servletContextEvent) {
        //ServletContext对象创建后会调用该方法
    }

    @Override
    public void contextDestroyed(ServletContextEvent servletContextEvent) {
        //ServletContext对象被销毁之前会调用该方法
    }
}

监听器细节

作用:
	监听web中中的域对象 ServletContext ServletRequest HttpSession
监听内容:
    监听三个对象的创建和销毁
    监听三个对象属性的变化
    监听session中javabean的状态
注意:listener全部是接口

监听三个对象的创建和销毁
	ServletContextListener
	ServletRequestListener
	HttpSessionListener
监听三个对象属性的变化
	ServletContextAttributeListener
	ServletRequestAttributeListener
	HttpSessionAttributeListener
监听session中javabean的状态
	HttpSessionActivationListener(钝化和活化)
	HttpSessionBindingListener(绑定和解绑)
监听三个对象的创建和销毁
    ServletContextListener
        创建:服务器启动的时候,会为每一个项目都创建一个servletContext
        销毁:服务器关闭的时候,或者项目被移除的时候
        以后用来加载配置文件
    ServletRequestListener
        创建:请求来的时候
        销毁:响应生成的时候
    HttpSessionListener
        创建:
            java中第一次调用request.getSession的时候
            jsp访问的时候创建
        销毁:
            session超时
            手动销毁session
            服务器非正常关闭	

注解Annotation

注释:解释说明范围,给人看的,编译器在编译时,就会忽略
注解:也叫元数据,是给程序看的,一种代码级别的说明

JDK1.5版本以后引入的特性,与类、接口、枚举是在同一个层次。
可以声明在包、类、字段、方法、局部变量、方法参数等的前面,用来对这些元素进行说明,注释

注解的作用:
	1.检测作用
	2.为了替代配置文件,来简化配置
	3.定义注解(元注解:注解上的注解)
	4.分析代码(用到反射)
	
JDK提供的一些常用的注解
	@Override 检测该方法,是不是重写父类
	@FunctionInterface 检测该接口,是不是函数式接口
	@Deprecated 标识该类或该方法过时
	@SuppressWarnings(value="all") 压制黄色警告

注解的使用:
	@注解名(属性名=属性值)

注解的本质:
	其实是个接口
	既然注解本质上是个接口,那么接口中可以定义抽象方法,
	其实定义在注解中的抽象方法,我们叫做注解的属性

一旦注解中,定义了属性,那么在使用注解时,必须给注解的所有属性赋值,除非属性有默认值
注解中有一个特殊的属性名:叫value
	如果注解中只有一个value属性,那么我们在使用这个属性时,value属性名可以省略不写

注解的数据类型(其实就是抽象方法的返回值类型)
	基本数据类型
	String
	Class
	Annotation
	Enum 枚举
	以及以上类型对应的一维数组	
	注解的属性是个数组时,你在给注解的属性赋值时,要带上大括号,如果数组中只赋值一个元素,可以省略大括号

自定义注解

格式:
	@interface 注解名{}

注解属性:
	注解本质就是一个接口, 可以用javap这个命令反编译一下,注解的字节码文件
	例如: javap myan.class
	那接口中可以有常量和抽象方法
	抽象方法在注解中就称之为注解属性

public @interface MyAnnotation{
    //注解本质上是一个接口
    //那接口中的抽象方法,其实就是注解中的属性
    //注解的属性,前面的public abstract可以省略
    public abstract String name();
    //前面的数据类型,不是所有类型都支持
    //通过default 关健字给属性赋上默认值
    int num() default 100;
    Class haha();
}

注意:
	一旦注解有属性了,使用注解的时候必须赋值
	(除非这个注解属性有默认值)

元注解

限定注解的注解
JDK提供的两个常用的元注解
    @Retention 规定注解保留在什么阶段
    	只在代码中保留,在字节码文件中就删除了
        RetentionPolicy.SOURCE
        在代码和字节码文件中保留
        RetentionPolicy.CLASS
        所有阶段都保留(保留到运行阶段)
        RetentionPolicy.RUNTIME
    @Target 限定注解用在什么地方
    	作用在类 接口 等上面
        ElementType.TYPE
        作用方法上面
        ElementType.METHOD
        作用字段上面
        ElementType.FIELD

注解连接数据库

注解类:定义连接数据库所需的四个参数
	@Target(ElementType.METHOD)  //这个表示我们自定义的注解只能加在方法上
	@Retention(RetentionPolicy.RUNTIME) //表示我们的注解保留到运行阶段
	public @interface JDBCAnnotation {
   		String driverClass() default "com.mysql.jdbc.Driver";
        String url() default "jdbc:mysql://localhost:3306/my_database";
        String user() default "root";
        String password() default "123456";
	}

工具类
	public class JDBCUtils {
        @JDBCAnnotation(password = "123456")
        public static Connection getConnection() throws Exception {
            //获取该类的字节码文件对象
            Class clazz= JDBCUtils.class;
            //获取方法对象
            Method m = clazz.getMethod("getConnection");
            //判断该方法上是否有注解,如果有获取到注解
            boolean b = m.isAnnotationPresent(JDBCAnnotation.class);//参数:是注解的Class类型
            if(b){ //如果方法上有注解,获取注解,并拿到注解的属性值
                JDBCAnnotation annotation = m.getAnnotation(JDBCAnnotation.class);
                //获取注解属性的值
                String driverClass = annotation.driverClass();
                String url = annotation.url();
                String user = annotation.user();
                String password = annotation.password();
                Class.forName(driverClass);
                return DriverManager.getConnection(url,user,password);
            }
            return null;
        }
    }

测试类
public class Test {
    public static void main(String[] args) throws Exception{
        Connection connection = JDBCUtils.getConnection();
        System.out.println(connection);
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值