I am having a data table like below in my xhtml:
<p:dataTable var="employee"
value="#{employeeBean.employeeLazyDataModel}">
Now in my backing bean, I have:
@ManagedBean
@RequestScoped
public class EmployeeBean implements Serializable {
@ManagedProperty("#{" + EmployeeLazyDataModel.MANAGEDBEAN_NAME + "}")
private EmployeeLazyDataModel employeeLazyDataModel;
public void preRender(ComponentSystemEvent event) throws Exception {
employeeLazyDataModel= // make a database call
}
// and getters + setters
Do you think I can call managedproperty inside preRender method? Please suggest. Thanks.
Surely this will work. The @ManagedProperty
is injected directly after bean's construction. The preRenderView
event listener requires an already-constructed bean before being invoked. So this is indeed guaranteed to work.
However, the canonical approach to initialize bean's state based on managed properties is a @PostConstruct
annotated method. Thus, so:
@ManagedBean
@RequestScoped
public class EmployeeBean implements Serializable {
@ManagedProperty("#{" + EmployeeLazyDataModel.MANAGEDBEAN_NAME + "}")
private EmployeeLazyDataModel employeeLazyDataModel;
@PostConstruct
public void init() throws Exception {
employeeLazyDataModel= // make a database call
}
// ...
}
(don't forget to remove the <f:event>
from the view)
As to the "expensive operations" complaint in the comment, just put the bean in view scope if you don't want to run it on a per-request basis, but only once on a per-view basis.
@ManagedBean
@ViewScoped
public class EmployeeBean implements Serializable {
Note that the preRenderView
event is fired before the view is rendered (thus, on every single HTTP request!), so you really need to keep the @PostConstruct
here. Otherwise, you have to add a check if FacesContext#isPostback()
returns false
.