当前位置: 首页 > news >正文

网站建设提升医院信息化水平关键词优化排名网站

网站建设提升医院信息化水平,关键词优化排名网站,广州番禺网站建设公司,营销项目策划公司之前学习了很多涉及servlet的内容,本小结我们说一下监听器,说起监听器,编过桌面程序和手机App的都不陌生,常见的套路都是拖一个控件,然后给它绑定一个监听器,即可以对该对象的事件进行监听以便发生响应&…

之前学习了很多涉及servlet的内容,本小结我们说一下监听器,说起监听器,编过桌面程序和手机App的都不陌生,常见的套路都是拖一个控件,然后给它绑定一个监听器,即可以对该对象的事件进行监听以便发生响应,从本质上来说这些都是观察者模式的具体实现,在web程序中的监听器也不例外。

在Java Web程序中使用监听器可以通过以下两种方法:

  • 通过注解@WebListener来标识一个自定义的监听器;

@WebListener
public class CustomListener implements Listener {}
  • 通过在web.xml中配置来使用监听器;
<listener><listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>

在Java Web程序中,主要是对ServletContext、HttpSession和ServletRequest三个对象提供支持。

一、 ServletContext监听器

有两类监听器用来监听ServletContext对象:
  1. ServletContextListener:该监听器用来监听ServletContext的初始化和销毁事件;
  2. ServletContextAttributeListener:该监听器用来监听ServletContext中属性的删除、添加和替换事件;
实例如下:
@WebListener
public class MyServletListener implements ServletContextListener, ServletContextAttributeListener {public void contextInitialized(ServletContextEvent sce) {System.out.println("ServletContextEvent source: " + sce.getSource());System.out.println("context created");}public void contextDestroyed(ServletContextEvent sce) {System.out.println("ServletContextEvent source: " + sce.getSource());System.out.println("context destroyed");}public void attributeAdded(ServletContextAttributeEvent event) {System.out.println("ServletContextAttributeEvent source: " + event.getSource());System.out.println("attribute added:  " + event.getName() + "--" + event.getValue());}public void attributeRemoved(ServletContextAttributeEvent event) {System.out.println("ServletContextAttributeEvent source: " + event.getSource());System.out.println("attribute removed:  "+ event.getName() + "--" + event.getValue());}public void attributeReplaced(ServletContextAttributeEvent event) {System.out.println("ServletContextAttributeEvent source: " + event.getSource());System.out.println("attribute replaced:  "+ event.getName() + "--" + event.getValue());}
}
该类实现了上述的两个接口,启动Servlet容器,分析结果,输出如下:

可以看到在启动的过程中首先创建了ServletContext,这激发了contextInitialized监听器方法,然后调用了每一个Servlet的init()方法对每一个Servlet进行初始化,对所有的Servlet(这里有两个自定义Servlet,MyServlet,TestServlet)初始化完成后则会向ServletContext添加一个属性,不管是事件对象还是添加的属性都是Servlet容器提供的。
当关闭Servlet容器的时候,分析结果,输出如下:

首先会调用所有Servlet的destroy方法,然后销毁ServletContext实例。
在对属性进行增加、替换、删除时,会调用相应的监听器,代码如下:
ServletContext context = req.getServletContext();
context.setAttribute("country", "zn");
context.setAttribute("country", "en");
context.removeAttribute("country");
代码输出:

这里要注意的是:当替换属性时也是使用setAttribute(),只不过是key的值是相同的。当替换属性后,监听器得到的值是旧值(我觉得旧值和新值都应提供相应API)。

二、 HttpSession监听器

