Container Naming in JSF2 / PrimeFaces

What are the possible name containers in PrimeFaces? Why is it necessary to add the name container identifier to invoke the Ajax update when we want to update some UI control in the form using update=":mainForm:MainAccordian:userNameTextbox" ?

+8
jsf primefaces
source share
3 answers

After scanning IntelliJ, all of my JARs for implementing javax.faces.component.NamingContainer are what I found:

From PrimeFaces 5.3

  • Accordionpanel
  • Carousel
  • Columns
  • DataGrid
  • Datalist
  • DataScroller
  • DataTable
  • Page
  • Ring
  • Subtable
  • subspecies
  • Tabview
  • Treetable
  • UIData li>
  • UITabPanel

From MyFaces 2.1

  • HtmlDataTable
  • Htmlform
  • Uitree
  • Uiform
+3
source share

What is the possible name container in Prime faces

In the JSF name containers, exit the UINamingContainer .

why is it necessary to add the identifier of the name container to invoke the Ajax update when we want to update some user interface control in the form using update = ": mainForm: MainAccordian: userNameTextbox"

Let's say <h:outputText value="test1" id="userNameTextbox" /> and you add another <h:outputText value="test2" id="userNameTextbox" /> to your page, you get an error in which says you have a duplicate ID . You can watch it here on JavaDoc for UIComponent.setId (String) :

Set the component identifier of this UIComponent (if any). Component identifiers must obey the following syntax restrictions: There must not be a String with a zero length. The first character must be a letter or an underscore (''). Subsequent characters must be a letter, number, underscore ('') or dash ('-').

.. Moreover, it is important for you:

The specified identifier must be unique among all components (including faces) that are descendants of the nearest UIComponent of the ancestor, which is NamingContainer , or within the scope of the entire component tree, if there is no such ancestor, which is NamingContainer.

means that you cannot have two components with the same identifier in the same NamingContainer (if you do not have a NamingContainer at all, the whole tree counts as a NamingContainer). So you need to add a NamingContainer, for example, <h:form id="myNamingContainer" />

Let's look at the following example:

 <h:outputText value="test1" id="userNameTextbox" /> <h:form id="container1"> <h:outputText value="test2" id="userNameTextbox" /> </h:form> <h:form id="container2"> <h:outputText value="test3" id="userNameTextbox" /> </h:form> 

.. and you want to make an update for userNameTextbox. Which userNameTextbox are you referring to, because there are 3?

First? Then update userNameTextbox

Second? Then update container1: userNameTextbox

Third? Then update container2: userNameTextbox

+16
source share

Naming containers in Prime Faces

As we can see in the JSF Reference

NamingContainer is an interface that must be implemented by any UIComponent that wants to be a naming container. Container naming affects the behavior of the UIComponent.findComponent (java.lang.String) and UIComponent.getClientId () methods;

So, to find Naming Containers in PF, you need to check the hierarchy of the NamingContainer interface. In Eclipse, you can do this, for example, using the keyboard shortcut Ctrl + T in the NamingContainer.

In PF 5.3 there are, for example: AccordionPanel, Carousel, Columns, DataGrid, DataList, DataScroller, DataTable, Ring, SubTable, TabView, Tree, TreeTable.

Naming the effect of a container on a component identifier

  • Default behavior

Container naming provides a naming convention for child components. Therefore, it always adds a prefix to its id. So the id of the child component is: parent_component_id".concat(":").concat("component_id") . There is one tip that I read in JavaServer Faces 2.0, The Complete Reference , that even if you do not add NamingContainer to your page , this is always automatically added by JSF itself :) There is also a special algorithm for this creation (chapter 11: “Creating a user interface of a user interface →” called “Rules for creating a top-level component for a composite component”). Of course, when you do not set an id, it will be automatically generated (for example ., J_idt234) Thus, the total component identifier might look like this: "j_idt123: j_idt234: j_idt345".

  1. Change component name separator (with JSF 2.x)

There is a way to override the default component name separator (":"). You can define it in web.xml as a context-param named javax.faces.SEPARATOR_CHAR. For example:

 <context-param> <param-name>javax.faces.SEPARATOR_CHAR</param-name> <param-value>-</param-value> </context-param> 
  1. UIForm attribute "prependId"

In order not to add an area to the child component, an attribute exists (only in the UIForm component). But this is not recommended. Take a look at, for example, uiform-with-prependid-false-breaks-fajax-render

Use of component identifier (for example, in “update”, “process”)

  • Target ID

You can use all id: "componentParent: component". This is not recommended (the code will be fragile, any changes to the identifier will require changing identifiers in many places).

  1. Relative identifiers at the same level of the naming container

Inside a single named container, you can use a simple component identifier.

  1. PrimeFaces Search Expression Frame

If you do not know this feature, check out the PrimeFaces documentation. Prime Faces provides the Search Expression Framework with several very useful mechanisms.

You can search by keywords.

Keywords are an easier way to link to components; they allow ids so that when the identifier changes, the link does not need to be changed. Core JSF provides a couple of keywords, and PrimeFaces provides more along with support for composite expressions.

Examples: @this (current component), @form (nearest ancestor form), @namingcontainer (nearest ancestor naming container), @parent, @widgetVar (name). You can also mix these keywords in rather complex ways (Composite Expressions), for example: @form: @parent, @this: @parent: @parent

The second PF feature gives you PrimeFaces (PFS) samples.

PFS combines the JQuery Selector API with a reference to a component of the JSF model, so that links can be executed using the jQuery Selector API instead of the id-based JSF base model.

So you can, for example:

  • update all form elements update="@(form)"
  • update all data types update="@(.ui-datatable)"
  • update all components that have a Class style named myStyle update="@(.myStyle)"

Pretty powerful tool.

+1
source share

All Articles