JavaWeb的三大组件详细总结

一、Servlet(Server Applet)

Servlet是Java Servlet的简称,称为小服务程序或服务连接器,用Java编写的服务器端程序,主要功能在于交互式地浏览和修改数据,生成动态Web内容。

狭义的Servlet是指Java语言实现的一个接口,广义的Servlet是指任何实现了这个Servlet接口的类,一般情况下,人们将Servlet理解为后者。Servlet运行于支持Java的应用服务器中。从原理上讲,Servlet可以响应任何类型的请求,但绝大多数情况下Servlet只用来扩展基于HTTP协议的Web服务器。

最早支持Servlet标准的是JavaSoft的Java Web Server,此后,一些其它的基于Java的Web服务器开始支持标准的Servlet。
注意: 每个Servlet都是唯一的,它们所处理的请求是不同的!

其中要使用到tomcat插件
Tomcat 是由 Apache 软件基金会属下 Jakarta 项目开发的 Servlet 容器,是开发和调试 JSP 程序的首选,按照 Sun Microsystems 提供的技术规范,实现了对 Servlet 和 JavaServer Page 的支持,并提供了作为 Web 服务器的一些特有功能,由于 Tomcat 本身也内含了 HTTP 服务器,因此也可以视作单独的 Web 服务器。但是,不能将 Tomcat 和 Apache HTTP 服务器混淆,Apache HTTP 服务器是用 C 语言实现的 HTTPWeb 服务器;这两个 HTTP web server 不是捆绑在一起的。Apache Tomcat 包含了配置管理工具,也可以通过编辑 XML 格式的配置文件来进行配置。

tomcat的环境: Tomcat 提供了一个 Jasper 编译器用以将 JSP 编译成对应的 Servlet。

Tomcat 的 Servlet 引擎通常与 Apache 或者其他 Web 服务器一起工作。除了用于开发过程中的调试以及那些对速度和事务处理只有很小要求的用户,很少会将 Tomcat 单独作为 Web 服务器。但随着版本的更新,正有越来越多的用户将其单独作为 Web 服务器用以那些对速度和可靠性有较高要求的环境中。

Servlet的作用:
1、接收请求数据
2、处理请求
3、完成响应

实现Sersvlet的方式有三种:

实现javax.servlet.Servlet接口;

继承javax.servlet.GenericServlet类;

继承javax.servlet.http.HttpServlet类;

通常我们会继承HttpServlet类来完成我们的Servlet。(因为它最方便)

1、Servlet概述:

Servlet一共有五个方法,其中生命周期方法有三个。
生命周期方法:

void init(ServletConf/g):出生之后(1次)(创建之前的初始化方法);

void servlet(ServletRequest request, ServletResponse response):每次处理请求时都会被调用;

void destroy:临死之前(1次)(释放资源的方法);

特性:

单例,一个类只有一个对象,当然可能存在多个Servlet类!

线程不安全的,所以它的效率高!

Servlet类由我们来写,但对象由服务器来创建,并且由服务器来调用相应的方法。

若要在idea中进行Servlet的操作,可以如下创建:(前提先下载好Tomcat插件)
在这里插入图片描述
在这里插入图片描述
然后命名确定后,在src中创建Servlet
在这里插入图片描述
在这里插入图片描述
然后就可以进行操作啦。

package cn.itcast.web.servlet;

import java.io.IOException;

import javax.servlet.Servlet;
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
/*
* 查看Serlvet接口中的方法
 */
public class AServlet implements Servlet {
    /*
     * 它也是生命周期方法
     * 它会在servlet被销毁之前调用,并且它只会被调用一次!
     */
    @Override
    public void destroy() {
	    System.out.println("destory()......");
    }
   /*
    * 可以用来获取Servlet的配置信息
    */
    @Override
    public ServletConfig getServletConfig() {
	    System.out.println("getServletConfig()......");
	    return null;
    }
    /*
    * 获取Servlet的信息
    */
	@Override
	public String getServletInfo() {
		System.out.println("getServletInfo()......");
		return "我是一个快乐的Servlet";
	}
	/*
	 * 它是生命周期方法
	 * 它会在Servlet对象创建之后马上执行,并只执行一次!(出生之后)
	 */
	@Override
	public void init(ServletConfig servletConfig) throws ServletException {
		System.out.println("init()......");
	}
	/*
	 * 它是生命周期方法 
	 * 它会被调用多次!!!
	 * 每次处理请求都是在调用这个方法!
	 */
	@Override
	public void service(ServletRequest request, ServletResponse response) throws ServletException, IOException {
		System.out.println("service()......");
	}
}