有四类监听器用来监听HttpSession对象:
  1. HttpSessionListener:用来监听HttpSession的创建和销毁;
  2. HttpSessionActivationListener:这个监听器是在分布式环境下使用的,当HttpSession实例要在不同的虚拟机之间进行迁移或者序列化时则会用到这个类,当HttpSession对象被迁移到新的虚拟机上时或者反序列化时则会调用sessionDidActivate()方法,当HttpSession实例从旧的虚拟机迁出或者序列化时则会调用sessionWillPassivate()方法;
  3. HttpSessionAttributeListener:用来监听HttpSession中属性的删除、增加和替换事件;
  4. HttpSessionBindingListener:
其实在新出来的Servlet3.1规范中还有一个Session监听器,javax.servlet.http.HttpSessionIdListener用于监听SessionId的改变,由于我用的是Tomcat7还不支持Servlet3.1所以会找不到这个类,所以这里就没写,如果有兴趣的可以自己尝试一下。

1、 HttpSessionListener和HttpSessionAttributeListener:

@WebListener
public class MyHttpSessionListener implements HttpSessionListener, HttpSessionAttributeListener {private Long startTime;public void attributeAdded(HttpSessionBindingEvent event) {startTime = (Long) event.getSession().getAttribute("startTime");System.out.println("HttpSessionBindingEvent source: " + event.getSource());System.out.println("add attribute: " + event.getName() + "--" + event.getValue());}public void attributeRemoved(HttpSessionBindingEvent event) {System.out.println("HttpSessionBindingEvent source: " + event.getSource());System.out.println("remove attribute: " + event.getName() + "--" + event.getValue());}public void attributeReplaced(HttpSessionBindingEvent event) {System.out.println("HttpSessionBindingEvent source: " + event.getSource());System.out.println("replace attribute: " + event.getName() + "--" + event.getValue());}public void sessionCreated(HttpSessionEvent se) {System.out.println("HttpSessionEvent source: " + se.getSource());System.out.println("session id: " + se.getSession().getId());System.out.println("session create");}public void sessionDestroyed(HttpSessionEvent se) {System.out.println("HttpSessionEvent source: " + se.getSource());System.out.println("session id: " + se.getSession().getId());System.out.println("active time: " + (System.nanoTime() - startTime));System.out.println("session destroy");}}
对应的Servlet如下:
@WebServlet(name="myHttpSessionServlet", urlPatterns="/myHttpSessionServlet", loadOnStartup=1)
public class MyHttpSessionServlet extends HttpServlet {private static final long serialVersionUID = 5687825632187950599L;@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {HttpSession session = req.getSession();session.setAttribute("startTime", System.nanoTime());session.setAttribute("visitTimes", 0);session.setAttribute("visitTimes", 1);session.removeAttribute("visitTimes");session.setMaxInactiveInterval(10);resp.getWriter().write("session listene demo");}@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {}
}
第一次请求该网站的资源时,输出如下:
可以看出第一次首先创建HttpSession,调用了sessionCreated()方法。之后是添加方法时触发了对应的属性监听器,替换属性时还是监听器返回的替换前的值。
由于设置了存活时间,之后会触发销毁Session的方法,输出如下:

从中可见,Session销毁时不是只是调用sessionDestroyed()方法,在执行完这个方法之后,还会调用attributeRemoved()方法,将其中保存的所有属性全部清除。

2、 HttpSessionActivationListener

该监听器就像上面说过的一样,是在分布式环境下或者当要序列HttpSession实例时才起作用。
  • 由于Session是存储在内存中的,所以有时候服务器为了节省内存,会把访问较少的Session 持久化到存储设备中,包括文件系统和数据库,这样就能节省内存空间,另一方面也告诉我们不要在Session中放过多的数据,以免造成服务器的负担;
  • 当在分布式环境下时,如果一台机器发生宕机不能访问,可以将Session序列化进行传输到别的服务器中的JVM中进行工作,这其中就要求存储在Session中对数据要可以序列化,这时候是会使用到这个监听器的;
  • 对Session进行序列化一般是Servlet容器进行的,我们可以进行配置;
