特別なオートスタートサーブレットを使用して、起動時に初期化し、アプリケーションデータを共有する

StackOverflow https://stackoverflow.com/questions/3468150

質問

構成を取得し、どこかに外部リソース/オブジェクト/システムに接続し、アプリケーションスコープに保存する必要があります。

アプリケーションをセットアップする2つの方法が表示されます。

  • オーバーライド init() 既存のサーブレットと必要なコードで、同じサーブレット内に構築されたすべてのオブジェクトを保持します。
  • 何らかの初期化サーブレットを持っていて、その使用 init() 仕事をするために。次に、作成したオブジェクトをに保存します ServletContext 私の他のサーブレットと共有します。

上からどちらがより良いアプローチですか?サーブレット間でオブジェクトを共有するより良い方法はありますか?互いに直接それらを呼び出しますか...?

役に立ちましたか?

解決

どちらもより良いアプローチではありません。サーブレットは、展開イベント(スタートアップ/シャットダウン)ではなく、HTTPイベント(HTTPリクエスト)で聞くことを目的としています。


CDI/JSF/EJBは利用できませんか?使用する ServletContextListener

@WebListener
public class Config implements ServletContextListener {

    public void contextInitialized(ServletContextEvent event) {
        // Do stuff during webapp's startup.
    }

    public void contextDestroyed(ServletContextEvent event) {
        // Do stuff during webapp's shutdown.
    }

}

まだサーブレット3.0にいない場合、アップグレードできないため、使用できない場合 @WebListener 注釈、その後、手動で登録する必要があります /WEB-INF/web.xml 以下のように:

<listener>
    <listener-class>com.example.Config</listener-class>
</listener>

アプリケーションスコープにオブジェクトを保存および取得するには(すべてのサーブレットがアクセスできるように)、使用してください。 ServletContext#setAttribute()#getAttribute().

リスナーがアプリケーションの範囲に自らを保存できる例は次のとおりです。

    public void contextInitialized(ServletContextEvent event) {
        event.getServletContext().setAttribute("config", this);
        // ...
    }

そして、それをサーブレットで取得します:

    protected void doGet(HttpServletRequest request, HttpServletResponse response) {
        Config config = (Config) getServletContext().getAttribute("config");
        // ...
    }

また、JSP El byで利用できます ${config}. 。だからあなたもそれを単純な豆にすることができます。


CDIは利用可能ですか?使用する @Observes の上 ApplicationScoped.class

import javax.enterprise.context.ApplicationScoped;

@ApplicationScoped
public class Config {

    public void init(@Observes @Initialized(ApplicationScoped.class) ServletContext context) {
        // Do stuff during webapp's startup.
    }

    public void destroy(@Observes @Destroyed(ApplicationScoped.class) ServletContext context) {
        // Do stuff during webapp's shutdown.
    }
}

これは、サーブレットで使用できます @Inject. 。必要に応じて作ってください @Named だからそれは介して利用可能です #{config} エルでも。

これは、CDI 1.1以降、これが新しいことであることに注意してください。まだCDI 1.0を使用していて、アップグレードできない場合は、別のアプローチを選択してください。


JSFが利用可能ですか?使用する @ManagedBean(eager=true)

import javax.faces.bean.ManagedBean
import javax.faces.bean.ApplicationScoped;

@ManagedBean(eager=true)
@ApplicationScoped
public class Config {

    @PostConstruct
    public void init() {
        // Do stuff during webapp's startup.
    }

    @PreDestroy
    public void destroy() {
        // Do stuff during webapp's shutdown.
    }
}

これは経由で利用できます #{config} エルでも。


EJBは利用可能ですか?検討 @Startup@Singleton

@Startup
@Singleton
public class Config {

    @PostConstruct
    public void init() {
        // Do stuff during webapp's startup.
    }

    @PreDestroy
    public void destroy() {
        // Do stuff during webapp's shutdown.
    }
}

これは、サーブレットで使用できます @EJB. 。スタートアップフックのためにEJBを乱用してはいけないからです。さらに、a @Singleton デフォルトでは、読み取り/書き込みがロックされており、主にバックグラウンドジョブのスケジューリングなどのトランザクションのものを目的としています。

参照:

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top