A Comprehensive Guide to JSF AJAX

These days I analyzed the AJAX implementation of Mojarra. My goal was to learn enough about it to implement an improved version of the original AJAX implementation in our BootsFaces libraries. Along the way I learned that I had chosen quite a chunk to swallow. The JSF AJAX specification has many, many options, most of which I wasn’t even aware of. Time to write an exhaustive guide. Apart from the JSF specification we’ll also have a look at it’s PrimeFaces counterpart and – of course – what BootsFaces 0.8.0 will bring to you.

Source code of the examples

You can find the source code of the examples on GitHub. There’s a second project on GitHub covering the BootsFaces AJAX examples.

Basic usage

Let’s start where most tutorials stop :). A regular <h:commandButton /> is turned into an AJAX button by adding an <f:ajax /> facet:

<h:commandButton value="Click me!">
    <f:ajax execute="@this" render="@form" />
</h:commandButton>

This snippet redraws the form surrounding the button. Note that it does not send the values of the input fields of the same form. They get lost by the redraw. That’s because we’ve set the execute attribute to @this, which in turn is the button itself. We’ll come back to execute and render in a minute.

Let’s check whether this is really AJAX. Modern PCs are so fast, you can’t always tell AJAX from non-AJAX. Open the F12-tool of your browser (or the ALT-CMD-I tool, if you’re using a Mac) to see what happens when you click the button. There is only a single request, and the response doesn’t consist of HTML, but XML:

As you can see, the non-AJAX request triggers quite a few HTTP requests. Usually, there are more requests than shown in the screenshot. We’ve used the CombinedResourceHandler of OmniFAces to concat the CSS and JavaScript files. In most cases the response of the initial post request is bigger than the AJAX request. However, the latter is not always true: it depends on the render attribute. In many cases, the major part of the speed boost comes from not loading and executing the CSS and JavaScript files again.

AJAX events

Basically, every DOM event is supported. Suffice it to present a single example: the <h:commandButton /> supports 15 events: blur, change, click, action, dblclick, focus, keydown, keypress, keyup, mousedown, mousemove, mouseout, mouseover, mouseup and select. The PrimeFaces command button is much more conservative: basically, the only AJAX operation it supports is click.

Note that the name of the event is the DOM event name – as opposed to the name of the corresponding JavaScript callback attribute, which is preceded by the syllable “on”. For instance, this event facet deals with the mouse click:

<h:commandButton value="Click me!">
    <f:ajax event="click" execute="@this" render="@form" />
</h:commandButton>

In this particular case, click is more or less the default action1, so you can omit the event name.

Components like the command button which derive from ActionSource also know the event called action. EditableValueHolders (such as input fields, check boxes and combo boxes) also support the event valueChange. (Notice the capital C – almost every other event handler is all lowercase).

Which components can be AJAXified?

You aren’t limited to the command button. Basically, every component dealing with user interactions can be AJAXified.

In the case of BootsFaces, every component is going to be AJAX-enabled when we’ve finished the implementation. That’s because every component supports JavaScript events like onmouseover, and the AJAX implementation of BootsFaces supports every JavaScript attributes.

Actions, actionlisteners and event listeners

Now let’s add some action to the example. Most of the time, JSF programmers want to call a method in a Java bean when clicking a button. There are three attributes to choose from:

  • First the listener defined in the <f:ajax /> is called. This method must implement the signature public void facetListener(javax.faces.event.AjaxBehaviorEvent event) throws javax.faces.event.AbortProcessingException.

    You can add multiple event listeners facets. However, when I tried this, it resulted in multiple AJAX requests. This may be useful in some cases – but it also resulted in multiple calls of the action and the actionListener. Be careful when you use this.

  • After calling the event listener, the actionListener attribute of the command button calls a method of the back-end bean. It takes a parameter of type ActionEvent. The action listener doesn’t return a value, and it can’t trigger navigation.
  • The action attribute of the command button calls a method of the back-end bean. It doesn’t take parameters, but it may return a String, which determines whether another JSF view is to be shown, and which one. If you don’t need navigation, you can either return null, or define the method to return void.
