Skip to main content

JSF 2.0, JPA, GlassFish and MySQL

Posted by caroljmcdonald on July 24, 2009 at 2:56 PM PDT


JSF 2.0, JPA, GlassFish and MySQL

JSF 2.0, JPA, GlassFish and MySQL


This Pet Catalog app explains a web application that
uses JSF 2.0, JPA, GlassFish and MySQL. I took this example  GlassFish
and MySQL, Part 2: Building a CRUD Web Application With Data Persistence

and modified it to use some of the new features JSF 2.0. 

Explanation of the usage of JSF 2.0, Java Persistence
APIs, Glassfish and MySQL in a sample Store Catalog Application

The image below shows the Catalog Listing page, which allows a user to
page through a list of items
in a store.




JSF 2.0 Facelets XHTML instead of JSP

For JSF 2.0, Facelets XHTML is the preferred way to declare JSF Web
Pages. JSP is supported for backwards compatibility, but not all JSF
2.0 features will be available for views using JSP as their page
declaration language.  JSF 2.0 Facelets has some nice features
like templating (similar in functionality to Tiles) and composite
components, which I'm not going to discuss here but you can read about
that in this article: http://www.ibm.com/developerworks/java/library/j-jsf2fu2/index.html
and in this Tech Tip Composite
UI Components in JSF 2.0.





The Catalog application's resources


JSF 2.0 standardizes how to define web resources. Resources are any
artifacts that a component may need in order to be rendered properly --
images, CSS, or JavaScript files.  With JSF 2.0 you put resources
in a resources
directory or a subdirectory.



In your Facelets pages, you can access css files with the  ,  javascript files with the
, and images with the JSF tags. The list.xhtml uses the  tag to load the styles.css stylesheet , and the tag to display images from the resources as
shown below:


Code Sample from:  list.xhtml


  name="css/styles.css" target="body"/>

     

      library="images" name="banner_logo.gif"  />   





The Catalog application uses a resource bundle to contain the static
text and
error messages used by the Facelets pages. Putting messages in a
resource bundle makes it easier to modify and internationalize your
Application text.  The messages are in a properties file in a java
package directory.


Code Sample from:  messages.properties 



     
Title=Pet Catalog

Next=Next

Previous=Prev

Name=Name

         





The resource bundle is configured in the faces-config.xml File (you don't need any other
configuration in the faces-config.xml for JSF 2.0, as explained later
you no longer have to configure managed beans and navigation with XML).



Code Sample from:  faces-config.xml



     


    <resource-bundle>

       
web.WebMessages

        msgs

   



         




The List.xhtml facelets page uses a JSF dataTable
component to display a list of
catalog items in an html table.  The dataTable component is useful when you want to show a set of
results in a table. In a JavaServer Faces application, the UIData
component
(the superclass of dataTable)  supports binding to a collection of
data objects. It does the
work of iterating over each record in the data source. The HTML dataTable
renderer
displays the data as an HTML table.


In the list.xhtml web page the dataTable is defined as shown
below: 
(Note: Red
colors
are for Java EE
tags, annotations code, 
and Green
is
for my code
or variables)


Code Sample from:  list.xhtml



     
<h:dataTable value='#{catalog.items}' var='row'
border="1"

      cellpadding="2" cellspacing="0">


     

     


The value attribute of a dataTable
tag references the data to be included
in the table. The var
attribute specifies a
name that is used by the components within the dataTable
tag as an alias to the data referenced in the value
attribute of dataTable.  In the dataTable
tag from the List.jsp
page, the value attribute points to a list
of catalog items. The var
attribute points
to a single item in that list. As the dataTable
component iterates through the list, each reference to dataTableItem

 points to the current item in the
list.





JSF 2.0 Annotations instead of XML configuration



The dataTable's value

is bound to the items
property
of the catalog managed
bean. With JSF 2.0 managed beans do not have to be configured in the
faces-config.xml file, you annotate the managed beans instead as shown
below:


Code Sample from: Catalog.java


     

      @ManagedBean

      @SessionScoped

