Document Information

Preface

Part I Introduction

1.  Overview

2.  Using the Tutorial Examples

Part II The Web Tier

3.  Getting Started with Web Applications

4.  Java Servlet Technology

5.  JavaServer Pages Technology

6.  JavaServer Pages Documents

7.  JavaServer Pages Standard Tag Library

8.  Custom Tags in JSP Pages

9.  Scripting in JSP Pages

10.  JavaServer Faces Technology

11.  Using JavaServer Faces Technology in JSP Pages

12.  Developing with JavaServer Faces Technology

Writing Bean Properties

Writing Properties Bound to Component Values

UIInput and UIOutput Properties

UIData Properties

UISelectBoolean Properties

UISelectMany Properties

UISelectOne Properties

UISelectItem Properties

UISelectItems Properties

Writing Properties Bound to Component Instances

Writing Properties Bound to Converters, Listeners, or Validators

Performing Localization

Creating a Resource Bundle

Localizing Dynamic Data

Localizing Messages

Creating a Message with a Message Factory

Using FacesMessage to Create a Message

Implementing an Event Listener

Implementing Value-Change Listeners

Implementing Action Listeners

Creating a Custom Validator

Implementing the Validator Interface

Creating a Custom Tag

Writing the Tag Handler

Writing the Tag Library Descriptor

Writing Backing Bean Methods

Writing a Method to Handle Navigation

Writing a Method to Handle an Action Event

Writing a Method to Perform Validation

Writing a Method to Handle a Value-Change Event

13.  Creating Custom UI Components

14.  Configuring JavaServer Faces Applications

15.  Internationalizing and Localizing Web Applications

Part III Web Services

16.  Building Web Services with JAX-WS

17.  Binding between XML Schema and Java Classes

18.  Streaming API for XML

19.  SOAP with Attachments API for Java

Part IV Enterprise Beans

20.  Enterprise Beans

21.  Getting Started with Enterprise Beans

22.  Session Bean Examples

23.  A Message-Driven Bean Example

Part V Persistence

24.  Introduction to the Java Persistence API

25.  Persistence in the Web Tier

26.  Persistence in the EJB Tier

27.  The Java Persistence Query Language

Part VI Services

28.  Introduction to Security in the Java EE Platform

29.  Securing Java EE Applications

30.  Securing Web Applications

31.  The Java Message Service API

32.  Java EE Examples Using the JMS API

33.  Transactions

34.  Resource Connections

35.  Connector Architecture

Part VII Case Studies

36.  The Coffee Break Application

37.  The Duke's Bank Application

Part VIII Appendixes

A.  Java Encoding Schemes

B.  About the Authors

Index

 

Creating a Custom Converter

As explained in Conversion Model, if the standard converters included with JavaServer Faces technology don’t perform the data conversion that you need, you can easily create a custom converter to perform this specialized conversion.

All custom converters must implement the Converter interface. This implementation, at a minimum, must define how to convert data both ways between the two views of the data described in Conversion Model.

This section explains how to implement the Converter interface to perform a custom data conversion. To make this implementation available to the application, the application architect registers it with the application, as explained in Registering a Custom Converter. To use the implementation, the page author must register it on a component, as explained in Registering a Custom Converter.

The Duke’s Bookstore application uses a custom Converter implementation, called tut-install/javaeetutorial5/examples/web/bookstore6/src/java/com/sun/bookstore6/converters/CreditCardConverter.java, to convert the data entered in the Credit Card Number field on the bookcashier.jsp page. It strips blanks and hyphens from the text string and formats it so that a blank space separates every four characters.

To define how the data is converted from the presentation view to the model view, the Converter implementation must implement the getAsObject(FacesContext, UIComponent, String) method from the Converter interface. Here is the implementation of this method from CreditCardConverter:

public Object getAsObject(FacesContext context,
     UIComponent component, String newValue)
         throws ConverterException {

    String convertedValue = null;
    if ( newValue == null ) {
        return newValue;
    }
    // Since this is only a String to String conversion,
     // this conversion does not throw ConverterException.
    
    convertedValue = newValue.trim();
    if ( (convertedValue.contains("-")) ||
         (convertedValue.contains(" "))) {
        char[] input = convertedValue.toCharArray();
        StringBuffer buffer = new StringBuffer(input.length);
        for ( int i = 0; i < input.length; ++i ) {
            if ( input[i] == ’-’ || input[i] == ’ ’  ) {
                continue;
            } else {
                buffer.append(input[i]);
            }
        }
        convertedValue = buffer.toString();
    }
        return convertedValue;
}

During the apply request values phase, when the components’ decode methods are processed, the JavaServer Faces implementation looks up the component’s local value in the request and calls the getAsObject method. When calling this method, the JavaServer Faces implementation passes in the current FacesContext instance, the component whose data needs conversion, and the local value as a String. The method then writes the local value to a character array, trims the hyphens and blanks, adds the rest of the characters to a String, and returns the String.

To define how the data is converted from the model view to the presentation view, the Converter implementation must implement the getAsString(FacesContext, UIComponent, Object) method from the Converter interface. Here is the implementation of this method from CreditCardConverter:

public String getAsString(FacesContext context,
     UIComponent component, Object value)
     throws ConverterException {
    
    String inputVal = null;
    if ( value == null ) {
        return null;
    }
    // value must be of the type that can be cast to a String.
    try {
        inputVal = (String)value;
    } catch (ClassCastException ce) {
        FacesMessage errMsg = MessageFactory.getMessage(
        CONVERSION_ERROR_MESSAGE_ID,
         (new Object[] { value, inputVal }));
        throw new ConverterException(errMsg.getSummary());
    }
    // insert spaces after every four characters for better
     // readability if it doesn’t already exist.
     char[] input = inputVal.toCharArray();
     StringBuffer buffer = new StringBuffer(input.length + 3);
    for ( int i = 0; i < input.length; ++i ) {
        if ( (i % 4) == 0 && i != 0) {
            if (input[i] != ’ ’ || input[i] != ’-’){
                 buffer.append(" ");
                 // if there are any "-"’s convert them to blanks.
             } else if (input[i] == ’-’) {
                buffer.append(" ");
             }
         }
         buffer.append(input[i]);
    }
     String convertedValue = buffer.toString();
    return convertedValue;
}

During the render response phase, in which the components’ encode methods are called, the JavaServer Faces implementation calls the getAsString method in order to generate the appropriate output. When the JavaServer Faces implementation calls this method, it passes in the current FacesContext, the UIComponent whose value needs to be converted, and the bean value to be converted. Because this converter does a String-to-String conversion, this method can cast the bean value to a String.

If the value cannot be converted to a String, the method throws an exception, passing the error message from the ResourceBundle, which is registered with the application. Registering Custom Error Messages explains how to register the error messages with the application. Performing Localization explains more about working with localized messages.

If the value can be converted to a String, the method reads the String to a character array and loops through the array, adding a space after every four characters.