shopping framework
TRANSCRIPT
-
8/2/2019 Shopping Framework
1/46
Java/XML-based Shopping Cart
Presented by
Mark Volkmann
Object Computing, Inc. (OCI)
2000 Object Computing, Inc.
All rights reserved. No part of these notes may be reproduced, stored
in a retrieval system, or transmitted, in any form or by any means,
electronic, mechanical, photocopying, recording or otherwise, without
the prior, written permission of Object Computing, Inc.
-
8/2/2019 Shopping Framework
2/46
Object Computing, Inc. Java/XML Shopping Cart2
Overview
Goal
create a prototype of a web-based shopping cart application that utilizes
Java servlets
XML and XSLT
HTML and JavaScript
Tools
Servlet Engine
Apache Tomcat 3.1
XML Parser
Apache Xerces - 1.1.3
XSLT Processor Apache Xalan 1.0.1
Java Development Kit
Sun JDK 1.2.2
-
8/2/2019 Shopping Framework
3/46
Object Computing, Inc. Java/XML Shopping Cart3
Screen Shots
-
8/2/2019 Shopping Framework
4/46
Object Computing, Inc. Java/XML Shopping Cart4
Screen Shots
-
8/2/2019 Shopping Framework
5/46
Object Computing, Inc. Java/XML Shopping Cart5
High Level Design
All client requests go through the GatewayServlet
The GatewayServlet directs each request to
a specific UseCaseController
A UseCaseController interacts with any number of
domain objects
Domain objects can populate themselves from databases
or XML documents
an improvement would be to move this functionality to other classes
that function as data adapters
Domain objects can create XML representations ofthemselves
an improvement would be to move this functionality to other classes
that function as data adapters
-
8/2/2019 Shopping Framework
6/46
Object Computing, Inc. Java/XML Shopping Cart6
Use Cases
View Inventory
display current inventory
allow user to enter item quantities desired
related files: ViewInventoryController.java, inventory.xsl
Add To Cart remove selected items from inventory
add selected items to users cart
invoke View Cart use case
related files: AddToCartController.java
View Cart
display contents of users cart
calculate total cost of cart including tax
done in XSLT stylesheet
related files: ViewCartController.java, cart.xsl
-
8/2/2019 Shopping Framework
7/46
Object Computing, Inc. Java/XML Shopping Cart7
Use Cases (Contd)
Remove From Cart
remove selected items from users cart
add selected items back to inventory
invoke View Cart use case
related files: RemoveFromCartController.java
Buy Cart gather information from user that is needed to process the transaction
includes name, address and credit card information
related files: BuyCartController.java, buy.xsl
Process Payment process credit card transaction
not actually done in sample code
display confirmation message
related files: ProcessPaymentController.java, purchase.xsl
-
8/2/2019 Shopping Framework
8/46
Object Computing, Inc. Java/XML Shopping Cart8
Interactions
Browser
Web Server
GatewayServlet
UseCaseController
Domain Object
Databases and
XML files
Domain Object Domain Object
UseCaseController UseCaseController
-
8/2/2019 Shopping Framework
9/46
Object Computing, Inc. Java/XML Shopping Cart9
Domain Objects
Item
holds a description, id, quantity and unit cost of an item
in the inventory or a user's cart
ItemCollection
holds a collection of Item objects Cart
extends ItemCollection
holds the Items currently in a user's cart
Inventory
extends ItemCollection holds the Items currently in the inventory
-
8/2/2019 Shopping Framework
10/46
Object Computing, Inc. Java/XML Shopping Cart10
Domain Objects (Contd)
Address
holds a street, city, state, country and postal code
used for user addresses
Person
holds the name and Address of a person
CreditCard
holds the name, number and expiration date of a credit card
Purchase
holds the Person, CreditCard, Cart and tax rate associated with a purchase
-
8/2/2019 Shopping Framework
11/46
Object Computing, Inc. Java/XML Shopping Cart11
Domain Objects (Contd)
Addressstreet : String
city : String
state : String
country : String
postalCode : String
Personname : String
address : Address
CreditCardname : String
number : String
expirationMonth : short
expirationYear : short
Itemid : String
description : String
quantity : int
unitCost : float
CartInventory
ItemCollectioncontents : Map
Purchasecard : CreditCard
cart : Cart
person : Person
taxRate : float*
1 1 1
1
-
8/2/2019 Shopping Framework
12/46
Object Computing, Inc. Java/XML Shopping Cart12
Controllers
GatewayControllerrun(ServletConfig, HttpServletRequest, HttpServletResponse) : void
AddToCartController
ProcessPaymentController
ViewCartControllerBuyCartController
ViewInventoryController
RemoveFromCartController
-
8/2/2019 Shopping Framework
13/46
Object Computing, Inc. Java/XML Shopping Cart13
GatewayServlet Overview
Creates a Map from use case names to
UseCaseController objects
only happens on the first request
mapping is described in UseCases.xml
more on this later
a use case name is passed as an initialization parameter to GatewayServlet
the use case name is a key in a Map of UseCaseControllers
this Map is placed in an HttpSession attribute so that
controllers can locate other controllers
useful when one controller needs to call another one
to finish processing a request
AddToCartController calls ViewCartController
after adding items to the cart
RemoveFromCartController calls ViewCartController
after removing items from the cart
-
8/2/2019 Shopping Framework
14/46
Object Computing, Inc. Java/XML Shopping Cart14
GatewayServlet Overview (Contd)
Looks up the UseCaseController that corresponds to
the requested use case name
Invokes the run method of the UseCaseController
This would be a good place to add
authentication
if the user has no current session then a login page could be displayed
authorization
GatewayServlet could restrict the use cases that a given user can execute
-
8/2/2019 Shopping Framework
15/46
Object Computing, Inc. Java/XML Shopping Cart15
HttpSession Attributes
Used to store
the UseCaseController objects
in a Map keyed on use case name
the Inventory
in a Map keyed on item id
a subclass of ItemCollection
the Cart
also in a Map keyed on item id
another subclass of ItemCollection
-
8/2/2019 Shopping Framework
16/46
Object Computing, Inc. Java/XML Shopping Cart16
UseCaseController Interface
package com.ociweb.framework;
import java.io.IOException;
import javax.servlet.http.*;
public interface UseCaseController {
void run(ServletConfig config,
HttpServletRequest request,
HttpServletResponse response) throws IOException;
}
ServletConfig provides access to the ServletContext which can be used to
read files in within the directory structure of the web app.
HttpServletRequest
provides access to form parameters andthe HttpSession object which contains a map of session attributes
HttpServletResponse
provides access to the Writer needed to send HTML back to the client
could also send WML
back to wireless devices
-
8/2/2019 Shopping Framework
17/46
Object Computing, Inc. Java/XML Shopping Cart17
ViewInventoryController Overview
This is the first UseCaseController that is invoked
If no Cart exists yet, it creates an empty Cart
If no Inventory exists yet, it creates an empty Inventory
and populates it
currently the data comes from inventory.xml
see next page
it really should come from a database
Creates a DOM Document object representing
the current inventory as XML
Transforms it to HTML by applying an XSLT stylesheet inventory.xsl
-
8/2/2019 Shopping Framework
18/46
Object Computing, Inc. Java/XML Shopping Cart18
inventory.xml
1
frying pan
39.99
5
2
spatula
4.99
7
-
8/2/2019 Shopping Framework
19/46
Object Computing, Inc. Java/XML Shopping Cart19
XMLUtil Overview
Provides static methods that make it easier to build
DOM XML Document objects
these return the new element so child elements can be added to it
Element appendChildElement(Node parent,
String childElementName)
Element appendChildElementWithText(Node parent,
String childElementName,
String text)
Element appendChildElementWithText(Node parent,
String childElementName,
float value)
Element appendChildElementWithText(Node parent,
String childElementName,
int value)
-
8/2/2019 Shopping Framework
20/46
Object Computing, Inc. Java/XML Shopping Cart20
XMLUtil (Contd)
Provides a static method that applies an XSLT stylesheet
to a DOM Documentvoid applyStylesheet(Document xmlDoc, String xslURL, Writer out)
void applyStylesheet(Document xmlDoc, InputStream xsl, Writer out)
Provides a static method that gets the value of a namedchild element within a given elementString getChildValue(Element element, String childName)
Provides static methods that pretty-print a DOM Document
void outputXML(Document doc) - sends to System.out for debuggingvoid outputXML(Document doc, OutputStream out)
-
8/2/2019 Shopping Framework
21/46
Object Computing, Inc. Java/XML Shopping Cart21
Mapping of Servlet Names to
Use Case Names
Tomcat web applications use web.xml to specify
servlet names and their initialization parameters
Each use case has a servlet mapping like the following
AddToCart
com.ociweb.framework.GatewayServlet
useCase
Add To Cart
-
8/2/2019 Shopping Framework
22/46
Object Computing, Inc. Java/XML Shopping Cart22
Mapping of Servlet Names to
Use Case Names (Contd)
There is one servlet mapping for each use case
All of them use GatewayServlet to service the request
An initialization parameter passed to GatewayServlet
identifies the use case being requested
Here are the URLs for running locally
using the default Tomcat port
http://localhost:8080/framework/servlet/AddToCart
http://localhost:8080/framework/servlet/BuyCart
http://localhost:8080/framework/servlet/RemoveFromCart
http://localhost:8080/framework/servlet/PurchaseCart http://localhost:8080/framework/servlet/ViewCart
http://localhost:8080/framework/servlet/ViewInventory
-
8/2/2019 Shopping Framework
23/46
Object Computing, Inc. Java/XML Shopping Cart23
Mapping of Use Cases to
UseCaseController Objects
Use case names are mapped to UseCaseController classes
by another XML file (UseCases.xml)
Add To Cart
com.ociweb.shopping.AddToCartController
Usage of this was described earlier
see page titled GatewayServlet Overview
-
8/2/2019 Shopping Framework
24/46
Object Computing, Inc. Java/XML Shopping Cart24
Sample UseCaseController(ViewCartController)
package com.ociweb.shopping;
import com.ociweb.framework.*;
import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;
import org.xml.sax.SAXException;
continued on next page
used to produce the right
screen shot on page 3
-
8/2/2019 Shopping Framework
25/46
Object Computing, Inc. Java/XML Shopping Cart25
Sample UseCaseController (Contd)
public class ViewCartController implements UseCaseController {
public void run(ServletConfig config,
HttpServletRequest request,
HttpServletResponse response)
throws IOException {
Writer out = response.getWriter();
HttpSession session = request.getSession();
Cart cart = (Cart) session.getAttribute("cart");
XMLUtil.outputXML(cart.getXML()); // for debugging
-
8/2/2019 Shopping Framework
26/46
Object Computing, Inc. Java/XML Shopping Cart26
Sample UseCaseController (Contd)
try {
ServletContext context = config.getServletContext();
InputStream is = context.getResourceAsStream("/WEB-INF/cart.xsl");
XMLUtil.applyStylesheet(cart.getXML(), is, out);
} catch (SAXException e) {
out.write(e.toString());
}
}
}
reads file from the directory of the web app.
(in my case, C:\Tomcat\webapps\framework)
-
8/2/2019 Shopping Framework
27/46
Object Computing, Inc. Java/XML Shopping Cart27
Sample XSLT Stylesheet(cart.xsl)
-
8/2/2019 Shopping Framework
28/46
Object Computing, Inc. Java/XML Shopping Cart28
Sample XSLT Stylesheet (Contd)
Cart Contents
Select
Description
Unit Cost
Quantity
Total Cost
table headers
testing whether cart is empty
outputs a table row for
each item in the cart
sorted on description
uses template on page 31
-
8/2/2019 Shopping Framework
29/46
Object Computing, Inc. Java/XML Shopping Cart29
Sample XSLT Stylesheet (Contd)
Subtotal:
Tax:
calculates the total before tax
calculates the tax
-
8/2/2019 Shopping Framework
30/46
Object Computing, Inc. Java/XML Shopping Cart30
Sample XSLT Stylesheet (Contd)
Total:
Your cart is currently empty.
calculates the total including tax
one of the registered
servlet names
posts form fields
to form action
-
8/2/2019 Shopping Framework
31/46
Object Computing, Inc. Java/XML Shopping Cart31
Sample XSLT Stylesheet (Contd)
-
8/2/2019 Shopping Framework
32/46
Object Computing, Inc. Java/XML Shopping Cart32
Sample XSLT Stylesheet (Contd)
outputs a table row for
the current cart item
see apply-templates on page 27
-
8/2/2019 Shopping Framework
33/46
Object Computing, Inc. Java/XML Shopping Cart33
Deficiencies in the Prototype
Controllers are dependent on the Servlet API
implementing controllers so they are unaware that they are
being invoked from a servlet is difficult
some controllers need to
access form parameters in the HttpServletRequest
send output to the client using information in the HttpServletResponse access and update session-level data in the HttpSession
read files in the directory of the web app. using the HttpContext
-
8/2/2019 Shopping Framework
34/46
Object Computing, Inc. Java/XML Shopping Cart34
Deficiencies in the Prototype (Contd)
Inventory persistence
the inventory is reloaded from an XML document
every time the servlet engine is restarted
the inventory is stored in a session-scoped object
so multiple users are not supported
one solution would to be to modify the Inventory class so that itinteracts directly with the database in every get and set method
as is done in a container-managed entity EJB
-
8/2/2019 Shopping Framework
35/46
Object Computing, Inc. Java/XML Shopping Cart35
Source Code
Complete source code is available in a separate zip file
ShoppingFramework.zip
setup steps are on the next page
Source code for couple of key classes follows
-
8/2/2019 Shopping Framework
36/46
Object Computing, Inc. Java/XML Shopping Cart36
Setup Steps
Here are the setup steps to run the provided code
installations
install Tomcat 3.1
install JDK 1.2 or 1.3
environment variables
insure that JAVA_HOME points to the JDK is installed insure that TOMCAT_HOME points to where TOMCAT is installed
copy framework.war to %TOMCAT_HOME%\webapps
modify %TOMCAT_HOME%\bin\tomcat.bat so CLASSPATH
contains xerces.jar BEFORE %TOMCAT_HOME%\lib\xml.jar
xml.jar is Suns Project X XML parser
start Tomcat point browser to http://localhost:8080/framework/servlet/ViewInventory
-
8/2/2019 Shopping Framework
37/46
Object Computing, Inc. Java/XML Shopping Cart37
GatewayServlet
package com.ociweb.framework;
import java.io.*;
import java.util.*;
import javax.servlet.*;
import javax.servlet.http.*;
import org.apache.xerces.parsers.DOMParser;
import org.w3c.dom.*;
import org.xml.sax.*;
public class GatewayServlet extends HttpServlet {
private ServletConfig config;
public void doGet(HttpServletRequest request,
HttpServletResponse response)
throws IOException, ServletException {response.setContentType("text/html");
PrintWriter out = response.getWriter();
config = getServletConfig();
-
8/2/2019 Shopping Framework
38/46
Object Computing, Inc. Java/XML Shopping Cart38
GatewayServlet (Contd)
HttpSession session = request.getSession();
Map controllers = (Map) session.getAttribute("controllers");
if (controllers == null) {
controllers = getControllers();
session.setAttribute("controllers", controllers);
}
String useCase = getInitParameter("useCase");
UseCaseController controller =
(UseCaseController) controllers.get(useCase);
if (controller == null) {
out.write("Fatal error: No controller found for " + useCase);
} else {
controller.run(config, request, response);
}
}
-
8/2/2019 Shopping Framework
39/46
Object Computing, Inc. Java/XML Shopping Cart39
GatewayServlet (Contd)
public void doPost(HttpServletRequest request,
HttpServletResponse response)
throws IOException, ServletException {
doGet(request, response);
}
private static Map getControllers() {
Map controllers = new HashMap();
ServletContext context = config.getServletContext();
InputStream is = context.getResourceAsStream("/WEB-INF/UseCases.xml");
-
8/2/2019 Shopping Framework
40/46
Object Computing, Inc. Java/XML Shopping Cart40
GatewayServlet (Contd)
try {
DOMParser parser = new DOMParser();
parser.parse(new InputSource(is));
Document doc = parser.getDocument();
NodeList useCases = doc.getElementsByTagName("useCase");
int count = useCases.getLength();
for (int i = 0; i < count; i++) {
Element useCase = (Element) useCases.item(i);
String name = XMLUtil.getChildValue(useCase, "name");
String controller = XMLUtil.getChildValue(useCase, "controller");
Class controllerClass = Class.forName(controller);
controllers.put(name, controllerClass.newInstance());
}
} catch (Exception e) {
System.err.println(e);
}return controllers;
}
}
-
8/2/2019 Shopping Framework
41/46
Object Computing, Inc. Java/XML Shopping Cart41
XMLUtil
package com.ociweb.framework;
import java.io.*;
import org.apache.xalan.xslt.*;
import org.apache.xerces.parsers.DOMParser;
import org.apache.xml.serialize.*;
import org.w3c.dom.*;
import org.xml.sax.SAXException;
public class XMLUtil {
/**
* Note: parent must already be directly or indirectly appended
* to a Document before calling this.
*/
public static Element appendChildElement(Node parent,
String childElementName) {
Document doc = parent instanceof Document ?(Document) parent : parent.getOwnerDocument();
Element childElement = doc.createElement(childElementName);
parent.appendChild(childElement);
return childElement;
}
-
8/2/2019 Shopping Framework
42/46
Object Computing, Inc. Java/XML Shopping Cart42
XMLUtil (Contd)
public static Element appendChildElementWithText(Node parent,
String childElementName,
String text) {
Document doc = parent.getOwnerDocument();
Element childElement = doc.createElement(childElementName);
parent.appendChild(childElement);
Text textNode = doc.createTextNode(text);
childElement.appendChild(textNode);
return childElement;
}
-
8/2/2019 Shopping Framework
43/46
Object Computing, Inc. Java/XML Shopping Cart43
XMLUtil (Contd)
public static Element appendChildElementWithText(Node parent,
String childElementName,
float value) {
return appendChildElementWithText
(parent, childElementName, String.valueOf(value));
}
public static Element appendChildElementWithText(Node parent,
String childElementName,
int value) {
return appendChildElementWithText
(parent, childElementName, String.valueOf(value));
}
-
8/2/2019 Shopping Framework
44/46
-
8/2/2019 Shopping Framework
45/46
Object Computing, Inc. Java/XML Shopping Cart45
XMLUtil (Contd)
public static String getChildValue(Element element, String childName) {
Node node = element.getFirstChild();
while (node != null) {
if (node instanceof Element &&
node.getNodeName().equals(childName)) {
return node.getFirstChild().getNodeValue();
}
node = node.getNextSibling();
}
return null;
}
-
8/2/2019 Shopping Framework
46/46
Object Computing, Inc. Java/XML Shopping Cart46
XMLUtil (Contd)
public static void outputXML(Document doc) {
outputXML(doc, System.out);
}
public static void outputXML(Document doc, OutputStreamout) {
OutputFormat format = new OutputFormat("xml", "UTF-8", true);
format.setIndent(2);
XMLSerializer serializer = new XMLSerializer(out, format);
try {
serializer.serialize(doc);
} catch (IOException e) {
System.err.println(e);
}
}
}