在web.xml中对Servlet进行配置

<servlet>
        <servlet-name>AServlet</servlet-name>
        <servlet-class>cn.itcast.web.servlet.AServlet</servlet-class>
    </servlet>
    <servlet-mapping>
        <servlet-name>AServlet</servlet-name>
        <url-pattern>/AServlet</url-pattern>
    </servlet-mapping>

启动服务器后,游览器访问:
在这里插入图片描述
效果为:
在这里插入图片描述
关闭服务器后:
在这里插入图片描述

1、ServletConfig API:
String getServletName()。获取的是 <servlet-name> 中的内容;
    
ServletContext getServletContext:获取Servlet上下文对象;
    
String getInitParamete(String name): 通过名称获取指定初始化参数的值;
    
Enumeration getInitParametnrNames(): 获取所有初始化参数的名称;
2、GenericServlet类

为了更好的使用Servlet

package cn.itcast.web.servlet;

import javax.servlet.*;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/*
    模拟GenericServlet
     */
public class BServlet extends HttpServlet {
    private ServletConfig config;

    /*
    需要就写,不需要就不写
     */
    public void destroy(){
        System.out.println("结束!!!");
    }

    /*
    这个方法一定会在init()方法之后被调用!
    init()被调用后,本类的成员this.config已经有值了!
     */
    public ServletConfig getServletConfig() {
        return this.config;
    }

    public String getServletInfo() {
        return "我是一个快乐的Servlet!";
    }

    /*
    由Tomcat来调用。并且只调用一次
    它是这些方法中第一个被调用的,它会在构造器之后马上被调用
     */
    public void init(ServletConfig config) throws ServletException {
        //吧tomcat传递的Servletconfig赋值给本类的一个成员,其实就是把它保存起来,方便在其他方法中使用!
        this.config = config;
        init();
    }

    /*
    这个方法是自己定义的,可以方便BServlet被其他类继承后,还能进行初始化动作
     */
    public void init() {
    }

    public void service(ServletRequest arg0, ServletRequest arg1)
            throws ServletException, IOException {
        /*
        这里是可以使用ServletConfig成员的
         */
        System.out.println("每次处理请求都会被调用!");
    }

    public ServletContext getServletContext() {
        return config.getServletContext();
    }

    public String getServletName() {
        return config.getServletName();
    }

    public String getInitParameter(String name) {
        return config.getInitParameter(name);
    }
}

2、HttpServlet类:(重点掌握)

HttpServlet extends GenderServlet {
void service(ServletRequest, ServletResponse) --> 生命周期方法
强转两个参数为http协议相关的类型。
调用本类的service(HttpServletRequest,HttpServletResponse)
void service(HttpServletRequest, HttpServletResponse) --> 参数已经是Http协议相关的,使用起来就更加方便。
它会通过request得到当前请求的请求方式,例如:GET或POST
根据请求方式再调用doGet()或doPost()方法

void doGet(){.......} --> 重写
void doPost(){.......} --> 重写,需要在表单加入:
<form action="/项目名/类名" name=”form1” method="get">
 <input type="submit" value="提交"/>
 </form>

}
这两个方法由我们自己来覆盖!!!如果你没有覆盖doGet或doPost,并且它们被调用了,那么会出现默认方法的内容405.

1、doGet和doPost的区别:

1、提交的form method=Post就执行DOPOST,否则执行GOGET 套用是不管method是post还是get都执行dopost方法

2、get:你可以通过URL传参数, Post不行

3、你的表单提交都有方法的,用什么就调用什么;get显示你传过去的参数,post则不显示.