<h:form>   
  <h:commandButton value="Click me!"                                      
                   actionListener="#{AJAXBean.standardJSFActionListener}" 
                   action="#{AJAXBean.standardJSFAction}">                
    <f:ajax execute="@this" render="@form :messages"                    
            listener="#{AJAXBean.facetListener}"/>                 
  </h:commandButton>                                                      
</h:form>      
public void facetListener(javax.faces.event.AjaxBehaviorEvent event)
		throws javax.faces.event.AbortProcessingException {         
	report("f:ajax listener called");                               
}                                                                   
                                                                    
public void standardJSFActionListener() {                           
	report("Standard JSF actionlistener without parameters called");
}                                                                   
                                                                    
public void standardJSFActionListener(ActionEvent even) {           
	report("Standard JSF actionlistener called");                   
}                                                                   


The numbers in the message area are timestamps. The newest action is on top.

Multiple event listeners

Sometimes you want to trigger different actions on different events. In this case you can add multiple <f:ajax /> facets, each with its own event, its own partial processing (see below) and its own partial DOM update (also explained below):

<h:commandButton value="Start navigation" 
   style="#{AJAXBean.buttonRed?'background-color:red':''}"
  action="landingPage.jsf">                                                                      
  <f:ajax execute="@this" render="@form" />                                                      
  <f:ajax event="mouseover" execute="@this" render="@this :messages"                             
    listener="#{AJAXBean.mouseOverListener}" />                                                  
  <f:ajax event="mouseout" execute="@this" render="@this :messages"                              
    listener="#{AJAXBean.mouseOutListener}" />                                                   
</h:commandButton>                                                                               

Of course it pays to be careful with events that are frequently fired, such as mousemove or mouseover and mouseout. AJAX requests involve a lot of network traffic and network latency, so keep an eye on performance.

PrimeFaces <prime:ajax /> listeners

PrimeFaces allows you to optionally omit the parameter of the action listener. Apart from that, PrimeFaces offers an extension of <f:ajax />. Among other things, <prime:ajax /> can automatically update the <prime:messages />, so you don’t have to mention this each and every time you add an AJAX behavior to a component. At this point, I’d like to point you to the PrimeFaces documentation: it’s very good, so I’ll resists the temptation to write just another tutorial.

As a corner case, it’s possible to use <f:ajax /> with PrimeFaces components. So far, I didn’t note any problem, but I wouldn’t recommend to mix namespaces like this, nonetheless.

I also observed that the mouseover event is fired on a PrimeFaces <prime:inputText /> each time the mouse is moved. It seems they fire the mouseover event when a mousemove event is fired. This makes the mouseout event unreliable. In my demo, it was almost always followed by a belated mouseover event.

The PrimeFaces approach to simplify AJAX

As for the command buttons, PrimeFaces adds a very nice addition: you don’t need to add a facet to the component. Instead, you can add the update attribute. It converts the command button into an AJAX button, and defines which part of the DOM is to be updated. In my eyes, update is a more intuitive name than render, so the resulting code is not only more compact, but also reads better than native JSF code.

<p:growl id="growl" life="2000" />
<p:commandButton value="Ajax Submit"
                 update="growl" 
                 actionListener="#{buttonView.buttonAction}"/>

The BootsFaces approach to simplify AJAX

The BootsFaces approach to AJAX starts with a simple observation. Basically, AJAX is JavaScript. JSF AJAX is a short JavaScript snippet calling a Java back-end bean method. Now, most BootsFaces components have a lot of JavaScript event handler attributes. For instance, the onclick is used to call JavaScript code when the component is clicked. Why don’t we use the existing JavaScript attributes like onclick, onfocus and onkeydown to define AJAX?

Starting with version 0.8.0, BootsFaces does exactly that. Unfortunately, the JSF engine translates EL expressions a bit too eagerly, so I had to invent a new syntax. Here’s a code snippet showing more or less every AJAX event of the <b:selectOneMenu />:

<b:selectOneMenu value="#{AJAXBean.brand}" id="brandID"                                                       
	onchange="console.log('before onChange');ajax:AJAXBean.onChange();javascript:console.log('afterOnChange')"
	onblur="console.log('blur');ajax:AJAXBean.onBlur()"                                                       
	onfocus="console.log('focus');ajax:AJAXBean.onFocus()"                                                    
	onclick="console.log('click');ajax:AJAXBean.onClick()"                                                    
	ondblclick="console.log('dblclick');ajax:AJAXBean.onDblClick()"                                           
	onkeydown="console.log('keyd own');ajax:AJAXBean.onKeyDown()"                                             
	onkeyup="console.log('key up');ajax:AJAXBean.onKeyUp()"                                                   
	onkeypress="console.log('key press');ajax:AJAXBean.onKeyPress()"                                          
	onmousedown="console.log('mouse down');ajax:AJAXBean.onMouseDown();"                                      
	onmouseout="console.log('mouse out');ajax:AJAXBean.onMouseOut();"                                         
	onmouseup="console.log('mouse up');ajax:AJAXBean.onMouseUp();"                                            
	onmouseselect="console.log('mouse select');ajax:AJAXBean.onMouseSelect();"                                
	onvaluechange="console.log('valueChange);ajax:AJAXBean.onValueChange()"                                   
	onselect="console.log('select');ajax:AJAXBean.onSelect()"                                                 
	update="messages">                                                                                        
 
	<f:selectItem itemLabel="(Please select)" itemValue="0" />                                                
	<f:selectItem itemLabel="Fiat" itemValue="1" />                                                           
	<f:selectItem itemLabel="Honda" itemValue="2" />                                                          
	<f:selectItem itemLabel="Opel" itemValue="3" />                                                           
</b:selectOneMenu>                                                                                            

Of course, you won’t ever see such a monster in the wild. It’s just a tech demo. But it shows the idea nicely:

  • You can use every JavaScript event handler to define an AJAX callback. This even includes onmousemove. In almost every case, network latencies will prevent onmousemove to work flawlessly, but then, why should we forbid it?
  • It’s possible to combine JavaScript and AJAX in a single event handler. By default, the attribute is treated as JavaScript code. AJAX calls are marked by a preceding ajax:. After that follows a method call – including the parenthesis and the parameters (if any). If you want to execute JavaScript after the AJAX call, you put it behind the AJAX call, preceded by a javascript: marker.

Actually, BootsFaces has also a second approach to AJAX: compatibility. The library aims to be compatible to standard JSF and – if possible – to PrimeFaces. This means you can use the <f:ajax /> facets and the update and process attributes of PrimeFaces. BootsFaces also support the PrimeFaces facet <prime:ajax />, but only to a certain extend. It doesn’t support most advanced features of <prime:ajax />.

At the time of writing, the AJAX support of BootsFaces is limited to a few components: <b:commandButton />,<b:selectBooleanCheckbox />,<b:selectOneMenu />,<b:inputText />,<b:inputSecret />, <b:tabView /> and <b:tab />.

BootsFaces corner cases

Striving for compatibility leads to a couple of corner cases. You can add both an JavaScript event handler and an <f:ajax /> facet to a BootsFaces component. In this case the JavaScript event handler is executed first. The AJAX call of the ajax facet is executed after the AJAX call of the JavaScript handler. However, better avoid this corner case. This isn’t a documented behavior and may change over time.

You can also define the update and/or process attribute of the BootsFaces component and the execute and render attribute of the <f:ajax /> facet. In this case, the values of the provided by the component are considered default values for the facet.

Wrapping <f:ajax /> around multiple components

Now we’re in for a surprise. You add AJAX by putting an AJAX facet to a component, right? But it also works the other way round. You can put a group of components inside an AJAX facet:

<f:ajax execute="@form" render="@form"                 
  listener="#{AJAXBean.facetListener}">                
  <h:outputLabel for="ageID"                           
    value="Enter your age (18-65)"/>                   
  <h:inputText value="#{AJAXBean.age}" id="ageID">     
    <f:validateLongRange minimum="18" maximum="65" />  
  </h:inputText>                                       
  <h:commandButton value="validate age" />             
  <h:message for="ageID" id="ageMessage"/>             
                                                       
  <h:outputLabel for="nameID"                          
    value="Enter your first name (3 -20 letters)"/>    
  <h:inputText value="#{AJAXBean.name}" id="nameID"    
    required="true">                                   
    <f:validateLength minimum="3" maximum="20" />      
  </h:inputText>                                       
  <h:commandButton value="validate name" />            
  <h:message for="nameID" id="nameMessage"/>           
</f:ajax>                                              

