JSF为每个AJAX请求调用viewparams

时间:2011-05-11 19:42:39

标签: jsf jsf-2 primefaces

我有一个JSF页面,它接受一个viewparam并设置一个变量,该变量从数据库中查找相应的实体,并使用找到的详细信息加载bean,如下所示:

<f:metadata>
    <f:viewParam name="attractionId" value="#{attractionsBean.attractionId}" />
</f:metadata>

我有使用primefaces API的谷歌地图,当拖动标记时,会发出ajax调用以更新标记位置。

<h:outputText value="Location" />
<f:view contentType="text/html">
    <p:gmap id="gmap" center="41.381542, 2.122893" zoom="10" type="HYBRID" style="width:380px;height:350px"
                        model="#{attractionsBean.attractionModel.mapModel}"
                        markerDragListener="#{attractionsBean.onMarkerDrag}"
                        onMarkerDragUpdate="growl" />
                </f:view>

问题是在每次标记拖动事件和ajax调用之后,每次都会调用元数据中的方法setAttractionId。

什么可以解决这个问题,以防止每次都调用setAttractionId方法?

3 个答案:

答案 0 :(得分:1)

在尝试找到解决方法的许多小时之后,此问题的解决方案如下:

  1. 将ManagedBean设为@ViewScoped,以便在同一页面上成为同一个bean

  2. 我没有在attractionId的setter中从数据库中检索实体,而是在视图范围bean中引入了一个@PostConstruct方法,使用以下代码通过view参数检索对象: / p>

    @PostConstruct
    public void setupAttractionModel() {
        this.attractionId = FacesContext.getCurrentInstance().getExternalContext().getRequestParameterMap().get(ATTRACTION_ID_VIEW_PARAM);
        // Lookup by attractionId ...
    }
    

    在每个需要bean的页面之前调用postconstruct方法。

  3. 删除导致问题的<f:metadata>标记

答案 1 :(得分:1)

真的更好的方法是将setter保持为一个简单的setter并使用延迟的实例化模式:

  1. 如果为脏,则设置setAttractionId中id的实例变量,并清除当前检索的实例。如果变量不是脏的,吸引力实例将保持不变。
  2. 在getter(getAttractionModel)中使用吸引力id检索吸引力实例(如果为null)。对getter的后续调用将返回实例而不从db。
  3. 检索
  4. 删除帖子构造
  5. 这适用于ViewScoped bean。

答案 2 :(得分:0)

托管bean中的setter可能是请求作用域。尝试将托管bean设置为ViewScoped,看看是否会产生影响。