4、通常的写法:先用doGet(),然后在doPost()中调用doGet(),这样就万无一失了,当然也可以反过来调用。

5、 get是通过httpheader来传输数据,有数量限制,而post则是通过httpbody来传输数据,没有数量限制。

6、get和post提交的数据量是不一样的.get最多只能在url后跟255个字符post没这个限制

2、Servlet细节:

1、不要在Servlet中创建成员!创建局部变量即可!

2、可以创建无状态成员!

3、可以创建有状态的成员,但状态必须为只读的!

在中配置,其中给出一个非负整数!

在中使用通配符,所谓的通配符就是星号"*",星号可以匹配任何URL前缀或后缀,注意:通配符只能放两端,不能出现在URL的中间。

3、web.xml文件(了解)

在${CATALINA_HOME}\conf\web,xml中的内容,相当于写到了每个项目的web.xml中,它是所有web.xml的父文件。

每个完整的JavaWeb应用中都需要有web.xml,但我们不知道所有的web.xml文件都有一个共同的父文件,它Tomcat的conf/web.xml路径。

4、ServletContext(重要):

一个项目只有一个ServletContext对象!

我们可以在N多个Servlet中来获取这个唯一的对象,使用它可以给多个Servlet传递数据!

这个对象在Tomcat启动时就创建,在Tomcat关闭才死去!

获取ServletContext:

ServletConfig # getServletContext();

GenericServlet # getServletContext();

HttpSession # getServletContext();

ServletContextEvent # getServletContext();

在Servlet中获取ServletContext对象:

在void init(ServletConfig config)中:
ServletContext context = config.getServletContext();
ServletConfig类的getServletContext()方法可以用来获取ServletContext对象;

在GenericeServlet或HttpServlet中获取ServletContext对象:
GenericServlet类有getServletContext()方法,所以可以直接使用this.getServletContext()来获取;

域对象的功能:(域对象就是用来在多个Servlet中传递数据!!!域对象必须有要存数据功能;域对象必须要有取数据功能;)

ServletContext是JavaWeb四大域对象之一:

1、PageContext;

2、ServletRequest;

3、HttpSession;

4、ServletContext;

所有域对象都有存储数据的功能,因为域对象内部有一个Map,用来存储数据,
下面是ServletContext对象用来操作数据的方法:

void setAttribute(String name,Object value):用来存储一个对象,也可以称之为一个域属性,
例如:servletContext.setAttribute("xxx","xxx"),在ServletContext中保存了一个属性,域属性名称为xxx,域属性的值为xxx。
请注意,如果多次调用该方法,并且使用相同的name,那么会覆盖上一次的值,这一特性与Map相同;
	
Object getAttribute(String name):用来获取ServletContext中的数据,当前在获取之前需要先去存储才行,
例如:String value = (String)servletContext.getAttribute("xxx");,获取名为xxx的域属性;
	
void removeAttribute(String name): 用来移除ServletContext中的域属性,如果参数name指定的域属性不存在,那么本方法什么都不做;
	
Enumeration getAttributeNames():获取所有域属性的名称;

ServletContext的演示:
保存数据:

package cn.itcast.web.servlet;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/*
演示向Servletcontext中保存数据
 */
public class CServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        /*
        1、获取ServletContext对象
        2、调用其setAttribute()方法完成保存数据
         */
        ServletContext applcation = this.getServletContext();
        applcation.setAttribute("name","哈哈");
    }
}

获取数据:

package cn.itcast.web.servlet;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/*
演示从ServletContext中获取数据
 */
public class DServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        /*
        1、获取ServletContext对象
        2、调用getAttribute()方法完成获取数据
         */
       ServletContext application = this.getServletContext();
       String name = (String)application.getAttribute("name");
       System.out.println(name);
    }
}

记得web.xml的配置,配置好后,运行服务器,其CServlet类运行后没有什么变化,只有白板,然后运行DServlet后效果为:
在这里插入图片描述
获取应用初始化参数:

Servlet也可以获取初始化参数,但它是局部的参数;也就是说,一个Servlet只能获取自己的初始化参数,不能获取别人的,即初始化参数只为一个Servlet准备。

