Академический Документы
Профессиональный Документы
Культура Документы
Copyright
Copyright 2005 Compuware Corporation. All rights reserved.
The software described in this manual is provided by Compuware Corporation under a license agreement. The software may be
used only in accordance with the terms of the agreement. This document or portions of it may only be transmitted or copied in
units of unmodified complete pages or larger unmodified document segments. This copyright notice must be clearly visible at the
beginning of each copy.
APRIL 2005
TABLE of CONTENTS
TABLE OF CONTENTS.........................................................................................................................2
1. INTRODUCTION ............................................................................................................................3
7. REFERENCES..............................................................................................................................40
1. Introduction
OptimalJ provides pattern technology and includes pre-defined patterns that generate new
artifacts from existing artifacts. Patterns are used to synchronize the generated artifacts
when the source has been updated, while preserving changes applied by the user to the
target. Examples of these patterns:
Technology Patterns generate components in the Platform Specific Application Models for
each class in the Platform Independent Domain Model
Implementation Patterns translate the artifacts in the Application Model into deployable
application code
This white paper focuses on one particular artifact generated by OptimalJ, the Business Faade.
The purpose of the Business Faade is to eliminate the difficulties that developers would encounter
in connecting the presentation tier with the business logic tier, by shielding the presentation logic
from the inner workings of the business logic. All the communication between the presentation
layer and the business logic layer is fully handled by the Business Faade, thus isolating the
components of the application in terms of functionality.
The Business Faade also promotes a weak coupling between the business logic tier and the
presentation tier and hence developers can vary the presentation components without affecting the
business logic tier. The default JSP web components generated by OptimalJ can be replaced by,
for example, Swing components, to be generated by Swing Implementation patterns or connected
manually with the Business Faade. To provide a general understanding about the use and the
flexibility of the Business Faade, this white paper includes a source code sample based on
JavaServer Faces (JSF) presentation technology.
2.1 Model-View-Controller
OptimalJ generates a Model-View-Controller (MVC) framework for building HTML forms, validating
their values, invoking business logic, and displaying results. The basic idea of MVC is to separate
the application data and business logic (the Model), the presentation of the data (the View), and
the interaction with the data (the Controller). In MVC-based web applications, multiple
presentations (Views) can be provided and easily modified. Changes in the business rules or
physical representation of the data (the Model) can be made without touching any of the user
interface code.
OptimalJ implements an MVC architecture for Apache Struts based applications using several
elements:
The JavaServer Pages (JSPs) and (Struts) formbeans implement the View. JSPs produce the
HTML output while formbeans serve as containers for data entered in HTML forms which can be
accessed by action classes. An action class is part of the Controller part of the MVC triage, and
processes the request. The action class identifies where control should be forwarded (e.g., a JSP,
or another action) to provide the appropriate response.
The Model provides data for the View. In OptimalJ, the Model part of the MVC triage is
implemented by Update Objects. An Update Object is a read/write data structure that is passed as
a parameter, and represents the business data.
The Update Objects are created and managed by the Business Faade. The Business Faade
solves the communication issues between the Web and the EJB tiers, and implements good
practices in the following areas:
The Business Faade is not part of Struts, but is an implementation of the Business Delegate
J2EE Design Pattern in OptimalJ (see also the white paper: Implementing Sun Microsystems
Core J2EE Patterns, which can be downloaded from JavaCentral:
http://javacentral.compuware.com/members/downloads/pdf/OJSunpatterns.pdf)
All actions are accessed via their execute method. The execute method issues various
methods calls to process the information and returns a status to the Controller. In essence, the
action classes offer the following functionality:
Display data:
1. Transfer the data from the Update Object to the formbean
2. Transfer the data from the formbean to the JSP
Submit data:
3. Transfer the data from the JSP to the formbean
4. Transfer the data from the formbean to the Update Object
In the Action classes data is copied to and from the Update Objects in their load/save methods.
Developing an application with OptimalJ starts by defining a Domain Model. In the Domain
Model the functionality and the structure of the application is defined, without implementation-
specific detail. Therefore, the Domain Model is a Platform Independent Model (PIM).
OptimalJs Technology Patterns automatically transform a Domain Model into the Application
Model. Application Models describe functionality in design models, which are independent of
specific code, but are based on a certain technology or application framework, and therefore
are Platform Specific Models (PSM).
Implementation Patterns automatically transform the Application Model into the Code Model. The
MVC implementation at code level is the result of an automated generation from the Application
Model definitions. The next picture gives an overview of the Application Model elements and how
they link to the MVC implementation on code level.
At Application Model level, the following presentation model components (in bold font format)
represent the View:
WebDataschemas
WebDataClass
(code level: Formbean)
WebComponent
(code level: Web Pages)
Web Component: is the presentation model element, which contains web pages and more
(see section about the Controller). Web pages provide entries where you can enter data to
interact with the business logic. Web pages also can display results of business logic
processing. With OptimalJs graphical User Interface Designer developers can design the
presentation and layout of web pages of user-defined web components. The User Interface
Designer is a model-driven editor. For example, the data from the formbean is represented by
a specific widget based on data binding. Because the formbeans are generated from the Web
Data Classes, data binding in the model is based on the attributes of these Web Data
Classes. After code generation the web pages are mapped to JavaServer Pages (JSP).
For more details about the User Interface Designer, see Using OptimalJ contained in the
on-line Help of the product.
Web Data Class: is a data class that is part of a Web Data Schema. A data class represents a
domain class. A data schema is a collection of related data classes that can be treated as a unit.
After code generation Web Data Classes are mapped to formbeans.
Web Data Schema: is a collection of related data classes that can be treated as a unit. It
allows for including all attributes of an associated class into the served data class instead of
just the primary key. It contains an origin data class from which related data classes can be
included byReference or byValue.
At Application Model level, the following model elements (in bold font format) represent the
Controller and the Model of the MVC triage:
WebComponent
Application DataSchema
WebFlows
(code level: Struts- Application DataClass
config) (code level: Update
& Object)
WebActions
(code level: Action
Classes)
OptimalJ Application Model: The Controller part and the Mode part of the MVC triage
Web Flows: contain control sequences between web actions and web pages, describing
user interactions. With Optimals Web Flow Diagram developers can create their own web
flows used to define the navigation through the web pages and web actions. They define web
pages and web actions and then create a web flow using the Web Flow Diagram. After code
generation web flows are mapped to the struts-config.xml file.
For more details about web flows, see Using OptimalJ contained in the on-line Help of the
product.
Web Actions: define a controller task within the MVC paradigm of the presentation model. After
code generation the Web Actions are mapped to action classes. At Application Model level,
OptimalJ offers a navigation mechanism, by which developers can navigate to the generated
action classes for a specific web component.
To decide about the most appropriate place to add code in web actions, developers need to
understand the flow of actions and the tasks these actions perform. While going through the
control sequences as defined by the web flows, developers are exposed to all of the actions,
their functions and the way they are linked together. When testing on JBoss/Tomcat, the
TomcatI/O tab of the Output Window helps developers monitor the flow of actions, as
generated in the web flows of the web components.
Application Data Class: represents the class that is included as a part of an Application Data
Schema. An Application Data Schema is an element of the Common Model that defines the data
view that should be provided by a component using it. The Application Data Class is mapped to
the Update Object after code generation.
The Business Faade model enables the web components to use the data and access the
methods provided by the business logic components.
The Web tier accesses the business logic tier through a BusinessFaadeComponent, which
relates a WebComponent to a business logic component using a
BusinessFaadeServingAttribute.
Note: using serving attributes is not the only mechanism by which you can connect
components. You can explictly model method calls from one component to the other via the
component wizards. The invocation details are saved in the usedComponent and
usedOperation properties of the calling component.
All Web Components contain a WebServingAttribute which has two main properties:
Application Model: The serving attribute of the Web Component and its properties
Type property, which points to the root Application DataClass (Update Object) of an
Application Data Schema.
UsedServingAttribute property which points to the serving attribute of a component in the
Business Logic layer (e.g. an EJB session component).
Application DataClass
(Update Object)
Application Model: connecting the Business Faade to the Web Component by use of the
Business Faades serving attribute
With regard to Domain to Business Faade mapping, a Business Faade component is created for
each Domain class and Domain service. Business Faade components can be visualized in
OptimalJ using either the Explorer window or the Application Component Diagram which shows
how Business Faade components relate to business logic components.
The Business Faade model is generated using the definitions contained in the Business
logic model. It allows the presentation component to use the data and access the methods
provided by the business logic components (EJBs and/or DAOs).
Transaction scope
The Business Faade is the interface between the presentation tier and the business logic tier.
When processing a retrieve request from a client, the Business Faade connects to the business
logic tier where a logic component (session bean or business logic component) creates a Data
Object populated with data attribute values and sends it back to the Business Faade. The Data
Object acts like a Transport object.
If the data requested is already available as an Update Object, no connection to the logic tier is
necessary. To edit Data Objects, Data Objects are converted to Update Objects. An Update Object
is an editable Data Object (representations of the business data) with a fine-grain interface. Update
Objects are created by the Business Faade.
When the client updates and submits data, the updated Update Object is sent back to the
business logic tier that takes care of the actual store in the database. A Business Faade and
corresponding Update Objects/Data Objects are generated for each ApplicationDataSchema
defined in the Common Model.
4.2 Communication media between the web and business logic tier
As a faade to the business logic tier, the Business Faade enhances communication by using a
coarse-grain/fine-grain communication mechanism. The Business Faade uses the coarse-
grain/fine-grain mechanism to limit tier-to-tier communication and therefore improve network traffic
performance. It provides the benefits of each type of communication to the corresponding tier, so
for the web tier a fine-grain communication mechanism is used (Update Objects), and for the
business logic a coarse grain one (Data Objects). In essence, fine-grain access is used for
usability, while coarse-grain communication is used for performance reasons.
The coarse-grain communication between the web and business logic tiers is based on Data
Objects, which are constructed and handed over from one tier to another (received and sent
with one-method invocation). The web tier requests Data Objects from the business logic tier
to be transferred in one go (coarse-grain). Not element for element, that is, e.g., first the
name, then the address and so on. A Data Object is a read-only data structure that contains a
set of data. On the web tier, the Business Faade receives the Data Objects and transforms
the Data Objects into Update Objects.
Update Objects contain a copy of the properties of the Data Object. The Update Object is a
read/write data structure that represents the Data Object in the web tier. They also have a get
and set method for each of those properties to enable the fine-grain communication mechanism
used in the web tier between the client (JSP) and the Update Object. Attribute values are
maintained with set and get methods for each data attribute. Fine-grain communication optimizes
connectivity by smartly dealing with updates and only capturing the data that was really updated.
The Business Faade holds a number of collections to maintain control over the state of the
Update Objects. These collections hold references to the Update Objects in a certain data status.
The original collection is the unchanged (retrieved) collection. This is a read-only collection and it is
the basis for all other collections. All other collections are derived or modified collections of the
unchanged collection. In the Business Faade, the unchanged (retrieved) collection holds the
Update Objects (copy of the Data Object).
Conceptually the modified collections are:
Create collection
Delete collection
Update collection
Depending on the type of class the modified collections are applicable. For example, in a
collections of keys, there is usually no update collection, since keys are not updateable by
nature.
Code Model: The Business Faade holds a number of collections to maintain control over the
state of the Update Objects.
The Update Object collects all the changes made on the original data. When the web tier is
ready to make changes to the data persistent, the web tier instructs the Business Faade to
store the data. The Business Faade then queries the changes from all Update Objects, this
includes the update, delete and create collections and sends the Update Objects to the
business logic tier.
The Business Faade queries the changes from all Update Objects, and sends the Update
Objects to the business logic tier.
In a three-tier application, the corresponding entity bean processes the Update Object in the
EJB tier, performing the modifications to the database. In a two-tier application, the
corresponding DAO component processes the Update Object in the business logic tier,
performing the modifications to the database.
Business Faade components cannot invoke one another. The operations they provide are only
available to presentation components, but a Business Faade is capable of delegating the
execution of an operation to methods in any business logic component. Additionally, these
components maintain state between method invocations by storing this state information in their
attributes.
Operations extend the behavior of Business Faade components. You can add operations to
Business Faade components to implement, for example:
The Business Faade holds the information regarding the state of data for a user session. The
Business Faade is responsible for keeping track of which Update Objects have been created,
updated, deleted or have not been used. In order to do the data state management, the Business
Faade implements collections to group the Update Object that belong to a certain state. The
Business Faade is responsible for propagating the appropriate information to the business logic
tier.
The code for the Business Faade is generated based on a singular Application Data Schema. A
data schema describes the origin data class it works with, and the associated classes. This
perspective of the involved classes enables the scope of a transaction.
Session scopea Business Faade is retrieved the first time when requested and stored
in the HttpSession object. The user who keeps a session to the Web application can
make use of this Business Faade during the session.
Application scopea Business Faade is generated when deploying the Web application
and stored in the ServletContext object. Every session that needs access to a
business component using this Business Faade gets access to the Business Faade
stored in ServletContext.
Note: To create a WebScopedContext select the presentation ModelPackage In the
Explorer[Application Model] window. From the pop-up menu, choose New Child >
WebScopedContext, a wizard guides you through the creation process.
To illustrate the communication between the web and Business Faade components, let's have a
closer look on how CRUD (Create-Read-Update-Delete) actions on data classes are executed.
The examples below assume a web tier, based on the Struts framework. Before calling a method,
a reference to a BusinessFacade needs to be obtained. The examples below assume that there is
a data schema called ProjectSvc, with Project as root data class. The method to obtain a business
faade instance is:
ProjectSvcProjectBusinessFacade bfProject =
obtainInstanceProjectSvcBusinessFacade(session);
Create
The Business Faade component contains a createDataClass method, where DataClass is
the root dataclass in a Web dataschema. This method creates an UpdateObject and puts it in the
create collection. In a Struts-based web environment, the UpdateAction calls this method:
UpdateAction class:
/** doCreate method **/
projectUpdateObject = bfProject.createProject(projectKey);
saveProjectBean (formBean, projectUpdateObject, request);
BusinessFacade
/** createProject method **/
updateObject = new ProjectUpdateObject () ;
getCreateCollection().add(updateObject);
Read
The retrieve method on the BusinessFacade takes care of retrieving data. It returns a collection
holding the ProjectUpdateObjects. There are more than one retrieve methods available, depending
on the type of query you want to perform.
BrowseAction class
/** doRetrieve method **/
projectCollection = bfProject.retrieve();
BusinessFacade
/** retrieve() method **/
setUnchangedCollection(collection);
setInitialCollection(collection);
return getUnchangedCollection();
Update
After retrieving data, you select one for updating. The BusinessFacade contains a method
retrieveForUpdate that adds an UpdateObject to an Update Collection. The UpdateObject will only
be retrieved from DBMS if necessary.
The retrieveForUpdate method can be called from a SelectAction class.
SelectAction class
/** doRetrieve method **/
projectUpdateObject = bfProject.retrieveForUpdate(projectKey);
loadProjectBean(formBean, projectUpdateObject, request);
Business Faade
/** retrieveForUpdate method **/
getUpdateCollection().add(updateObject);
return updateObject;
Delete
The Business Faade component contains a deleteDataClass method, where DataClass is
the root dataclass in a Web dataschema. This method moves an UpdateObject that is already
retrieved into the Delete Collection. If the update object resides in create or update collections, it
will be removed from there.
UpdateAction class
/** doDelete method **/
bfProject.deleteProject(projectUpdateObject);
Business Faade
/** deleteProject method **/
getDeleteCollection().add(updateObject);
OptimalJ generates by default a MVC application architecture based on Apache Struts. The Model
part of the MVC triage consists of the Business Faade. The OptimalJ Business Faade hides the
business layer from the presentation layer, and handles maintaining the state of data sent between
the presentation and business tiers. The transparency of the OptimalJ Business Faade makes
this a multi-purpose component, which implies that it can be used with basically any presentation
technology (JSP, Swing, JSF). To illustrate this capability and to further explain how to use the
Business Faade, this chapter will provide a code sample of how to connect the Business Faade
against a JavaServer Faces (JSF) client.
Like Apache Struts, JavaServer Faces (JSF) can be viewed as a Model-View-Controller (MVC).
JSF implementations support JavaServer Pages (JSP) as a presentation layer technology, with
JSF components represented by JSP custom action elements (custom tags). JSF focuses on the
user interface, providing an event-driven component model. In JSF the presentation components
(JSPs) declare what events they can fire, such as value changed, menu item selected, and
button clicked. Event handlers (representing the Controller) handle events. A separate renderer
class (representing the View) renders each JSF presentation component. In this sample, the
Model is represented by the Update Object.
The Business Faade runs on the client tier and can be used by any presentation tier. This case
study explains how to integrate a JavaServer Faces (JSF) client application with a Business
Faade and back-end functionality that is generated with OptimalJ.
Prerequisite: To understand this sample we assume the reader had basic OptimalJ
hands-on experience, and a good conceptual knowledge about JSF.
The JSF-based client application consists of two pages: A Project List page and a Project
Details page. The Project List page shows all available projects and the Project Details page
allows the user to change the project data.
o name: projects
o package: mycomp.projects
e) Build project
i) Enter some test data and ensure that the generated application works correctly
To create the JSF client application, virtually any IDE can be used for that purpose. In this
sample we choose NetBeans 3.6, which includes Tomcat 5. NetBeans 3.6 can be downloaded
for free from: http://www.netbeans.info/downloads/download.php?a=arch&p=1
b) Mount a folder
1. Choose File >New to open the New wizard. The Choose Template
page appears.
2. Expand JSPs & Servlets, select Web Module, and click Next.
d) Copy all jar files that are needed for JSF (use any JSF example) to the WEB-INF/lib.
These files are:
commons-beanutils.jar
commons-collections.jar
commons-digester.jar
commons-logging.jar
e) Copy the jar files from the OptimalJ project into WEB-INF/lib .
f) Copy the OptimalJ jar files for Alturalib into WEB-INF/lib of Netbeans
j) To prevent conflicts change the port number in OptimalJ for the HTTP Server from 8084
(or 8082) into something else, e.g. 8089.
k) Add the JSF Servlet to the web deployment descriptor web.xml (located in the
NetBeans WEB-INF directory)
Be sure to add it as the first entry in the web-app tag. It might be a good idea to
select validate xml when you have finished. The full web.xml should look like:
Listing WEB-INF/web.xml:
<web-app xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee
http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"
version="2.4">
<context-param>
<param-name>javax.faces.STATE_SAVING_METHOD</param-name>
<param-value>client</param-value>
</context-param>
<servlet-mapping>
<servlet-name>FacesServlet</servlet-name>
<url-pattern>*.faces</url-pattern>
</servlet-mapping>
<session-config>
<session-timeout>
30
</session-timeout>
</session-config>
<welcome-file-list>
<welcome-file>
index.html
</welcome-file>
</welcome-file-list>
</web-app>
From here on we illustrate how to create the JSF client application in NetBeans 3.6. Two
pages and a Handler will be created:
Project Handler
At the end of this step, the folders and file structure in NetBeans should look like in the
screenshot below. Note that the package structure for the Java classes has been created
manually in NetBeans (new package mycomp.projects.application.web).
Create a simple HTML page (index.html) to redirect to the Projects application, in this case
the Project List page.
Listing index.html:
<html>
<meta http-equiv="Refresh" content="0; URL=projectList.faces" />
<body>
<p>Wait a moment, please .....</p>
</body>
</html>
The Project List page displays a list of projects and allow the user to select a project for update.
This page displays a list of projects using a JSF DataTable. The DataTable uses the
projectsModel model, which is implemented in the ProjectHandler. The first column of the
projects table is a commandLink that will bring the user to the details page.
Listing: projectList.jsp
<h:form>
<h:dataTable value="#{projectHandler.projectsModel}" var="project">
<h:column>
<f:facet name="header">
<h:outputText value="Name"/>
</f:facet>
<h:commandLink action="#{projectHandler.selectProject}"
immediate="true">
<h:outputText value="#{project.name}" />
</h:commandLink>
</h:column>
<h:column>
<f:facet name="header">
<h:outputText value="Start Date"/>
</f:facet>
<h:outputText value="#{project.startdate}" />
</h:column>
<h:column>
<f:facet name="header">
<h:outputText value="End Date"/>
</f:facet>
<h:outputText value="#{project.enddate}" />
</h:column>
<h:column>
<f:facet name="header">
<h:outputText value="Budget"/>
</f:facet>
<h:outputText value="#{project.budget}" />
</h:column>
<h:column>
<f:facet name="header">
<h:outputText value="Status"/>
</f:facet>
</h:dataTable>
</h:form>
</f:view>
</body>
</html>
The ProjectHandler is responsible for the user interaction with the Projects.
It contains the following properties:
Listing ProjectHandler.java
package mycomp.projects.application.web;
import java.util.Iterator;
import java.util.List;
5.2.3.3.1 Properties that are shared between the List page and the Details page.
The Faade property contains a reference to the ProjectSvcProjectBusinessFaade. The
currentProject that the user selected from the list page. is referred to by the
ProjectUpdateObject.
// PROPERTY: facade
private ProjectSvcProjectBusinessFacade facade;
public ProjectSvcProjectBusinessFacade getFacade() {
if (this.facade == null) {
this.facade = new ProjectSvcProjectBusinessFacade();
}
return this.facade;
}
public void setFacade(ProjectSvcProjectBusinessFacade facade) {
this.facade = facade;
}
// PROPERTY: currentProject
// Used to indicate the current Project to the ProjectDetail
page.
private ProjectUpdateObject currentProject;
public ProjectUpdateObject getCurrentProject() {
return currentProject;
}
public void setCurrentProject(ProjectUpdateObject currentProject)
{
this.currentProject = currentProject;
}
The selectProjects method handles the event when the user has clicked on the link in
the list page. It obtains the ProjectUpdateObject that corresponds to the selected row in
the DataTable using the selectForUpdate method in the Business Faade.
// PROPERTY: projectsModel
private DataModel projectsModel;
public DataModel getProjectsModel() {
if (projectsModel == null) {
projectsModel = new ListDataModel();
}
projectsModel.setWrappedData(getProjectList());
return projectsModel;
}
// PROPERTY: projectList
private java.util.Collection projectList;
public java.util.Collection getProjectList() {
if (projectList == null) {
this.retrieveProjects();
}
return this.projectList;
}
public void setProjectList(java.util.Collection projectList) {
this.projectList = projectList;
}
/**
* Retrieve all Projects from the Businessfacade
* This method will be indirectly used by the ProjectList page.
*/
public String retrieveProjects() {
try {
if (this.facade == null) {
this.facade = new ProjectSvcProjectBusinessFacade();
}
this.projectList = this.facade.retrieve();
this.projectList = this.facade.getProjectCollection();
} catch
(com.compuware.alturadev.application.AlturaRetrieveException are) {
FacesContext context = getFacesContext();
FacesMessage msg = new
FacesMessage(FacesMessage.SEVERITY_ERROR,
are.getMessage(),
are.detail.toString());
context.addMessage(null, msg);
}
TECHNICAL WHITE PAPER COMPUWARE CORPORATION PAGE 32
APRIL 2005
return "success";
}
/**
* Select the current Project for update in the Businessfacade.
* This method will be used by the ProjectList page.
*/
public String selectProject() {
FacesContext facesContext = getFacesContext();
ProjectUpdateObject project =
(ProjectUpdateObject)this.projectsModel.getRowData();
try {
project =
this.facade.retrieveForUpdate(project.getKey());
this.setCurrentProject(project);
} catch (AlturaRetrieveException are) {
FacesContext context = getFacesContext();
FacesMessage msg = new
FacesMessage(FacesMessage.SEVERITY_ERROR,
are.getMessage(),
are.detail.toString());
context.addMessage(null, msg);
}
return "success";
}
// PROPERTY: projectStatusOptions (read-only)
// Used by the dropdown listbox on the ProjectDetail page.
public List getProjectStatusOptions() {
List projectStatusOptions = new ArrayList();
projectStatusOptions.add(
new SelectItem(ProjectStatus.PLANNED,
ProjectStatus.PLANNED.toString()));
projectStatusOptions.add(
new SelectItem(ProjectStatus.STARTED,
ProjectStatus.STARTED.toString()));
projectStatusOptions.add(
new SelectItem(ProjectStatus.FINISHED,
ProjectStatus.FINISHED.toString()));
return projectStatusOptions;
}
The OK button on the details page is handled by the updateproject action. Because JSF
will have already updated the UpdateObject, we only need to store the results that are in the
Business Faade. This is achieved by invoking the store operation of the Business Faade,
which will pass the UpdateObjects on to the business tier and eventually to the database.
If any errors occur in thta process, we will get an AlturaStoreExceptions exception.
Please note the plural; this is because the exception will contain all detail exceptions that
have occurred. For the individual exceptions we create a message in the JSF context. If an
exception occurred, the details page will be shown again - we return null - and these
messages will be displayed.
/**
* Update the current/chnaged Projects in the BusinessFaade.
* This method will be used by the ProjectDetail page.
*/
public String updateProject() {
try {
this.Faade.store();
} catch (AlturaStoreExceptions ase) {
// handle store exceptions
FacesContext context = getFacesContext();
FacesMessage msg1 = new
FacesMessage(FacesMessage.SEVERITY_ERROR,
ase.getMessage(), ase.getMessage());
context.addMessage(null, msg1);
List ares = ase.exceptions;
for (Iterator it = ase.exceptions.iterator();
it.hasNext();){
AlturaStoreException asex =
(AlturaStoreException)it.next();
FacesMessage msg = new
FacesMessage(FacesMessage.SEVERITY_ERROR,
asex.getMessage(),
asex.detail.toString());
context.addMessage(null, msg);
}
return null;
}
this.setProjectList(null);
this.setCurrentProject(null);
return "updated";
}
Listing faces-config.xml :
<?xml version="1.0"?>
<faces-config>
<managed-bean>
<managed-bean-name>projectFacade</managed-bean-name>
<managed-bean-
class>mycomp.projects.application.business.facade.ProjectSvcProjectBu
sinessFacade</managed-bean-class>
<managed-bean-scope>session</managed-bean-scope>
</managed-bean>
<managed-bean>
<managed-bean-name>projectHandler</managed-bean-name>
<managed-bean-
class>mycomp.projects.application.web.ProjectHandler</managed-bean-
class>
<managed-bean-scope>session</managed-bean-scope>
</managed-bean>
<navigation-rule>
<from-view-id>/projectList.jsp</from-view-id>
<navigation-case>
<from-outcome>success</from-outcome>
<to-view-id>/projectDetails.jsp</to-view-id>
</navigation-case>
</navigation-rule>
<navigation-rule>
<from-view-id>/projectDetails.jsp</from-view-id>
<navigation-case>
<from-outcome>updated</from-outcome>
<to-view-id>/projectList.jsp</to-view-id>
</navigation-case>
</navigation-rule>
<navigation-rule>
<from-view-id>/projectDetails.jsp</from-view-id>
<navigation-case>
<from-outcome>cancel</from-outcome>
<to-view-id>/projectList.jsp</to-view-id>
</navigation-case>
</navigation-rule>
The details page allows the user to change the project data. This page has an entry for each
attribute of a Project. These rows consist of a label, an input field and an error message. The
project's status input is implemented as a radio group, for which the possible values are
obtained from the ProjectHandler's projectStatus property. Please note that the page also has
a global error message, which will be used for messages that stem from store errors. The OK
button will delegate the action to the ProjectHandler's update method. The Cancel button will
navigate back to the list page.
Listing projectDetails.jsp:
<%@page contentType="text/html"%>
<%@page pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsf/html" prefix="h" %>
<%@ taglib uri="http://java.sun.com/jsf/core" prefix="f" %>
<html>
<head>
<title>Project Details</title>
</head>
<body>
<f:view>
<h1>Project Details</h1>
<h:form >
<h:messages showDetail="true" layout="table"/>
<h:panelGrid columns="3" border="1">
<h:panelGroup/>
<h:panelGrid columns="2">
<h:commandButton action="#{projectHandler.updateProject}"
value="OK"/>
</h:panelGrid>
</h:form>
</f:view>
</body>
</html>
A custom converter for the Enumerationtype ProjectStatus is needed, so that JSF can
directly access the Project.status attribute, which is of type ProjectStatus.
Listing: ProjectStatusConverter.java
package mycomp.projects.application.web;
import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import javax.faces.convert.Converter;
import mycomp.projects.application.business.common.ProjectStatus;
<converter>
<converter-id>projectStatus</converter-id>
<converter-
class>mycomp.projects.application.web.ProjectStatusConverter</convert
er-class>
</converter>
TECHNICAL WHITE PAPER COMPUWARE CORPORATION PAGE 37
APRIL 2005
</faces-config>
b) Deploy the JSF client application in NetBeans (Web Module -> execute )
The JSF client application will retrieve all projects data. The end user can select a project,
modify the data and store the modified data in the database. All the back-end functionality is
handled by the Business Faade, which was automatically generated from the Domain Model
and Application Model.
6. Conclusion
In recognition that the businessand not software technologyis the heart and soul of a
company, OptimalJ pioneered the field of driving a working application from a business model
(known as the Domain Model) yet doing it iteratively, with preservation of changes and
freedom from vendor lock-in.
Once the first iteration of the Domain Model is complete, OptimalJ automatically transforms the
Domain Model to the Application Model. To implement a J2EE application, the Application
Model defines what needs to be generated. Although the Domain Model drives the
development process, developers have a number of options at their disposal when refining the
Application Model. Once the Application Model is in place, OptimalJ generates the actual code
to implement the components of the respective models. This automatic generation process
ensures consistency with the Domain Model, saving a great deal of time and reducing the
potential for programming errors.
OptimalJ generates the Presentation tier using the Apache Struts framework based on the
Model-View-Controller (MVC) concept. The MVC concept was designed to help control
change. It separates the interface from business logic and data and offers multiple benefits
over an approach based on JSP only. In OptimalJ, the Model part of the MVC triage is
implemented with the Business Faade. It provides the high-level interface of the business
logic component to the clients. It allows the presentation component to use the data and
access the methods provided by the business logic components (EJBs and/or DAOs).
Since the Business Faade is the split between the presentation and business logic tiers it
enables developers to create a new web front-end on top of existing functionality in the
business logic tier. As a result the same data can be shown in the default HTML-based web
components as well in any other presentation technologies. In this white paper this was
illustrated by means of a JavaServer Faces (JSF) client application.
7. References