public class Catalog
implements Serializable {

     

     


     


     

     

By convention, the name of a managed bean is the same as the class
name, with the first letter of the class name in lowercase. To specify
a managed bean name you can use the name attribute of the ManagedBean
annotation, like this: @ManagedBean(name = "Catalog").



This Catalog ManagedBean items
property is defined as shown below:


Code Sample from: Catalog.java


    private DataModel items = null;




    public DataModel getItems()
{

        if (items == null) {

           
getPagingInfo();

           
items = new ListDataModel(getNextItems(pagingInfo.getBatchSize(),
pagingInfo.getFirstItem()));

        }

        return items;

    }

   



     

     



The getItems()
method wraps a List of item objects in a DataModel.
UIData,
the superclass of dataTable,
supports data binding to a
collection of data objects represented by a DataModel
instance.  The data
collection underlying a DataModel instance is modeled as a collection
of row objects that can be accessed by a row index.  The APIs
provide mechanisms to position to a specified row index, and to
retrieve an object that represents the data that corresponds to the
current row index.   


The Item
properties Name, Photo, and price  are
displayed with the column
component:


Code Sample from: list.xhtml



<h:dataTable var="row" value="#{catalog.items}">
  <h:column>

      <f:facet name="header">

          <h:outputText value="#{msgs.Name}"/>

     

      <h:outputText value="#{row.name}"/>

 
  

  <h:column>

      <f:facet name="header">

          <h:outputText value="#{msgs.Photo}"/>

     

     
library="images" name="#{row.imagethumburl}"/>


 


  <h:column>

      <f:facet name="header">

          <h:outputText value="#{msgs.Price}"/>

     

      <h:outputText value="#{row.price}"/>

 


     



     


The column
tags represent columns of data in a UIData
component. While
the UIData component is iterating over the rows of data, it processes
the UIColumn component associated with each column tag for each row in
the table.


The UIData component  iterates through the list
of items
(catalog.items
and displays the row.price.
Each
time UIData iterates through the list of items, it renders one cell in
each column.


The dataTable and column tags use facet
to represent parts of the
table that are not repeated or updated. These include headers,
footers,
and captions.


Using the Java Persistence API (JPA) with JSF

The


Catalog

ManagedBean uses the Java
Persistence API
EntityManager
Query
object to return a list of items.
The Catalog ManagedBean annotates the field private EntityManager em; 
with @PersistenceUnit
, which causes an entity manager factory to be injected when the managed bean is instatiated.




Code Sample from: Catalog.java
 

     
@ManagedBean

      @SessionScoped

public class Catalog
implements Serializable {


    

    @PersistenceUnit(unitName
= "catalogPU")

    private EntityManagerFactory
      emf;

     

    private EntityManager getEntityManager() {

        return
emf.createEntityManager();

    }

     

    public List  getNextItems(int
maxResults, int firstResult) { 

       EntityManager em =
getEntityManager();

       try {    

         Query q = em.createQuery("select
object(o)
from Item as o");

         q.setMaxResults(maxResults);

         q.setFirstResult(firstResult);

         return
q.getResultList();

        } finally {

           
em.close();

       
}      

   }

   

     


The Java Persistence Query
APIs
are used to create and execute queries that can return a
list of results.  The JPA Query interface provides
support for pagination via the setFirstResult() and setMaxResults()
methods: q.setMaxResults(int maxResult)
sets the maximum number of results to retrieve. q.setFirstResult(int startPosition)
sets the position of the first result to retrieve.

In the code below, we show the Item
entity class which maps to the  ITEM table that stores the
item instances. This is a
typical Java Persistence entity object. There are two requirements for
an entity:

  1. annotating the class with an @Entity
    annotation.
  2. annotating   the primary key identifier with @Id

Because the fields name, description.... are basic mappings from the
object fields to columns of the same name in the database table, they
don't have to be annotated.  The O/R  relationships with Address
and Product
are also annotated. For more information on
defining JPA entities see Pro
EJB 3: Java Persistence API book
.


Code Sample from: Item.java


      @Entity

public class Item
implements java.io.Serializable {

     

   
@Id
   

    private Integer id;


    private String name;   

    private String description;   

    private String imageurl;   

    private String imagethumburl; 

    private BigDecimal price;

    @ManyToOne

    private Address
address;

     
    @ManyToOne

    private Product
product;


     

    public Item() { }

    


    public String getName() {

       
return name;

    }


    public void setName(String name) {

       
this.name = name;

    }
    

     


    ...

}   

     

     




The Catalog
ManagedBean pages through the list of Items
by
maintaining the PagingInfo.firstItem and PagingInfo.batchSize
attributes and passing these as
parameters to the  getNextItems(firstItem,
batchSize) method.
The catalog's
scope  is
defined with the annotation @SessionScoped,
a JSF Managedbean
with session scope will be stored in the session meaning that the
bean's properties will stay alive for the life of the Http Session.



A JSF commandButton
is  used to provide a button to click on to
display the next page of items.  The commandButton
tag is used to submit an action event
to the application. 


Code Sample from: list.xhtml


       
      action="#{catalog.next}"
value="#{msgs.Next}" />   

     


This

commandButton action
attribute
references the catalog
Managed bean next()
method which calculates
the
next page's first row number  and returns a logical outcome
String, which causes the list.xhtml
page
to display the next page's
list .
The catalog
next
method is defined as shown below:


Code Sample from: catalog.java


   public String next() {

       if (firstItem + batchSize
< itemCount()) {

          
firstItem += batchSize;

       }

       return "list";

   }

     


JSF 2.0 Simplified Navigation


The JavaServer Faces 2.0  NavigationHandler
convention adds .xhtml to the logical outcome of the action method (in
this example list)
and
loads that file, in this case, it loads the list.xhtml
page after this method returns. If the action doesn't begin with a
forward slash (/), JSF assumes that it's a relative path.  You can
specify an absolute path by adding the slash like this "/items/list".



A JSF commandLink
is  used to provide a link to click on to
display a page with the item details. This 

commandLink
action
attribute 
references The catalog
getDetail()
method:


Code Sample from: list.xhtml


  

      

          value="Name"/>

      


       commandLink action="#{catalog.getDetail}"
value="#{row.name}"/>   

  


     


The catalog
getDetail()
method  gets the item
data from the
current row of the dataModel,
and returns a string which causes the detail.xhtml
page to display
the item details :


Code Sample from: Catalog.java


    public String getDetail()
{

        item = (Item) model.getRowData();

        return "detail";

    }

     


The JavaServer Faces NavigationHandler
adds .xhtml to the logical outcome of the action, detail

 and loads
that file. In this case, the
JavaServer Faces implementation loads the detail.xhtml

page after this method returns.


The detail.xhtml uses the outputText
component to display the catalog
ManagedBean's item
properties:


Code Sample from: detail.xhtml
 

   
outputText
value="#{catalog.item.name}"
title="Name" />

   
title="Description"/>

   


   
catalog
.item.price}"
title="Price" />

   
catalog
.item.address.city}"
title="Address" />

   
catalog
.item.contactinfo.email}"
title="Address"/>
 




    



Hot Deployment and Session Retention with JSF 2.0 and Glassfish

  • Incremental compile of all JSF 2.0  artifacts when you save.
  • Auto-deploy of all web or Java EE 6 artifacts
  • Session retention: maintain stateful sessions across
    re-deployments



Conclusion

This concludes the sample application which demonstrates a pet catalog
web application which uses JSF 2.0, JPA, GlassFish and MySQL.


Running the Sample Application

  1. If you haven't already done so, download and install NetBeans IDE , GlassFish , and MySQL Community
    Server
    . You can download and install GlassFish with
    NetBeans as a single bundle
    .
  2. Follow these instructions
    to install JSF Mojarra 2.0.0 Beta2 on GlassFish v2 or Glassfish v3

  3. Download
    the sample code.

Create the Pet Catalog database

In order to run the sample code you first have to create the Pet
Catalog database
and fill in  the Item table.


  1. Start NetBeans IDE
  2. Ensure that GlassFish is registered in the NetBeans IDE, as
    follows:

    • Click the Services tab in the NetBeans IDE.
    • Expand the Servers node. You should see GlassFish v2 in
      the list of servers. If not,
      register GlassFish v2 as follows:

      • Right-click the Servers node and select Add Server.
        This opens an Add Server Instance wizard.
      • Select GlassFish v2 in the server list of the
        wizard
        and click the Next button.
      • Enter the location information for the server and
        click
        the Next button.
      • Enter the admin name and password and click the
        Finish
        button.

  3. Start the MySQL or Java DB database as follows:
    • Click the Services tab in the NetBeans IDE.
    • Expand the databases node. You should see the Java DB
      database in the list of databases. If you have installed the MySQL
      server database, you should also see the MySQL database in the list of
      databases.. Note:  Java DB 
      comes bundled with Netbeans, you can  download MySQL separately.


    • Right-mouse click on the Java DB or MySQL server
      database
      and select Start.
  4. If you installed MySQL, set the properties of the MySQL
    server database as follows:

    • Right-click on the MySQL server database and select
      Properties. This opens the MySQL Server Properties dialog box, as shown
      in
      Figure 8
      .

       

      MySQL Server Basic Properties

      Figure
      8.
      MySQL Server Basic Properties

       

    • In the Basic Properties tab, enter the server host name
      and port number. The IDE specifies localhost as the
      default server host name and 3306 as the default server
      port number.
    • Enter the administrator user name, if not displayed,
      and the
      administrator password -- the default
      administrator password is blank.
    • Click the Admin Properties tab.
    • Enter an appropriate path in the Path/URL to admin tool
      field. You
      can find the path by browsing to the location of a MySQL Administration
      application such as the MySQL Admin Tool.
    • Enter an appropriate path in the Path to start command.
      You can
      find the path by browsing to the location of the MySQL start command.
      To find the start command, look for mysqld in the bin
      folder of the MySQL installation directory.
    • Enter an appropriate path in the Path to stop command
      field. You
      can find the path by browsing to the location of the MySQL stop
      command. This is usually the path to mysqladmin in the bin
      folder of the MySQL installation directory. If the command is mysqladmin,
      in the Arguments field, type -u root stop to grant root
      permissions for stopping the server. The Admin Properties tab should
      look similar to
      Figure 9
      .

       

      MySQL Server Administration Properties

      Figure
      9.
      MySQL Server Administration Properties

       

    • Click the OK button.

     

  5. Right-click on the MySQL server or Java DB database and
    select Start.
  6. Create the petcatalog database as follows:
    • Right-mouse click on the Java DB or MySQL server
      database
      and select Create Database.
      This will
      open a create Database window.
    • Enter the database name catalog for Java DB or
      petcatalog
      for MySQL.





      For Java DB enter userid
      password app app as shown
      below:





       Click O.K. to accept the
      displayed settings.
  7. Create the tables in the catalog database
    as follows:

    • Underneath Databases you should see a database
      connection for
      the petcatalog database. For example
      MySQL:


      or Java DB:


    • Right-mouse click on the petcatalog connection and
      select Connect.
    • Right-mouse click on the petcatalog connection and
      select Execute Command. This will open up a SQL command window.
    • Copy the contents of the catalog.sql
      file in the riapetcatalog\exercises\exercise0

      directory and paste the contents into
      the SQL command window, as shown in below:

               

      Creating Tables in the Database

    •      
    • Click the Run SQL icon Run SQL icon
      (Ctrl+Shift+E) above the SQL command window.

    •      
    • Note: It is ok to see this: "Error code -1, SQL state 42Y55:
      'DROP TABLE' cannot be performed on 'ITEM' because it does not exist.
      Line 2, column 1" . This just means you are deleting a table that does
      not exist.  If you need to delete and recreate the tables you will
      not  see this message the second time.

           

    •    

     

  8.  
  9. View the data in the Pet
    Catalog database Item table as follows:


       

           
    • Underneath Databases you should see a database
      connection for
      the petcatalog database. For example
      MySQL:
             
               
                 
                   
                 
               
             


                   

      or Java DB:
             
               
                 
                   
                 
               
             


                   

           

    •      
    • If the database connection is broken like in the
      following diagram:

             

             

                 
      • Right-mouse click on the petcatalog connection and
        select Connect. as shown below:

                   

                 

      •          
      • if prompted for a password, for MySQL leave it
        blank, for JavaDB enter user app password app.

      •        

           

    •      
    • Expand
      the Tables node below the petcatalog database in the
      Services window. You should see the item table under the
      Tables node. You can expand the item table node to see
      the table columns, indexes, and any foreign keys, as shown in below :

      An Expanded Table Node

      Figure
      12.
      An Expanded Table Node

       


      You can view the contents of a table or column by right-clicking the
      table or column and selecting View Data as shown  below:

       

      Viewing the Contents of a Table

      Figure
      13.
      Viewing the Contents of a Table




  10. Follow these
    instructions to Create a JDBC Connection pool and JDBC resource.
    Name
    the  pool mysql_petcatalog_rootPool and the jndi resource
    jdbc/petcatalog. Note: you do not have to create a JDBC connection pool
    and resource if you use the Netbeans wizard to generate JPA entities
    from database tables as described in this article GlassFish
    and MySQL, Part 2: Building a CRUD Web Application With Data Persistence.

Running the Sample solution:

If you want to run the sample solution, you have to create the catalog
database tables first as described above.


  1. If you haven't already download
    the sample code
    and start the NetBeans IDE. Unzip the catalog.zip
    file which you downloaded, this will create a catalog directory with
    the project code.
  2. Open the
    catalog/setup/sun-resources.xml
    file and verify that the
    property values it specifies match those of the petcatalog database and
    jdbc resources you created. Edit the property values as necessary.

     
  3. Open the catalog project as follows:
    • In NetBeans IDE, click Open Project in the File menu.
      This opens the Open Project dialog.
    • Navigate in the Open Project dialog to the catalog 
      directory and click the Open Project button.

     

    In response, the IDE opens the catalog project. 
    You can view the logical structure of the project in the Projects
    window (Ctrl-1).

  4. Run the catalog by right-clicking on the catalog
    project in the Projects window and selecting Run Project. The NetBeans
    IDE compiles the application, deploys it on Glassfish, and brings up
    the default page in your browser.  (at
    http://localhost:8080/catalog/).


For more information see the following
resources:



Comments

I don't know about running JSF 2.0 on tomcat. In the release notes it only documents how to install on glassfish v2 or v3. https://javaserverfaces.dev.java.net/nonav/rlnotes/2.0.0/releasenotes.html It says this release of JSF requires: Java Servlet 2.5, JavaServer Pages 2.1 JavaServer Pages Standard Tag Library 1.2

Thanks, will try that out!

That's because you don't have the latest version of the EL library. Use Glassfish v3 b56 or later, and you get the correct behavior.

this gives an EL Exception

Ugh, I should have used preview. I meant: You can use <h:commandLink action="#{catalog.getDetail(row)}" value="#{row.name}" /> and...

Sure, but now that actions can have parameters, you can use and public String getDetail(Item item) { this.item = item; return "detail"; } Also, it would be good to remove the '...' around numbers in the SQL file. Derby does not like them. Cheers, Cay

yes , an advantage I think is the item = (Item) model.getRowData(); in the getDetail() method

Hi Carol, this looks very nice. I have a question about the getItems method. Is there any advantage to wrapping the List in a ListDataModel? If you just give the h:dataTable a List, it will supply its own ListDataModel. And you have one less dependency on the JSF API in your controller. Thanks, Cay

The web server container (in this case glassfish) injects the EntityManagerFactory for the@PersistenceUnit annotated property.

Will JSF inject @PersistenceUnit annotated property, or it's handled by Glassfish itself?

Hi Carol. Thanks for your article... One question: You wrote, that you can use Glassfish v2 or v3? But only v3 supports JEE6. So why does JSF 2.0 work in v2? I ask this, because I have to evaluate some web frameworks for a project soon. But I need to use a Tomcat Web Container, not Glassfish. I assume, that if JSF 2.0 works with Glassfish v2, it also works with a stable Tomcat release? Thanks for your help. Greetings Kai

concerning the configuration files, that would be a good question for the glassfish forum.

sorry the managed bean uses @PersistenceUnit(unitName = "catalogPU"), an EJB can use @PersistenceContext

Hi again, This might go too deep and off topic: but I wonder whether JSF (and any other JEE API) is using another API for handling the configuration files (e.g. faces-config.xml, pesistence.xml, web.xml etc.)? If so where can I get further details? Thanks Tai

Hi Carol, as you have stated above: "...The Catalog ManagedBean annotates the field private EntityManager em; with @PersistenceContext , which causes an entity manager to be injected when the managed bean is instatiated." But in your sampe code the entity manager factory is annotated with @PersistenceUnit. Correct or am I missing something? Thanks Tai