If you want to add the same AJAX processing to each component of a field group, this may save you a couple of key strokes.

The execute attribute: partial processing

By default, AJAX requests always send the entire form. Sometimes you don’t need it, or this behavior even stands in your way. In this case you can use the execute attribute to send only an individual input field or a group of fields to the server:

<b:panel title="Partial processing and partial update">                          
  <h:form>                                                                       
    <b:panelGrid colSpans="3,2,2,5">                                             
      <h:outputLabel for="ageID" value="Enter your age (18-65)"></h:outputLabel> 
      <h:inputText value="#{AJAXBean.age}" id="ageID">                           
        <f:validateLongRange minimum="18" maximum="65" />                        
      </h:inputText>                                                             
      <h:commandButton value="validate age">                                     
        <f:ajax execute="ageID" render="ageID ageMessage messages"              
          listener="#{AJAXBean.facetListener}" />                                
      </h:commandButton>                                                         
      <h:message for="ageID" id="ageMessage"></h:message>                        
                                                                                 
      <h:outputLabel for="nameID"                                                
        value="Enter your first name (3 -20 letters)"></h:outputLabel>           
      <h:inputText value="#{AJAXBean.name}" id="nameID" required="true">         
        <f:validateLength minimum="3" maximum="20" />                            
      </h:inputText>                                                             
      <h:commandButton value="validate name">                                    
        <f:ajax execute="nameID" render="nameID nameMessage messages"           
          listener="#{AJAXBean.facetListener}" />                                
      </h:commandButton>                                                         
      <h:message for="nameID" id="nameMessage"></h:message>                      
                                                                                 
    </b:panelGrid>                                                               
    <h:commandButton value="validate both">                                      
      <f:ajax execute="@form" render="@form"                                     
        listener="#{AJAXBean.facetListener}" />                                  
    </h:commandButton>                                                           
    <h:messages id="messages/>                                                               
  </h:form>                                                                      
</b:panel>                                                                                                                            
@ManagedBean
@SessionScoped
public class AJAXBean {
  private int age;
  
  private String name;
  public int getAge() {
    return age;
  }

  public void setAge(int age) {
    this.age = age;
    FacesContext.getCurrentInstance().addMessage(null, new FacesMessage("You've successfully entered the age."));
  }

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
    FacesContext.getCurrentInstance().addMessage(null, new FacesMessage("You've successfully entered the name."));
  }
}


The numbers in the message area are timestamps. The newest action is on top.

This example allows you to validate each field individually, or both fields at the same time. The latter doesn’t accept the input unless both fields are valid. Partial processing allows you to check input fields even if the form contains invalid values in other fields.

The render attribute: partial update of the DOM tree

Consider the previous example again. The upper two command buttons send only one of the two input field to the back-end bean. If we were to render the entire form, it would show the old value of the other field. If you’ve modified the other input field before clicking the button, your input is lost. To avoid this inconvience we’ve defined the AJAX event handler to update only one input field, the corresponding message and the global messages area:

<h:commandButton value="validate age">                                     
   <f:ajax render="ageID ageMessage messages"              
           execute="ageID" listener="#{AJAXBean.facetListener}" />                                
</h:commandButton>   

Search Expressions

It’s a bit inconvenient and error-prone to define an ID for each input field, each label and each message of a JSF view. You can make your life easier using the advanced search expressions. Actually, search expressions are possibly the most compelling reason to use PrimeFaces or – since version 0.8.0 – BootsFaces. Their search expression engines go far beyond the JSF standard.

I’ve dedicated an article to search expressions. For now, suffice it to say they are a great addition to JSF. Using advance search expressions instead of static ids makes it simpler to move widgets on the screen or to refactor your JSF view.

Navigation

Most people consider it a bit odd, but it’s possible to use AJAX to navigate to another JSF view. In general, the idea of a single-page application matches the idea of AJAX better. But if you insist to do so, you can also replace the entire JSF view using AJAX:

<h:form>                                      
  <h:commandButton value="Start navigation" action="landingPage.jsf">                 
    <f:ajax execute="@this" render="@form" /> 
  </h:commandButton>                          
</h:form>                                     

