当f:ajax被执行时,总是调用JSF2 preRenderComponent

时间:2011-12-19 08:17:34

标签: ajax jsf jsf-2 initializer postconstruct

我有一个由NewsBean.java支持的JSF页面,它有<f:event type="preRenderComponent" listener="#{newsBean.init}" />作为bean初始化程序。

页面底部有一个按钮,用于发送评论,其中包含: <f:ajax event="click" execute="@form" render="@form" listener="#{newsBean.sendComment}" />并被<h:form>包围。单击按钮时,始终会调用NewsBean.init()

我的bean范围是视图。这是一个有效的行为(总是调用init())?如何防止始终致电init()

2 个答案:

答案 0 :(得分:9)

始终在预呈现事件上调用preRender侦听器,无论它是初始请求还是回发请求。每个请求都有一个呈现响应阶段,无论它是普通请求还是ajax请求。所以这种行为是通过规范。如果它是回发请求,您需要通过检查FacesContext#isPostback()来检查自己的侦听方法。

public void sendComment() {
    if (!FacesContext.getCurrentInstance().isPostback()) {
        // ...
    }
}

<f:event type="preRenderXxx">(其中Xxx可以是ViewComponent)实质上是一种“解决方法”,用于能够调用的功能要求在初始请求上处理视图参数之后的bean操作方法。在即将推出的JSF 2.2中,将引入一个新的<f:viewAction>标签,该标签应完全符合预期的工作:

<f:viewAction action="#{newsBean.sendComment}" />

此标记支持onPostback属性,该属性已默认为false

<f:viewAction action="#{newsBean.sendComment}" onPostback="false" />

JSF 2.2将于2012年第一季度发布.JSF 2.2的快照版本目前已经发布。

答案 1 :(得分:0)

我猜你的<f:event>标记放在<h:form>标记内。因此,当您单击ajax按钮时,它会重新呈现整个<h:form>组件,从而导致再次触发preRenderComponent事件。

我认为你应该使用的是PreRenderViewEvent