可以配置公共的初始化参数,为所有的Servlet而用!这需要ServletContext才能使用!
其实践运用:

package cn.itcast.web.servlet;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/*
演示ServletContext获取公共的初始化参数
 */
public class EServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        /*
        1、得到ServletContext
        2、调用它getInitParameter(String)得到初始化参数
         */
        ServletContext app = this.getServletContext();
        String value = app.getInitParameter("context-param");
        System.out.println(value);
    }
}

web.xml配置

<context-param>
        <param-name>context-param</param-name>
        <param-value>context-value</param-value>
    </context-param>

其结果为:
在这里插入图片描述
获取真实路径:
使用ServletContext对象来获取Web应用下的资源,例如在hello应用的根目录下创建_.txt文件
现在想在Servlet中获取这个资源,就可以使用ServletContext来获取。
获取x.txt的真实路径
String realpath = servletContext.getRealPath("/x.txt"),realPath的值为
x.txt文件的绝对路径:E:\xxx\xxx\x.txt

获取资源流:
ServletContext不仅可以获取路径,还可以获取资源流,即使资源以输入流的方式获取:
获取x.txt资源流:InputStream In = servletContext.getResourceAsStream("/x.txt");
如下演示:

package cn.itcast.web.servlet;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;

/*
使用ServletContext获取资源路径
 */
public class FServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        /*
        它得到的是有盘符的路径:E:/xxx/xxx/
         */
        String path = this.getServletContext().getRealPath("_.txt");
        System.out.println(path);

        /*
        获取资源的路径后,再创建输入流对象!
         */
        InputStream input = this.getServletContext().getResourceAsStream("/_.txt");
    }
}

3、网站访问量统计小案例:

一个项目中所有的资源被访问都要对访问量进行累加!

创建一个int类型的变量,用来保存访问量。然后把它保存到ServletContext的域中,这样可以保存所有的Servlet都可以访问到!

最初时,ServletContext中没有保存访问量相关的属性;

当本站第一次被访问时,创建一个变量。设置其值为1;保存到ServletContext中;

当以后的访问时,就可以从ServletContext中获取这个变量,然后在其基础之上加1.

获取ServletContext对象,查看是否存在名为count的属性,如果存在,说明不是第一次访问,如果不存在,说明是第一次访问;

第一次访问:调用Servletcontext的setAttribute()传递一个属性,名为count,值为1;

第2~N次访问:调用ServletContext的getAttribute()方法获取原来的访问量,给访问量加1.再调用Servletcontext的setAttribute()方法完成设置。

package cn.itcast.web.servlet;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/*
 * 统计访问量
 * @author cxf
 */
public class Demo1_Two extends HttpServlet {

	public void doGet(HttpServletRequest request, HttpServletResponse response) 
			throws ServletException, IOException {
		/*
		 * 1、获取ServletContext对象
		 * 2、从ServletContext对象中获取名为count的属性
		 * 3、如果存在:给访问量加1.然后再保存回去;
		 * 4、如果不存在:说明是第一次访问,向Servletcontext中保存名为count的属性,值为1
		 */
		ServletContext app = this.getServletContext();
		Integer count = (Integer)app.getAttribute("count");
		if(count == null) {
			app.setAttribute("count", 1);
		} else {
			app.setAttribute("count", count+1);
		}
		/*
		 * 向游览器输出
		 *   需要使用响应对象!
		 */
		PrintWriter pw = response.getWriter();
		pw.print("<h1>" + count + "</h1>");
	}
}

配置web.xml后,启动服务器,游览器访问了多次后,出现的效果为:
在这里插入图片描述
获取类路径下的资源:

package cn.itcast.web.servlet;

import sun.misc.IOUtils;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.InputStream;

/*
演示获取路径下的资源
 */
