在使用 JSF 来使用 NetBeans 开发 Web 应用程序时,我多次注意到,在某些情况下,JSF ManagedBeand 中的 getter 方法(可能还有 setter)在它们打算执行时会被执行多次只有一次。在这种情况下,有时对于某些操作(尤其是某些计算)强制执行一些关键条件(if等)以防止它们被淹没是极其重要的。我一直试图了解其背后的真正原因,但我无法做到。
在这里,我演示了一个非常简单的应用程序,其中有一个 getter 方法
public Collection<entity.Country> getCountries(){};
调用远程EJB并从MySql数据库中的相关表中检索所有国家/地区并显示在JSF页面上。网页的屏幕截图如下所示。
无需过多关注屏幕截图、JSF 页面代码及其相应的 ManagedBean。
这是 JSF 页面代码
<?xml version='1.0' encoding='UTF-8' ?>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core">
<h:head>
<title>Countries</title>
</h:head>
<h:body>
<h:form>
<center><br/><br/><br/>
<h:dataTable id="dataTable" styleClass="table" frame="box" value="#
{country.countries}" var="row" bgcolor="lightyellow" border="7"
cellpadding="7" cellspacing="7" rules="all" width="50%" dir="ltr">
<f:facet id="header" name="header">
<h:outputText value="~:Country:~" styleClass="tableHeader"/>
</f:facet>
<h:column>
<f:facet name="header">Country ID</f:facet>
<h:outputText id="countryID" value="#{row.countryID}"/>
</h:column>
<h:column>
<f:facet name="header">Country Name :</f:facet>
<h:outputText id="countryName" value="#{row.countryName}"/>
</h:column>
</h:dataTable>
</center>
</h:form>
</h:body>
</html>
相应的简单 JSF ManagedBean 代码位于此处。
package country;
import commonBean.CommomBeanRemote;
import java.util.Collection;
import javax.ejb.EJB;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.RequestScoped;
@ManagedBean
@RequestScoped
public class Country
{
@EJB
private CommomBeanRemote obj=null;
private Collection<entity.Country>countries=null;
public Country() {}
public Collection<entity.Country> getCountries()
{
countries=obj.getAllCountries(); //Calls a remote EJB to retrieve the data.
System.out.println("The Country() method called.");//Here this displays 8 times unnecessarily
return countries;
}
public void setCountries(Collection<entity.Country> countries)
{
this.countries = countries;
}
}
显示实际数据的数据表绑定(bind)到国家属性value="#{country.countries}"
ManagedBean的相关内容及其对应的getter和setter如下。
public Collection<entity.Country> getCountries()
{
countries=obj.getAllCountries();
System.out.println("The Country() method called.");
return countries;
}
public void setCountries(Collection<entity.Country> countries)
{
this.countries = countries;
}
方法countries=obj.getAllCountries();
从远程EJB检索数据。 我觉得在这里发布这个方法(在 EJB 中)的实际实现是完全没有必要的。所有这些只是为了展示我正在尝试的内容。
现在,我的实际问题是 public Collection<entity.Country> getCountries(){}
不必要地执行了 8 次,而它只能执行一次,这在某些非常特定的情况下非常关键。
我已经尝试了很多次,同时增加和减少显示的行数,但这个方法总是执行 8 次,为什么......???
最佳答案
长话短说:Why JSF calls getters multiple times
在这种特殊情况下,您应该使用 @PostConstruct
方法而不是预加载/初始化从注入(inject)的业务服务检索的内容,而不是 getter 方法。
@ManagedBean
@RequestScoped
public class Country {
@EJB
private CommomBeanRemote commonBeanRemote;
private Collection<entity.Country> countries;
@PostConstruct
public void init() {
countries = commonBeanRemote.getAllCountries();
}
public Collection<entity.Country> getCountries() {
return countries;
}
// Setter is completely unnecessary here.
}
关于java - 为什么 JSF ManagedBean 方法要执行多次,而它们本来应该只执行一次?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7961475/