1。基本概念
Javawebのリスナーは、オブザーバーのデザインパターンを通じて実装されています。オブザーバーモードに関しては、ここではあまり紹介することはありませんので、それが何を意味するのかについて大まかに話します。
オブザーバーモードは、パブリッシュサブスクリプションモードまたはリスナーモードとも呼ばれます。このモードには、オブザーバーとオブザーバー(通常は被験者とも呼ばれます)の2つの文字があります。オブザーバーは、トピックに関心のあるイベントを登録します。このイベントが発生すると、トピックはコールバックインターフェイスを介してオブザーバーに通知します。
人生の例を教えてください:新聞を購読してください。家族や個人は、新聞とともに新聞を購読することができます。ここで新聞は「テーマ」であり、家族は「オブザーバー」です。たとえば、家族が明日の朝に新聞を購読する必要がある場合、これは「イベント」です。翌朝、新聞が制作され、これが「イベント」でした。事件が発生すると、新聞は新聞を「コールバックインターフェイス」であるホームメールボックスに送ります。
Javawebのリスナーの場合、サーブレット仕様はリスナーインターフェイスクラスのいくつかの列を定義し、インターフェイスクラスを介してアプリケーションにイベントを公開します。アプリケーションが関心のあるイベントを聞きたい場合、対応するイベントを直接登録する必要はありません。代わりに、対応するインターフェイスクラスを実装するために独自のリスナーを書き込み、自分のリスナーをサーブレットコンテナに登録します。プログラムが気にかけているイベントが発生すると、サーブレットコンテナはリスナーに通知し、リスナーのメソッドを呼び戻します。ここでカスタマイズされたリスナーはオブザーバーであり、サーブレットコンテナがテーマです。
2。サンプル分析
上記のように、サーブレットコンテナは、リスナーインターフェイスクラスを通じてイベントをアプリケーションに公開します。そのため、イベントを登録するのではなく、リスナーを登録することです。対応するプログラミングの手順は次のとおりです。1。独自のリスナーを作成し、特定のリスナーインターフェイスを実装します。 2。web.xmlでリスナーを登録します。以下は、最も単純なリスナーインターフェイスServleTContextListenerの例です。
1.testlistener.java
Public Class TestListenerはServletContextListener {public TestListener(){} public void contextInitialized(servletContextExtevent scce){system.out.println( "servletcontextListener.contextInitialized");} public voiddestroyed(servetcontextexteedevent sccs) {system.out.println( "servletcontextlistener.contextdestroyed");}}2.web.xml
<リスナー> <リスナークラス> com.nantang.listener.testlistener </ristener-class> </ristener>
コンテナが起動すると、「servletcontextListener.contextinitialized」がログに出力され、コンテナが閉じられると、 "servletcontextlistener.contextdestroyed"が出力されます。詳細な説明を後でさらに分析します。
ここでは、IDE(Eclipse、Stsなど)で上記の例を示す場合、サーバーを起動するとき、「ServletContextListener.ContextInitialized」をコンソールで見ることができ、「ServletContextListener.ContextDestroyed」を見ることができないことに注意してください。これは、ContextDestroyedメソッドが実行されないということではなく、IDEが完全に実装していないことです。 ContextDestroyedが実際に呼び出されていることを確認するために、コンソールに出力するのではなく、ファイルのコンテンツを出力するためにContextDestroyedでコードを書くことができます。
3。ソースコード分析
次に、サーブレット仕様が定義するイベントを分析しましょう。より正確には、どのリスニングインターフェイスが定義されているか。以下の紹介は、サーブレット3.0仕様に基づいています。
Servlet3.0は、8つのリスナーインターフェイスを提供します。これは、範囲に応じて3つのカテゴリに分けることができます。
1. ServletContextListenerおよびServletContextAtttributElistenerを含む、コンテキスト関連のリスニングインターフェイスを担当します。
2。HTTPセッション関連のリスニングインターフェイス(HTTPSESSIONLISTENER、HTTPSSESSIONACTIVERACTIVELISTENER、HTTPSSESSIONATTRIBUTELISTENER、およびHTTPSSESSION BINDINGLISTENERを含む。
3.サーブレットリクエストに関連するリスニングインターフェイス:ServletRequestListenerおよびServletRequestattributeListenerを含む。
実際、インターフェイスの命名から、その基本的な機能を推測できるはずです。以下のカテゴリで説明しましょう。
1.サーブレットコンテキスト関連のリスニングインターフェイス
以前にサーブレットを紹介するとき、Webアプリケーションはサーブレットコンテキストに対応することを説明しました。したがって、ServletContextListenerとServletContextAttributeListenerによって聞かれるイベントのライフ範囲は、Webアプリケーション全体を実行します。以下は、これら2つのインターフェイス間のクラス図階層関係です。
1.1 EventListener
EventListenerはタグインターフェイスであり、すべてのイベントリスナーはこのインターフェイスを継承する必要があります。これはサーブレットの仕様であり、説明はありません。
1.2 EventObject
EventListenerと同様に、EventObjectはイベントレベルのクラスであり、すべての特定のイベントクラスはEventObjectを継承する必要があります。
Public Class eventObjectはjava.io.serializable {Protected Transient Object source; public eventObject(object source){if(source == null)Throw new Illegalargumentexception( "null source"); this.source = source;} public object getsource(){return source;} public String toString() "]";}}このクラスは非常にシンプルで、その本質は単なるものです。ソースです。クラス名Event Objectとプロパティ名ソースを通じて、このクラスが「イベントソースオブジェクト」を保持していることが1つのことをしていることがわかります。
1.3 ServletContextEvent
public class servletcontextevent extends java.util.eventobject {public servletcontextevent(servletcontext source){super(source);} public servletcontext gestervletcontext(){return(servletcontext)super.getSource();}}}サーブレットコンテキストイベントこのイベントクラスは、EventObjectの単純な継承です。 ServletContextインスタンスは、コンストラクターのイベントソースとして提供されます。イベントソースはサーブレットコンテキストであるため、servletContextインスタンスを取得するためにgetServletContextが提供されます。
将来、他のイベントクラスを説明するとき、それらはすべて同じ型です。各イベントクラスは、対応する構造方法を提供し、対応するイベントソースオブジェクトに合格し、イベントソースを取得するための追加方法を提供します。したがって、EventObjectはイベントソースの基本クラスです。すべてのイベントサブクラスの本質が1つのことを行い、特定のイベントソースオブジェクトを決定します。
そのため、事件を説明する場所は後で通り過ぎます。
1.4 ServletContextListener
public interface servletcontextListener extend extente eventlistener {public void contextInitialized(servletcontextextevent sce); public void contextdestroyed(servletcontextextevent sce);}サーブレットコンテキストリスナーインターフェイスは、サーブレットコンテキスト初期化イベントとサーブレットコンテキストクロージングイベントの2つのイベントに対応しています。
Webアプリケーションが初期化されると、サーブレットコンテナはServletContextevenインスタンスを構築し、ContextInitializeメソッドを呼び戻します。
サーバーを閉じる前に、サーブレットのコンテキストが閉じようとしている場合、サーバーコンテナはServletContextevenインスタンスを構築し、ContextDestroyedメソッドを呼び戻します。ここでは、すべてのサーブレットとフィルターが破壊方法を完了した後、ContextDestroyedメソッドの実行が実行されることに注意する必要があります。
したがって、アプリケーションが起動または閉じるときに何かをしたい場合は、インターフェイスを実装するために独自のリスナーを書き込みます。
すべてのイベントリスナーも同じモデルです。対応するイベントコールバックインターフェイスメソッドは、サーブレット仕様に従って定義されます。メソッドエントリパラメーターは、対応するイベントソースインスタンスです。そのため、後でモニターについて説明する場所も通り過ぎます。
1.5 ServletContextAttributeEvent
public class class servletcontextattributeevent extends servletcontextevent {private string name; private object value; public servletcontextattributeevent(servletcontext source、string name、object value){super(source); this.name = name; this.value = value;} public string getName(){return this.name;} public getValue;} public getValue;} }}ServletContextAttributeEventは、サーブレットコンテキスト属性に関連するイベントを表します。一般に、属性が変更されるとイベントがトリガーされます。このクラスはServletContextexevenを継承し、イベントソースもServletContextインスタンスです。属性名と属性値を取得するための追加の方法が提供されます。
1.6 ServletContextAttributElistener
パブリックインターフェースServletContextAttributElistener extends EventListener {public void astributeadded(servletcontextattributeevent scab); public void astributeremoved(servletcontextattributeevent scab); public void astributeReplaced(servletcontextattributeeventeeventeventeventeventeventeventeventevenサーブレットの上記の属性が追加、削除、または変更された場合、サーブレットコンテナはServletContextAttributeEvent Eventオブジェクトを構築し、それぞれ属性、属性、および属性のあるメソッドを呼び戻します。
ここで注意する必要があるのは、属性の値が置き換えられたときに呼び戻すように呼び戻すメソッドです。この時点で、servletcontextattributeeventeevent.getValue()メソッドを呼び出すと、戻りは以前の属性値を置き換えることです。
2 HTTPセッション関連のリスニングインターフェイス
2.1 httpsessionevent
public class httpsessioneventはjava.util.eventobjectを拡張します{public httpsessionevent(httpsession source){super(source);} public httpsession getsession(){return(httpsession)super.getsource();}}}HTTPセッション関連のイベント。セッションが変更されるとトリガーされます。イベントソースはHTTPSESSIONインスタンスであり、追加のHTTPSESSION取得方法を提供します。
2.2 httpsessionListener
public interface httpsessionListener extend extent eventelistener {public void sessioneded(httpssessionevent se); public void sessiondestroyed(httpssessionevent se);}セッションが作成されて破壊されると、サーブレットコンテナはHTTPSSESSEVENT Eventオブジェクトを構築し、セッション作成およびセッションが作成されたメソッドを呼び出します。
2.3 httpsessionactivationlistener
public interface httpssessionactivationlistener extenting eventlistener {public void sessionwillpassivate(httpssessionevent se); public void sessiondidactivate(httpsessionevent se);}セッションが受動されようとしているか、アクティブ化されている場合、サーブレットコンテナはHTTPSSESSEVENTイベントオブジェクト、CallBack SessionWillPassivate、およびSessionDidactivateメソッドを構築します。
パッシベーションと活性化はここで説明されています。パッシベーションとは、サーバーのメモリが不十分であるか、セッションのアクティビティタイムアウトが到来し、最近非アクティブなセッションがディスクにシリアルされています。アクティベーションとは、パッシブセッションに再びアクセスされ、ディスクからメモリにセッションを脱却することを意味します。
ここでは、パッシブ化とアクティブ化するためには、セッションを最初にシリアル化して脱isizedする必要があることがわかります。同時に、プログラミングプロセス中に、文字列や整数などの単純なオブジェクトを可能な限り使用し、リストやマップなどのコレクションを使用しないようにします。
2.4 httpsessionBindingEvent
public class httpsessionbindeventはhttpssessevent {private string name; private object value; public httpsessionbindeventevent(httpssession session、string name){super(session); this.name = name;} public httpsessionbindingvent(httpsession session、httpssession session、string name = upert; this.name ^ falue; httpsesssion getSession(){return super.getsession();} public string getname(){return name;} public object getValue(){return this.value; }}HTTPセッション属性に関連するイベントは、セッション属性が変更されたときにトリガーされます。イベントソースはHTTPSESSIONインスタンスであり、HTTPSESSION、属性名、および属性値を取得するための追加の方法を提供します。
2.5 HTTPSSESSIONATTRIBUTELISTENER
public interface httpssessionAttributeListener extend extends eventlistener {public void astributeadded(httpssessionbindingevent se); public void astributeremoved(httpssessionbindingevent se); public void astributeReplaced(httpssessionbindevent se);};}セッション属性が追加、削除、または変更された場合、サーブレットコンテナはhttpsessionBindingEventイベントオブジェクトを構築し、それぞれ属性、属性、および属性のあるメソッドを呼び出します。
ここで注意する必要があるのは、属性の値が置き換えられたときに呼び戻すように呼び戻すメソッドです。この時点で、servletcontextattributeeventeevent.getValue()メソッドを呼び出すと、戻りは以前の属性値を置き換えることです。
セッションの無効なメソッドが呼び出されるか、セッションが失敗した場合、属性化されたメソッドもコールバックされます。
2.6 httpsessionbindingListener
public interface httpsessionbindinglistener extend extenting eventlistener {public void valuebound(httpssessionbindingEvent event); public void valueunbound(httpsessionbindingEventイベント);}このリスナーは、セッションの属性の変更についても耳を傾けます。セッション属性が追加および削除された場合、つまり属性値がバインドされ、属性値が固定されていない場合、サーブレットコンテナはhttpsessionbindingEventイベントオブジェクトを構築し、それぞれValueBoundおよびValueUnboundメソッドを呼び戻します。
HTTPSSESSIONATTRIBUTELISTENERと違いはありませんが、そうではありません。 2つの本質的な違いの1つは、イベントトリガーの条件です。
セッションプロパティに変更がある場合、サーブレットコンテナはHTTPSSESSIONATTRIBUTELISTENERに通知します。ただし、HTTPSESSIONBINDINGLISTENERの場合、サーブレットコンテナは、バインドされていないプロパティ値がリスナーのインスタンスである場合にのみ通知します。例えば:
パブリッククラスTestListenerはhttpsessionBindingListener {@OverridePublic Void ValueBound(httpsSessionBindingEvent Event){system.out.println( "httpssessionbindinglistener.valuebound");}@overridepublic valueunbound(htpssession -bindesbindebindebindebindebenteventevent) {system.out.println( "httpsessionbindinglistener.valueunbound");}}リスナーTestListenerをカスタマイズして、httpsessionbindingListenerを実装します。次のセッション属性をコードに設定しましょう。
httpssession session = request.getSession(); testListener testListener = new testListener(); session.setattribute( "listener"、testListener); session.RemoveAttribute( "リスナー");
ここで、セッションの属性値は、リスナーTestListenerインスタンスです。したがって、このコードが実行されると、サーブレットコンテナはTestListenerに通知し、ValueBoundおよびValueUnboundメソッドを呼び戻します。
ここでは、セッションの無効なメソッドが呼び出された場合、またはセッションが失敗した場合、ValueUnboundメソッドも呼び戻されることに注意してください。
3サーブレットリクエスト関連のリスニングインターフェイス
3.1 ServletRequestEvent
public class servletrequesteventはjava.util.eventobject {private servletrequest request; public servletrequestevent(servletcontext sc、servletrequest request){super(sc); this.request = request;} public servletrequest getServletrequest(){return retriceth; (servletcontext)super.getSource();}}サーブレットリクエストに関連するイベントは、リクエストが変更されたときにトリガーされます。イベントソースはServletContextインスタンスであり、ServletContextおよびServletRequestメソッドの追加フェッチを提供します。
3.2 ServletRequestListener
public interface servletrequestlistener extend eventeventener {public void requestdestroyed(servletrequestevent sre); public void requestInitialized(servletrequestevent sre);}リクエストが初期化または破壊された場合、クライアントはWebアプリケーションの入力(サーブレットまたは最初のフィルターを入力)をリクエストするか、Webアプリケーションがクライアントへの応答を返します(サーブレットまたは最初のフィルターを終了します)。サーブレットコンテナは、サーブレッケストベントインスタンスを構築し、requestInitializedおよびrequestDestroyedメソッドを呼び戻します。
3.3 ServletRequestattributeevent
public class servletrequestattributeeventは、servletrequesteventを拡張します{private string name; private object value; public servletrequestattributeevent(servletcontext sc、servletrequest request、string name、object value){super(sc、request); this.name = name; this.value = value; this.value; }}サーブレットに関連するイベントは、要求属性が変更されるとトリガーされる属性を要求します。イベントソースはServletContextインスタンスであり、属性名と属性値を取得するための追加の方法を提供します。
3.4 ServletRequestattributeListener
パブリックインターフェースServletRequestattatributElistener extends EventListener {public void aTtiontributeedded(servletrequestattributeevent srae); public void astributeremoved(servletrequestattributeevent srae); public void astributeReplaced(servletrequestattributeevent srae);要求された属性が追加、削除、または変更された場合、サーブレットコンテナはServletRequestattributeEvent Eventオブジェクトを構築し、それぞれ属性、属性、および属性のあるメソッドを呼び戻します。
ここで注意する必要があるのは、属性の値が置き換えられたときに呼び戻すように呼び戻すメソッドです。この時点で、ServletRequestattributeEvent.getValue()メソッドに電話すると、戻りは以前の属性値を置き換えることです。
4。概要
この時点で、リスナーは話し終えました。リスナー、サーブレット、フィルターには共通点が1つあり、どちらもコンテナによってスケジュールされていることがわかります。気にするリスナーインターフェイスを実装して登録するために、独自のリスナーを作成する必要があります。残りの仕事は、私たち自身のリスナーにビジネスロジックを書くことです。
このブログ投稿で導入されたリスナーは、サーブレット3.0仕様によって策定されています。 3.1はイベントリスナーインターフェイスを追加しましたが、原則は似ています。読者は自分でそれらを理解できます。