public class HServlet extends HttpServlet {

    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        /*
        1、得到ClassLoader
                >先得到Class,再得到ClassLoader
        2、调用其getResourceAsStream(),得到一个InputStream
         */
//   方法1:
//        ClassLoader c1 = this.getClass().getClassLoader();
        //相对/classes
//        InputStream input = c1.getResourceAsStream("cn/itcast/servlet/_.txt");


//   方法2,加斜杠和不加斜杠的区别
        Class c = this.getClass();
        //相对当前.class文件目录
       // InputStream input = c.getResourceAsStream("_.txt");

        //相对classes下
        InputStream input = c.getResourceAsStream("/_.txt");


        String s = IOUtils.toString(input);//读取输入流内容,转换成字符串返回
        System.out.println(s);
    }
}

二、过滤器

web开发人员通过Filter技术,对web服务器管理所有的web资源:例如jsp,静态文件等进行拦截,从而实现一些特殊的功能。例如实现URL级别的权限访问控制、过滤敏感信息、压缩信息等高级功能。 Servlet API中提供了一个Filter接口,如果编写的java类实现了这个接口,则把这个java类称之为过滤器Filter。

1、都需要在web.xml中进行配置

Servlet

Listener(2个感知监听器不需要配置)

Filter

2、过滤器

它会在一组资源(jsp、servlet、css、html等等)的前面执行!

它可以让请求得到目标资源,也可以不认请求达到!

过滤器有拦截请求的能力!

过滤器如何编写:

1、写一个类实现Filter接口

2、在web.xml中进行配置

Filter接口
方法:

void init(FilterConfig) : 创建之后,马上执行;Filter会在服务器启动时就创建!

void destory() : 销毁之前执行!在服务器关闭时销毁

void doFilter(ServletRequest, ServletResponse, FilterChain) : 每次过滤时都会执行

Filter是单例的!



FilterConfig --> 与ServletConfig相似

  获取初始化参数:getInitParameter()

  获取过滤器名称:getFilterName()

  获取appliction: getServletContext()



FilterChain

   doFilter(ServletRequest, ServletResponse): 放行!

放行,就相当于调用了目标Servlet的service()方法!

代码演示:

package cn.itcast.web.filter;

import javax.servlet.*;
import java.io.IOException;

public class AFitler implements Filter {
    /*
	创建之后马上执行,用来做初始化!
 */
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        System.out.println("过滤器启动!!!");
    }
    /*
    每次过滤时都会执行
     */
    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain)
            throws IOException, ServletException {
        System.out.println("你被拦截了!!!");
    }
    /*
    销毁之前执行,用来做对非内存资源进行释放
     */
    @Override
    public void destroy() {
        System.out.println("过滤器结束!!!");
    }
}

web.xml:

<filter>

    <filter-name>xxx</filter-name>

    <filter-class>cn.itcast.web.filter.AFitler</filter-class>

</filter>

<filter-mapping>

    <filter-name>xxx</filter-name>

    <url-pattern>/*</url-pattern>

</filter-mapping>

演示结果为:
在这里插入图片描述
服务器关闭:
在这里插入图片描述

FilterConfig --> 与ServletConfig相似
		获取初始化参数:getInitParnmeter()
	    获取过滤器名称:getFilterName()
	    获取appliction: getServletContext()

FilterChain:
doFilter(ServletRequest, ServletResponse(): 放行!
放行,就相当于调用了目标Servlet的service()方法!

多过滤器:

 FilterChain#doFilter()方法:执行目标资源,或是执行下一个过滤器!
 如果没有下一个过滤器那么执行的是目标资源,如果有,那么就执行下一个过滤器!

过滤器的四种拦截方式:(背)

截请求:<dispatcher>REQUEST</dispatcher>默认的;

截转发:<dispatcher>FORWARD</dispatcher>

截包含:<dispatcher>INCLUDE<dispatcher>

截错误:<dispatcher>ERROR</dispatcher>

在<filter-mapping>中进行配置!

多个过滤器的执行顺序:

<filter-mapping>的配件顺序决定了过滤器的执行顺序!

过滤器的应用场景:

1、执行目标资源之前做预处理工作,例如设置编码,这种试通常都会放行,只是在目标资源执行之前做一些准备工作;(几乎是的Servlet中都需要写request.setCharaterEndoing()可以把它入到一个Filter中)

2、通过条件判断是否放行,例如效验当前用户是否已经登录,或者用户IP是否已经被禁用;

3、在目标资源执行后,做一些后续的特殊处理工作,例如把目标资源输出的数据进行处理;(回程拦截)

下面是filter-mapping的元素:

<filter-mapping>

    <filter-name></filter-name>

    <url-pattern></url-pattern>

    <dispatcher></dispatcher>(四种拦截方式)

    <servlet-name></servler-name>
    
</filter-mapping>

三、监听器

Listener:监听器

1、初次接触:AWT

2、二次接触:SAX

监听器:

它是一个接口,内容由我们来实现;

它需要注册,例如注册在按钮上!

监听器中的方法,会在特殊事件发生时被调用!

观察者

事件源;

小偷

事件;

偷东西

监听器;

警察
监听器中的方法:抓捕

事件源:三大域!

ServletContext

生命周期监听:ServletContextListener,它有两个方法,一个在出生时调用,一个在死亡时调用;

void contextInitialized(ServletContextEvent sce):创建SErvlecontext时
void contextDestroyed(ServletContextEvent sce):销毁Servletcontext时

代码演示:

package cn.itcast.web.listener;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.http.HttpSessionAttributeListener;
import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;
import javax.servlet.http.HttpSessionBindingEvent;
/*
ServletContext监听

作用:可以在这个监听器存放一些tomcat启动就要完成的代码!
 */