Note that the <f:ajax /> facet declares that the command button is to redraw only the form. But in reality the entire HTML page – including the header and the JavaScript imports – is replaced. You can see this in the network tab of your browser’s F12 tool (or ALT+CMD+I tool if you’re using a Mac):

As you can see, the UIViewRoot is replaced, and the replacement code starts with <html>. In other words: the ajax facet doesn’t render @form, but @all.

The immediate flag

The immediate flag is one of the more exotic flags. Basically, it’s only useful for the “cancel” button. Immediate suppresses the validation of the input. Actually, it doesn’t send the input to the back-end bean. The immediate flag is also available in the <f:ajax /> facet.

Delaying events

This flag has been introduced in JSF 2.2 to suppress AJAX events that are triggered to often. The attribute defines a number of milliseconds. If two or more events are fired within this time interval, every request except the most recent one is discarded.

The reset flag

Since JSF 2.2, you can use this flag to clear input fields in an AJAX request.

The disabled flag

Use this flag to disable an AJAX facet. Typically this attribute is used with an EL expression.

onevent, onerror, oncomplete and onsuccess

These are JavaScript callback functions that are called before or after an AJAX request:

  • onevent is called before the AJAX request is submitted.
  • onerror is called if an AJAX request results in an error. By the way, there’s a subtle difference between PrimeFaces and standard JSF. If the Java code raises an exception, standard JSF calls the onerror handler. PrimeFaces calls the onerror handler only if there’s a technical error, such as an http transport layer error. If the Java code raises an unhandled exception, PrimeFaces considers the response valid and calls the onsuccess handler. In other words: you can safely ignore onerror and onsuccess. In most cases oncomplete is all you need.
  • oncomplete and onsuccess are not available in standard JSF. However, they are available in the PrimeFaces <prime:ajax /> facet. They are called when an AJAX request is completed. In the case of oncomplete, it’s called regardless of whether the request resulted in an error. Onsuccess is called only if the request didn’t not cause an error.

Both PrimeFaces and BootsFaces allow you to check if a validation has failed. In the case of PrimeFaces, this information is always sent with the response, so you can simply check it:

<p:commandButton ... oncomplete="if (args &amp;&amp; !args.validationFailed) $('#dialog_id').dialog('close')" />

The weird entities &amp;&amp; are needed because the XML parser tries to interpret an ampersand sign as entity. So &amp;&amp; is simply an && operator.

BootsFaces needs a special component, <b:fetchBeanInfos />, to send the validation state with the response:

<h:form>
       ...
       <b:fetchBeanInfos />
       <b:commandButton value="Ajax Modal" ajax="true" update="@form:inform" 
          oncomplete="if(validationFailed) alert('Please enter valid input before opening the modal'); else $('#amodal').modal('show')" />
<h:form>

The async flag

This is a PrimeFaces addition. The async flag prevents AJAX events from being queued. Instead, they are executed truly asynchronously. Strictly speaking, most AJAX event aren’t AJAX events: they are synchronous.

Wrapping it up

The standard JSF approach to AJAX uses a dedicated facet. That’s a powerful approach, if a tad verbose. PrimeFaces and BootsFaces both simplify the use of AJAX.


Dig deeper

JSF 2.2 Javadoc of f:ajax
JSF 2.1 Javadoc of f:ajax
JSF 2.0 Javadoc of f:ajax
Detailed explanation of update and execute by Bauke Scholz


  1. unless you want to distinguish between mouse clicks and the corresponding keyboard action

7 thoughts on “A Comprehensive Guide to JSF AJAX

  1. Pingback: JAXenter.de

    1. Stephan Rauh Post author

      Fixed. In fact, the word was there, but it was hidden because I forgot to close the <code> HTML tag :). Thanks for reporting the bug!

      Reply
  2. Jon

    Hi Stephan,

    I noticed you are really knowledgeable with bootsfaces.

    Q. Why are there no remote sql JSF template examples for bootfaces?

    Reply
    1. Stephan Rauh Post author

      Simple: the BootsFaces SQL example doesn’t look different from a PrimeFaces SQL example. In large projects, the SQL code is even put into a different module of the program which compiles independently of the UI module. So I didn’t see any point in providing just another SQL example. But of course it’s possible to use SQL with BootsFaces, and many people do so.

      Reply

Leave a Reply

Your email address will not be published.