ERROR,错误使用:
HttpSession session = req.getSession();
session.setAttribute("startTime", System.nanoTime());
session.setAttribute("visitTimes", 0);
session.setAttribute("visitTimes", 1);
session.removeAttribute("visitTimes");
ObjectOutputStream output =new ObjectOutputStream(new FileOutputStream("C:\\demo"));
output.writeObject(session);
上述是错误的使用办法,不能序列化HttpSession,此处的序列化只是将Session实例中的信息转换成能在网络中传输的数据形式即可,含义范围要大于Java中的序列化概念,一般的理解是将对象转化成字符串。
至于Session为什么序列化,这就很明显了,如果服务器宕机,客户访问服务器的所有信息因为存在于内存中,所以也就全部丢失了,将Session序列化到存储设备之后可以在服务器恢复运行之后将用户信息也同时恢复。

3、 HttpSessionBindingListener

首先这个监听器的作用和之前的HttpSessionAttributeListener很像,使用起来也很类似,但是它们有如下区别:
  • HttpSessionAttributeListener要进行注册,或者通过注解或者通过web.xml,它是用来监听整个应用程序中的所有的Session实例,和所有Session实例对应的属性,属于一个通用的监听器;
  • HttpSessionBindingListener则是针对于一个特定的Session和一个特定的属性的监听器,是量身定制的,并且它也不需要进行注册;
使用实例如下:
public class Person implements Serializable, HttpSessionBindingListener{private static final long serialVersionUID = -4972586177179694554L;private String name;private Integer age;public Person(){}public Person(String name, Integer age) {super();this.name = name;this.age = age;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Integer getAge() {return age;}public void setAge(Integer age) {this.age = age;}@Overridepublic String toString() {return "Person [name=" + name + ", age=" + age + "]";}public void valueBound(HttpSessionBindingEvent event) {System.out.println("person bound");}public void valueUnbound(HttpSessionBindingEvent event) {System.out.println("person unbound");}
向doGet()方法中的Session中添加属性:
session.setAttribute("person", new Person("lmy", 23));
session.setMaxInactiveInterval(10);
发出请求之后,输出如下:
HttpSessionBindingEvent source: org.apache.catalina.session.StandardSessionFacade@fdfaab5
person bound
10秒之后Session失效,输出:
HttpSessionBindingEvent source: org.apache.catalina.session.StandardSessionFacade@fdfaab5
person unbound

三、 ServletRequest监听器

有三类监听器用来监听ServletRequest对象:
  1. ServletRequestListener:用来监听ServletRequest的创建和销毁,注意Servlet容器是通过池来重用ServletRequest的,创建一个ServletRequest实例其实就是从池中取出一个实例,销毁该对象也就是将该实例放回池中;
  2. ServletRequestAttributeListener:用来监听ServletRequest中属性的删除、增加和替换事件;
  3. AsyncListener:这个后面提到异步编程时再详细说;
监听器代码如下:
@WebListener
public class MyServletRequestListener implements ServletRequestListener, ServletRequestAttributeListener {public void attributeAdded(ServletRequestAttributeEvent srae) {System.out.println("ServletRequestAttributeEvent source: " + srae.getSource());System.out.println("request attribute added:  " + srae.getName() + "--" + srae.getValue());}public void attributeRemoved(ServletRequestAttributeEvent srae) {System.out.println("ServletRequestAttributeEvent source: " + srae.getSource());System.out.println("request attribute removed:  " + srae.getName() + "--" + srae.getValue());}public void attributeReplaced(ServletRequestAttributeEvent srae) {System.out.println("ServletRequestAttributeEvent source: " + srae.getSource());System.out.println("request attribute replaced:  " + srae.getName() + "--" + srae.getValue());}public void requestDestroyed(ServletRequestEvent sre) {System.out.println("ServletRequestEvent source: " + sre.getSource());System.out.println("request destroy");}public void requestInitialized(ServletRequestEvent sre) {System.out.println("ServletRequestEvent source: " + sre.getSource());System.out.println("request init");}
}
MyHttpServlet1类接受请求代码:
</pre><pre name="code" class="java">@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {System.out.println("MyHttpServlet1 request work");
<span style="white-space:pre">	</span>System.out.println("current thread :" + Thread.currentThread().getName());
}
</pre><div>MyHttpServlet类接受请求代码:</div><pre name="code" class="java"><pre name="code" class="java">@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {System.out.println("MyHttpServlet request work");
<span style="white-space:pre">	</span>System.out.println("current thread :" + Thread.currentThread().getName());
}
 向MyHttpServlet发送一个请求输出如下:
可以看出接收一个请求后首先初始化ServletRequest对象,调用requestInitialized()方法,之后会发现进行了属性的替换,使能异步处理,在之后进行处理请求的具体工作,最后销毁该请求对象。
向MyHttpServlet1发送一个请求输出如下:
处理的流程和向MyHttpServlet发送请求相同但是看出来请求的处理线程是不同的
在请求的过程中添加属性和ServletContext中的对属性的监听器是类似的:
req.setAttribute("area", "zh");
req.setAttribute("area", "ts");
req.removeAttribute("area");
输出如下:
属性替换时也是返回的替换之前的值,和ServletContext中属性的替换是相同的。


相关文章:
  • How are Threads allocated to handle Servlet request?
  • Java序列化(一)
  • HttpSessionActivationListener Example Use Case
  • 理解Java对象序列化
  • java tomcat实现Session对象的持久化原理及配置方法介绍
  • Using Sessions and Session Persistence
  • Practical Usage of HttpSessionBindingListener And HttpSessionAttributeListener
  • What is difference between HttpSessionAttributeListener and HttpSessionBindingListener?
http://www.lbrq.cn/news/2635975.html

相关文章:

  • 阿里妈妈用哪个软件做网站体验营销是什么
  • 资料查询网站建设注册安全工程师
  • win7在iis中新建一个网站优秀企业网站模板
  • 算命网站做竞价赚钱企业网络营销策划方案
  • 怎样做自己公司的网站领硕网站seo优化
  • 烟台福山建设工程监测网站百度搜索网页版
  • python wordpress api第三方关键词优化排名
  • 青岛外贸建设网站制作常用的网络推广方法
  • 在手机上怎么赚钱博客seo怎么做
  • 如何对网站做压力测试抖音关键词搜索排名收费
  • 做网站都需要准备什么网络推广培训课程内容
  • 如何制作课程网站模板下载微信运营
  • 做动画网站郑州seo优化顾问热狗
  • 网络建设可行性分析怀化网站seo
  • 社交网站设计附近成人电脑培训班
  • 扬州网站建设制作有了域名怎么建网站
  • 武汉微信网站建设站长之家网站流量查询
  • 佛山顺德容桂网站制作关键词网站排名查询
  • 威海专业网站建设营销软文范例大全100
  • 项目经理职责及工作范围搜索引擎优化的方法与技巧
  • 门户网站的定义百度指数使用方法
  • 静态网站做301重定向百度教育网站
  • 做韩国护的网站天津网站建设公司
  • 网站开发会计处理百度一下你就知道搜索引擎
  • 可以做女鞋批发的网站南宁网站seo大概多少钱
  • 郑州做网站七彩科技产品市场调研怎么做
  • 网站联系方式连接怎么做seo薪资水平
  • 怎么做公司销售网站武汉seo排名
  • smarty做网站软文发布网站
  • 网站设计概述广告公司
  • 【Qt开发】常用控件(二) -> enabled
  • 计算机毕业设计java疫情开放下的新冠信息共享平台 基于Java的社区疫情防控人员流动管理系统 疫情防控期间社区人员动态管理系统
  • Redis 分布式Session
  • Webpack 5 高性能配置方案
  • 全栈:如何操作在SQLserver里面CRUD(增删改查)
  • WMS及UI渲染底层原理学习