public class AListener implements ServletContextListener{

    public void contextInitialized(ServletContextEvent sce) {
        System.out.println("哈,我来了!!!");
    }

    public void contextDestroyed(ServletContextEvent sce) {
        System.out.println("啊,我走了!!!");
    }
}

启动服务器后:
在这里插入图片描述
关闭服务器后:
在这里插入图片描述
属性监听:ServletContextAttribute Listener,它有三个方法,一个在添加属性时调用,一个在替换属性时调用,最后一个是在移除属性时调用

void attributeAdded(ServletContextAttributeEvent event):添加属性时;

void attributeReplaced(ServletContextAttributeEvent event):替换属性时;

void attributeRemoved(ServletContextAttributeEvent event):移除属性时;

HttpSession

生命周期监听:HttpSessionListener,它有两个方法,一个在出生时调用,一个在死亡时调用;

void sessionCreated(HttpSessionEvent se):创建session时
void sessionDestroyed(HttpSessionEvent se):销毁session时

属性监听:HttpSessioniAttributeListener,它有三个方法,一个在添加属性时调用,一个在替换属性时调用,最后一个是在移除属性时调用。

void attributeAdded(HttpSessionBindingEvent event):创建session时;

void attributeReplaced(HttpSessionBindingEvent event):替换属性时;

void attributeRemoved(HttpSessionBindingEvent event):移除属性时;

ServletRequest

生命周期监听:ServletRequestListener,它有两个方法,一个在出生时调用,一个在死亡时调用;

void requestInitlalized(ServletRequestEvent sre):创建request时;

void requestDestroyed(ServletReguestEvent sre):创建request时;

属性监听:ServletRequestAttributeListener,它有三个方法,一个在添加属性时间调用,一个在替换属性时调用,最后一个是在移除属性时调用。

void attributeAdded(ServletRequestAttributeEvent srae):添加属性时;

void attributeReplaced(ServletRequestAttributeEvent srae):替换属性时;

void attributeRemoved(ServletRequestAttributeEvent srae):移除属性时;

JavaWeb中完成编写监听器:

写一个监听器类:要求必须去实现某个监听器接口;

注册,是在web.xml中配置来完成注册!

事件对象:

ServletContextEvent:ServletContext getServletContext()

HttpSessionEvent: HttpSession getSession()

ServletRequest:

     ServletContext getServletContext()

     ServletReques getServletRequest()

ServletContextAttributeEvent:

    ServletContext getServletContext();
    
    String getName():获取属性名
    
    Object getValue():获取属性值

HttpSessionBindingEvent: 略;
ServletRequestAttributeEvent: 略;

其它的监听器:

感知监听(都与HttpSession相关)

