TA的每日心情 | 衰 2021-2-2 11:21 |
---|
签到天数: 36 天 [LV.5]常住居民I
|
一、监听器原理:
) h1 K- N0 x' a% e, U监听器就是一个实现特定接口的普通java程序,这个程序专门用于监听一个java对象的方法调用或属性改变,当被监听对象发生上述事件后,监听器某个方法将立即被执行。1 W! a D& ~5 G( O/ N0 X
+ D- Y! e2 Y* M2 j4 [
' H7 V, ~; D8 l \7 @- @
& b$ ~$ r5 P0 o, p* u简单的说,被监听对象A中,关联着B对象。事件源A类对外提供一个方法,用于设置监听器对象B到A类的某一实例变量中。在需要监听事件源的方法中,方法体的某一处先构造创建一个Event对象,将this即B与相关的动作封装进Event对象中,然后调用监听器B对象的doXXXX(event)方法,将事件对象传入方法实参中。1 n3 M" z) P9 W/ d
简单的类图示例:
. {4 B6 s" X9 v# p( ?* V) J3 Z% K
- i% J: f1 [. F- J) z! I8 k) C+ m/ O( W# g1 U
二、简介:) ]1 l+ n( y3 [# a
在Servlet规范中定义了多种类型的监听器,它们用于监听的事件源分别为SerlvetConext,HttpSession和ServletRequest这三个域对象。# n% _" S7 K2 J; e$ J: {/ s
Servlet规范针对这三个对象上的操作,又把这多种类型的监听器划分为三种类型:
1 B. ~+ d+ d V# T1>监听三个域对象创建和销毁的事件监听器
6 F7 W- k& H. q' ]( X, z% U2>监听域对象中属性的增加和删除的事件监听器
3 s8 Q0 N3 ?0 a6 Z8 ^: ^3 c7 X3>监听绑定到HttpSession域中的某个对象的状态的时间监听器。
' ^. Q% d t2 y- f$ B6 e1 ga、如三个域对象的创建与销毁方法签名:) q8 H. C5 e3 L V
ServletRequestListener有以下两个方法( i8 R4 \1 z3 R# ^
void requestDestroyed(ServletRequestEvent sre) - J( k- R0 c2 \2 ~
void requestInitialized(ServletRequestEvent sre)
( o8 l( E3 w: ]' y8 KHttpSessionListener有以下两个方法 }! ]( n& l* c" y$ c& w
void sessionCreated(HttpSessionEvent se)
9 r' Y0 F' f) t" Cvoid sessionDestroyed(HttpSessionEvent se) & M- i% ^+ Q3 m& W/ B# b( ]2 d
ServletContextListener1 L- j- o) R |% x. y7 s' M/ X
void contextDestroyed(ServletContextEvent sce) , m4 j# J8 M$ n- F% \
void contextInitialized(ServletContextEvent sce) 5 j; v( u3 V7 G
b、三个类型对象域中增、删、改的监听器(3个); R O% q3 r9 |+ b5 _$ @
ServletContextAttributeListener,8 i: C2 x; K: y8 v) e
HttpSessionAttributeListener,
. H1 {% K' }3 y8 t, UServletRequestAttributeListener
' h! j7 {* Y# q1 ^& v6 t! D' _- yc、感知型监听器(2个):监听自己何时被帮到session上,何时解绑了;何时被钝化了,何时被活化了(序列化到某个存储设置中)。8 @+ e1 G& b; ]( ^9 U8 o/ m$ |
注意:这种监听器不需要注册。某个javabean实现这些接口后就可以监听何时被绑定、解绑或被激活或钝化。4 {% l. g; o9 [0 V
HttpSessionBindingListener:实现该接口的类,能检测自己何时被Httpsession绑定,和解绑: a! @0 M$ G* \
HttpSessionActivationListener:实现该接口的类(要求些javabean必须是实现了Serializable接口的),能监测自己何时随着HttpSession一起激活和钝化。6 c b2 V0 g- u9 M! ?
三、Listenner的注册
' {) O& Z' y6 X- BJavaweb的这些特别的监听器注册比较简单,因为ServletRequest、HttpSession、ServletContext对象都是容器创建的,所以需要它们的监听器的话,只需要在应用的web-info的web.xml里配置即可:: m# [; [; f' {5 r, Z: `0 S
<listener>$ V$ D* e) e; f, |
<listener-class>com.test.listener.MyHttpSessionAttributeListener</listener-class>( R8 l* k8 y9 e' \
<listener-class>com.test.listener.MyServletContextAttributeListener</listener-class>
8 B% I. H; U& M<!-- 多个实现相同的Listenner接口,在执行时是按web.xml注册出现的来决定。 -->
+ l+ J0 [4 a2 P9 [</listener>% ?) E; ^) b6 F0 e
注意:感知型监听器HttpSessionBindingListener、HttpSessionActivationListener不需要注册。9 l& t1 N/ h: L2 V3 z! h
三、应用场景:6 x. F0 U* G7 C* x6 d
由于ervletRequest、HttpSession、ServletContext对象都是容器创建的,什么时候创建,用户都不知道。通过实现这些对象的监听器后,就可以得知了。比如:2 n- g9 `% e; ]2 ]9 r6 N2 a
1>在ServletContextLintener监听器的contextInitialized方法中,进行应用级的资源初始化以便提高效率,在contextDestroyed方法中对应用级的资源进行释放。$ M8 p6 b8 ~& Z v* J2 j& ~3 \
2>又比如web应用中,会存在会话,通常的作法是将当前登录的用户存放在session会话中。那么如何统计在线人数话,如何显示出当前登录的用户呢。如何踢出某些已登录的用户呢。就可以通过HttpSessionAttributeListener监听器的attributeAdded方法。
* i$ v1 p! L' ]& c) K等等。
- p2 W( H- I( {+ [. d! H
9 V( n4 e, Z( K/ K: ^( d% f/ B |
|