Real-Time Validation

As we saw in the section “Form Completion,” on page 9, you can implement basic Ajax in a JSF application with little more than a servlet and a few lines of JavaScript. In this example, we’ll implement real-time validation, which will give us the opportunity to explore some of the more complex interactions between Ajax and JSF.

The application shown in Figure 3 performs real-time validation. When the user enters the fifth character of the Zip Code, we execute an Ajax request to validate those five digits.

Figure 3. Real-time validation

image

On the server, we obtain a reference to the component that represents the Zip Code field and iterate over that component’s validators, invoking each in turn. If any of the validators attached to the component throws an exception, we catch the exception, write an error to the response, and terminate the request. Subsequently, back on the client, we display that error response in a DIV. That scenario is depicted in Figure 3, where the user has entered an invalid Zip Code.

Here’s the pertinent JSP:

image

We’ve wired the onkeyup event for our Zip Code field to a function called zipChanged, which we’ll discuss momentarily. We’ve also added a custom validator to the Zip Code component. That validator recognizes only the 97402 Zip Code; all other Zip Codes are considered invalid. Finally, we’ve added our errors DIV, which is initially empty.

This real-time validation example is more complex than the application discussed earlier, in the “Form Completion” section, because real-time validation forces us to access view state, meaning the component tree, for the JSP page. Remember that we need to get a reference to the Zip Code component and iterate over its validators. To do that, we need access to the view state, which is available only to POST requests. Because of that restriction, we issue a POST request, like this:

image

Notice the URL that we’re using for this request: window.document.forms[0].action. That URL represents the action for the lone form in the page; in effect, we’re tricking JSF into thinking that the user submitted the form. We’re doing that because we want to access the view state for the current page, which JSF makes available—after the Restore View phase of the life cycle—when the form is submitted.

The preceding code shows how we invoke the URL from the client, but how do we handle the URL on the server? In this case, because we need access to the view state, we can’t use a servlet. Servlets know nothing about JSF, so they can’t access the view state. Instead, we’ll use a phase listener and handle the request after the Restore View phase, when JSF has restored the component tree for us. Figure 4 shows the JSF life cycle when our phase listener handles the request.

Figure 4. The JSF life cycle with an Ajax phase listener

image

After the Restore View phase, JSF invokes our phase listener, which checks to see whether this is an Ajax request, signified by a request parameter; if so, the phase listener validates the component, generates a response, and short-circuits the life cycle. Here’s a truncated listing of that phase listener:

image

image

The preceding code fragment leaves out a majority of the details of the method. Here we want to emphasize that the phase listener goes into action after the Restore View phase of the life cycle, after JSF has prepped the view state for us. If the current request is an Ajax request—signified by a request parameter named ajax whose value must be true—the phase listener locates the Zip Code component and its validators, iterates over the validators, and generates a response. Finally, it calls the responseComplete method on the faces context to short-circuit the rest of the life cycle.

Notice that the phase listener short-circuits the life cycle only when we explicitly qualify a request as an Ajax request. That qualification is necessary because we must distinguish between Ajax requests and non-Ajax requests: We can’t short-circuit the life cycle on every request, or our application would not work at all.

Finally, back on the client, we process the response:

image

If the response text is okay, we know the Zip Code was valid, so we hide the errors DIV. If the response text is anything other than okay, we display the response text in the errors DIV.


javax.faces.context.FacesContext

image

  • void responseComplete()

Forces JSF to short-circuit the life cycle. After this method is called, JSF will not execute the next phase in the life cycle.



javax.faces.event.EditableValueHolder

image

  • Validator[] getValidators()

Returns an array of validators associated with an input component. All input components implement the EditableValueHolder interface.



image Note: JSF and POST requests

POST requests are meant to change state on the server, whereas GET requests are for obtaining information only. Because of that distinction, JSF makes view state available only to POST requests, which allows modifications to view state. If you’re implementing functionality that requires access to view state, you must send a POST request.


..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.149.253.210