它用来添加到JavaBean上,而不是添加到三大域上!

这两个监听器都不需要web.xml中注册!
如下代码演示:

package cn.itcast.web.listener;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.http.*;

public class User implements HttpSessionBindingListener {
    private String username;
    private String password;
    public String getUsername(){
        return username;
    }
    public void setUsername(String username){
        this.username = username;
    }
    public String getPassword(){
        return password;
    }
    public void setPassword(String password){
        this.password = password;
    }
    public User() {
        super();;
    }
    public User(String username, String password){
        super();
        this.username = username;
        this.password = password;
    }

    public String toString(){
        return "User [username" + username + ",password=" + password + "]";
    }

    @Override
    public void valueBound(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("哈~~~,session添加了我!!!");
    }

    @Override
    public void valueUnbound(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("唔~~~,无情的session抛弃了我!!!");
    }
}

并在Web中创建了一个session文件来存储创建好的两个jsp文件,一个添加add.jsp,一个抛弃remove.jsp;它们各配置好文件:
add.jsp:

<%
    cn.itcast.web.listener.User user = new cn.itcast.web.listener.User();
    session.setAttribute("user", user);
%>

remove.jsp:

<%
    session.removeAttribute("user");
%>

启动服务器,游览器访问后结果为:
访问app.jsp后:
在这里插入图片描述
在这里插入图片描述
访问remove.jsp后:
在这里插入图片描述
在这里插入图片描述
HttpSessionBindingUstener:添加到javabean上,javabean就知道自己是否添加到session中了。

最后一个监听器:
session的序列化

Session可死后重生,即使关了服务器再重启依然可以无需存储直接读取,因为在关掉服务器时所储存的数据保存在SEESSIONS.ser文件中,如果需要废掉其功能只需在context.xml文件中添加

session的钝化和活化:

钝化:
当服务器正常关闭时,还存活着的session(在设置时间内没有销毁) 会随着服务器的关闭被以文件SESSIONS.ser的形式存储在tomcat 的work 目录下,这个过程叫做Session 的钝化。(会保存到硬盘里)。

活化:
当服务器再次正常开启时,服务器会找到之前的SESSIONS.ser文件,从中恢复之前保存起来的Session 对象,这个过程叫做Session的活化。(调到内存中进行使用)

配置Tomcat钝化session的参数,把下面配置文件放到tomcat\conf\catallna\localhost目录下!

<Context>

    <Manager className="org.apache.catalina.session.PersistenManager" maxIdleSwap="1"> //如果session在1分钟内没有使用,那么Tomcat就会钝化它。

    <Store className="org.apache.catalina.session.FileStore" directory="mysession"/>  //把session序列化到Tomcat\work\Catalina\localhost\listener\mysession目录下。

    </Manager>

</Context>

监听器之最后的HttpSessionActivationListener:
代码演示:
先创建一个Java class类:

package cn.itcast;

import javax.servlet.http.HttpSessionActivationListener;
import javax.servlet.http.HttpSessionEvent;

public class User implements HttpSessionActivationListener, java.io.Serializable {
    @Override
    public void sessionWillPassivate(HttpSessionEvent httpSessionEvent) {
        System.out.println("哈~~~我陪session去硬盘里了!!!");
    }

    @Override
    public void sessionDidActivate(HttpSessionEvent httpSessionEvent) {
        System.out.println("啊哈~~~我和session又回到内存中了!!!");
    }
}

再Web中创建两个jsp文件,配置的内容为:
a.jsp:

<h1>向session中保存session数据</h1>
<%
    session.setAttribute("xxx", new cn.itcast.User());
%>

b.jsp:

<h1>获取session中的数据</h1>
<%
    out.print(session.getAttribute("xxx"));
%>

启动服务器,游览器访问后:
在这里插入图片描述
在这里插入图片描述
JavaWeb的三大组件的笔记记录就到这里,ψ(*`ー´)ψ

发布了5 篇原创文章 · 获赞 28 · 访问量 4805

猜你喜欢

转载自blog.csdn.net/weixin_45537947/article/details/104711485
今日推荐