[ Team LiB ] Previous Section Next Section

A Bean-Based Web Application

In Hour 13, "More About Saving Data," you learned how to make a shopping cart application by creating several core classes and then using servlets and JSPs to manipulate those core classes. The core shopping cart classes are all implemented as JavaBeans, making them ideal candidates for the jsp:useBean action.

Many of the servlets used in Hour 13 become very short JSPs, thanks to the jsp:useBean and jsp:setProperty actions. Listing 14.10 shows the updated ShowProductCatalog2.jsp file.

Listing 14.10 Source Code for ShowProductCatalog2.jsp
<%@ page language="java" import="examples.cart.*,java.net.*,java.text.*" %>

<%!
// Declare a constant for the number of items to show on a page.
    public static final int ITEMS_PER_PAGE = 5;
%>

<html>
<body bgcolor="#ffffff">

<a href="ViewShoppingCart.jsp">View Shopping Cart</a>
<p>
<h1>Available Products</h1>
<table border="1">
<tr><th>Description<th>Quantity<th>Price

<%-- Get an instance of the product catalog class --%>
<jsp:useBean id="catalog" class="examples.cart.ProductCatalog"
    scope="application"/>
<%

// Get the next starting position for displaying catalog items.
    String startingPositionStr = (String) request.
        getParameter("StartingPosition");

    int startingPosition = 0;

// If there is a starting position parameter, parse it as an integer.
    if (startingPositionStr != null)
    {
        try
        {
// If there's an error parsing the number, the starting position will
// just remain 0.
            startingPosition = Integer.parseInt(startingPositionStr);
        }
        catch (Exception ignore)
        {
        }
    }

// Get ITEMS_PER_PAGE items at a time.
    Item[] items = catalog.getItems(startingPosition, ITEMS_PER_PAGE);

// Get a currency formatter for showing the price.
    NumberFormat currency = NumberFormat.getCurrencyInstance();

    for (int i=0; i < items.length; i++)
    {
        Item item = items[i];

// Create the URL for adding the item to the shopping cart.
        String addItemURL = 
            "AddToShoppingCart.jsp?"+
            "productCode="+URLEncoder.encode(item.getProductCode())+
            "&description="+URLEncoder.encode(item.getDescription())+
            "&quantity="+URLEncoder.encode(""+item.getQuantity())+
            "&price="+URLEncoder.encode(""+item.getPrice());
%>
<tr><td><%=item.getDescription()%><td><%=item.getQuantity()%>
    <td><%=item.getPrice()%>
<td><a href="<%=addItemURL%>">Add to Shopping Cart</a>
<%
    }
%>
</table>
<table border="0">
<tr>
<%
    if (startingPosition > 0)
    {
        int prevPosition = startingPosition-ITEMS_PER_PAGE;

// Don't let the starting position go negative.
        if (prevPosition < 0) prevPosition = 0;

// Write out a link to display the previous catalog page.
        out.println("<td><a href=\"ShowProductCatalog2.jsp?StartingPosition="+
            prevPosition+"\">&lt;&lt;Prev</a>");
    }

// Compute the next starting position in the catalog.
    int nextPosition = startingPosition+ITEMS_PER_PAGE;

// Make sure that there are still items to display at that starting
// position (that is, make sure nextPosition isn't greater than the total
// catalog size).
    if (catalog.itemsAvailable(nextPosition))
    {
// Write out a link to display the next catalog page.
        out.println("<td><a href=\"ShowProductCatalog2.jsp?StartingPosition="+
            nextPosition+"\">Next&gt;&gt;</a>");
    }
%>
</table>
</body>
</html>

Most of the ShowProductCatalog2.jsp file is identical to the version in Hour 13. The two main differences are the jsp:useBean action that gets the ProductCatalog object and the link to add an item to the shopping cart. Instead of using a servlet to add an item to the cart, the new ShowProductCatalog2.jsp file uses a JSP.

