0

我们正在使用 ApplicationListener 加载一些计时器库,这些库将对一些 bean 进行常规后台工作。然而,在 applicationCreated 我们似乎无法通过 ApplicationEx 对象找到进入 ServletContext 的方法。有很多不推荐使用的方法似乎会有所帮助。有谁知道在 applicationCreated 方法期间如何从 ApplicationEx 遍历 FacesContext 或外部 ServletContext ?

4

2 回答 2

1

似乎没有办法从 ApplicationEx 获取 FacesContext 或 ServletContext。

ServletContextListener在 Web 应用程序初始化时提供 ServletContext,但不幸的是,XPages 不支持这种侦听器。

那么,ApplicationListener 和应用程序范围的托管 bean 的组合呢?

首先,ApplicationListener 将启动。然后,如果在用户可以首先调用的每个页面的 beforePageLoad 事件中“调用”托管 bean,它将被实例化。此时
,托管 bean 能够通过以下方式获取 ApplicationListener 对象

(ApplicationEx)(FacesContext.getCurrentInstance().getApplication()).getApplicationListeners()

并且可以在 ApplicationListener 中运行一个方法来获取 FacesContext、ExternalContext 和 bean。ApplicationListener 可以在 FacesContext/ExternalContext 的帮助下启动所有操作(例如计时器库),并将上下文和/或 bean 作为字段保存在 ApplicationListener 对象中。在 applicationDestroyed() 时,仍然可以使用上下文或“关闭”托管 bean。

这是一个例子:

应用程序监听器“我的应用程序监听器”

package com.knutherrmann.listener;

import javax.faces.context.ExternalContext;
import javax.faces.context.FacesContext;
import com.ibm.xsp.application.ApplicationEx;
import com.ibm.xsp.application.events.ApplicationListener;

public class MyApplicationListener implements ApplicationListener {

    private FacesContext facesContext;
    private ExternalContext externalContext;
    private AppBean app;

    public void applicationCreated(ApplicationEx arg0) {
        System.out.println("applicationCreated(" + arg0.getApplicationId() + ") in MyApplicationListener");
    }

    public void applicationDestroyed(ApplicationEx arg0) {
        System.out.println("applicationDestroyed(" + arg0.getApplicationId() + ") in MyApplicationListener");
        System.out.println("...FacesContext: " + facesContext);
        System.out.println("...ExternalContext: " + externalContext);
        System.out.println("...AppBean: " + app);
        app.stop();
    }

    public void initContext(AppBean app) {
        facesContext = FacesContext.getCurrentInstance();
        externalContext = facesContext.getExternalContext();
        this.app = app;
        System.out.println("initContext() in MyApplicationListener");
        System.out.println("...FacesContext: " + facesContext);
        System.out.println("...ExternalContext: " + externalContext);
        System.out.println("...AppBean: " + app);
    }

}

应用程序范围的托管 bean“app”作为类“AppBean”的实例

package com.knutherrmann.listener;

import java.io.Serializable;
import javax.faces.context.FacesContext;
import com.ibm.xsp.application.ApplicationEx;
import com.ibm.xsp.application.events.ApplicationListener;

public class AppBean implements Serializable {
    private static final long serialVersionUID = 1L;

    public AppBean() {
        ApplicationEx app = (ApplicationEx) FacesContext.getCurrentInstance().getApplication();
        for (ApplicationListener listener : app.getApplicationListeners()) {
            if (listener instanceof MyApplicationListener) {
                MyApplicationListener myApplicationListener = (MyApplicationListener) listener;
                myApplicationListener.initContext(this);
            }
        }
    }

    public void start() {
    }

    public void stop() {
        System.out.println("AppBean stopped");
    }

}

XPage

<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core"
    beforePageLoad="#{app.start}">
    Test MyApplicationListener and AppBean
</xp:view>

服务器控制台的输出

07:23:44   HTTP JVM: applicationCreated(32) in MyApplicationListener
07:23:44   HTTP JVM: initContext() in MyApplicationListener
07:23:44   HTTP JVM: ...FacesContext: com.ibm.xsp.domino.context.DominoFacesContext@f850f85
07:23:44   HTTP JVM: ...ExternalContext: com.ibm.xsp.domino.context.DominoExternalContext@13891389
07:23:44   HTTP JVM: ...AppBean: com.knutherrmann.listener.AppBean@22c522c5

07:54:06   HTTP JVM: applicationDestroyed(32) in MyApplicationListener
07:54:06   HTTP JVM: ...FacesContext: com.ibm.xsp.domino.context.DominoFacesContext@f850f85
07:54:06   HTTP JVM: ...ExternalContext: com.ibm.xsp.domino.context.DominoExternalContext@13891389
07:54:06   HTTP JVM: ...AppBean: com.knutherrmann.listener.AppBean@22c522c5
07:54:06   HTTP JVM: AppBean stopped
于 2013-06-16T22:02:51.767 回答
0

我们使用服务器的预加载 xpage 功能 ( bit.ly/10rfvEs ),但这不会创建会话,因此永远不会有 FacesContext(获取当前实例返回 null)。所以我们做了一些技巧来打开一个从监听器返回到应用程序的链接,然后创建我们需要的第一个会话和应用程序范围。

于 2013-07-08T16:35:35.627 回答