I have primefaces p:tree element. In my backing bean I have a field 'root' which holds all the tree structure. I populate this 'root' field in init method which is annotated with @PostConstruct annotation. When I perform some CRUD operation, like adding a new element to the tree and submit the form, the page is not updated with new information. The JSF bean is @ViewScoped. The thing is, that p:tree's getter gets called after page is refreshed, but I cannot put update logic in there as it is very expensive DB operation and getter gets called too many times in JSF lifecycle. The init method only gets called once and does not update the tree structure. Even if I make the bean @RequestScope, it does not fix the problem. The @PostConstruct method gets called first, then the database method addCategory() gets called and then the tree with old informtion is rendered. @RequestScope just makes everything slow, like selecting tree nodes in UI.. How can I solve this, preferably without ajax? I am using JSF 2.2 with Primefaces. I suppose this is not intended JSF behavior and something is wrong with my project's configuration maybe?
Bean:
@ManagedBean(name="menuBean")
@ViewScoped
public class MenuBean {
private TreeNode root;
private TreeNode selectedNode;
private UiElement category = new CategoryElement();
@PostConstruct
public void init() {
root = new DefaultTreeNode("root", null);
List<UiElement> rootElements = menuElementDao.getRootElements();
for (UiElement element : rootElements) {
if (element.isActive() || admin) {
createNodeWithChildren(element, root, admin);
}
}
}
public void addCategory() {
if (selectedNode != null) {
category.setParent((UiElement) selectedNode.getData());
}
menuElementDao.addElement(category);
category.clear();
}
public void setRoot(TreeNode root) {
this.root = root;
}
public TreeNode getRoot() {
return root;
}
}
Index.xhtml:
<h:form id="categoryForm">
<h:panelGrid id="categoryFormGrid" columns="2" style="border:1px solid black" styleClass="controlVisibility">
<h:outputLabel for="categoryName" value="Category name: "/>
<h:inputText id="categoryName" value="#{menuBean.category.name}">
<p:ajax/>
</h:inputText>
<h:commandButton value="Add Category" action="#{menuBean.addCategory()}"/>
<h:outputText/>
</h:panelGrid>
</h:form>
<h:form>
<p:tree value="#{menuBean.root}" var="node" selectionMode="single" selection="#{menuBean.selectedNode}" dynamic="true">
<p:ajax event="select" update="controlButtons"/>
<p:ajax event="unselect" update="controlButtons"/>
<p:treeNode>
<h:outputText value="#{node.render()}"/>
</p:treeNode>
</p:tree>
</h:form>