Listing 14.11 shows the AddToShoppingCart.jsp file that adds an item to the cart. This file is significantly smaller and easier to read than its corresponding servlet from Hour 13.

Listing 14.11 Source Code for AddToShoppingCart.jsp
<%-- Get a reference to the shopping cart --%>
<jsp:useBean id="cart" class="examples.cart.ShoppingCart" scope="session"/>

<%-- Create an item object --%>
<jsp:useBean id="item" class="examples.cart.Item" scope="page"/>

<%-- Copy the request parameters into the item --%>
<jsp:setProperty name="item" property="*"/>

<%-- Add the item to the shopping cart --%>
<% cart.addItem(item); %>

<%-- Display the product catalog again --%>
<jsp:forward page="ShowCartAfterAdd.jsp"/>

AddToShoppingCart.jsp is much smaller for two reasons. First, the code to get an instance of the shopping cart is reduced to a single line. The servlet must check to see whether the cart already exists and, if not, create it. The jsp:useBean handles that.

Second, the servlet must copy each parameter into the Item object, converting any integer or double quantities as necessary. The jsp:setProperty action copies all the parameters at once, because the parameters conveniently have the same names as their corresponding bean properties.

Likewise, the RemoveItem.jsp file, which replaces the RemoveItemServlet class from Hour 13, is equally small. Listing 14.12 shows RemoveItem.jsp.

Listing 14.12 Source Code for RemoveItem.jsp
<%-- Get the shopping cart --%>
<jsp:useBean id="cart" class="examples.cart.ShoppingCart" scope="session"/>

<%-- Ask the shopping cart to remove the item --%>
<% cart.removeItem(Integer.parseInt(request.getParameter("item"))); %>

<%-- Display the shopping cart --%>
<jsp:forward page="ShowCartAfterRemove.jsp"/>

Again, the biggest savings here is the one-line creation/retrieval of the shopping cart.

Listing 14.13 shows the SubmitOrder.jsp file that handles the order submission in place of the CheckoutServlet from Hour 13.

Listing 14.13 Source Code for SubmitOrder.jsp
<%-- Declare a page to receive any errors that occur --%>
<%@ page errorPage="ShoppingCartError.jsp" %>

<%-- Get the shopping cart instance --%>
<jsp:useBean id="cart" class="examples.cart.ShoppingCart" scope="session"/>

<%-- Create an object to hold shipping information --%>
<jsp:useBean id="shipping" class="examples.cart.Shipping" scope="page"/>

<%-- Copy the shipping information into the shipping object --%>
<jsp:setProperty name="shipping" property="*" />

<%-- Create an object to hold billing information --%>
<jsp:useBean id="billing" class="examples.cart.Billing" scope="page"/>

<%-- Copy the billing information into the billing object --%>
<jsp:setProperty name="billing" property="*" />

<html>
<body>
<h1>Thank you for your order.</h1>
<p>
Your order confirmation number is
<%= cart.completeOrder(shipping, billing) %>.
<p>
Please use this number when calling to inquire about your order status.
</body>
</html>

Once again, the JSP realizes a huge savings over the servlet by use of the jsp:useBean and jsp:setProperty actions. The SubmitOrder.jsp uses a slightly different philosophy for displaying its results, too. The CheckoutServlet class is forwarded to a JSP to display the order confirmation. If it has an error submitting the order, it prints out an error message.

SubmitOrder.jsp prints out the order confirmation and uses the errorPage option in the page directive to specify a page to handle the error. The error-handling page prints out an error message that is only useful for developers. Listing 14.14 shows the error-handling page.

Listing 14.14 Source Code for ShoppingCartError.jsp
<%@ page isErrorPage="true" %>
<html>
<body>
<h1>Error</h1>
<p>
Your order could not be processed because of the following error:
<pre>
<%= exception.getMessage() %>
</pre>
We are sorry for the inconvenience.
</body>
</html>
    [ Team LiB ] Previous Section Next Section