You are on page 1of 458

Oracle 10g: Build J2EE

Applications

Volume I • Student Guide

D17247GC11
Edition 1.1
June 2005
D18757
Authors Copyright © 2005, Oracle. All rights reserved.

Lynn Munsinger This documentation contains proprietary information of Oracle Corporation. It is


Sunitha Patel provided under a license agreement containing restrictions on use and disclosure and
Glenn Stokol is also protected by copyright law. Reverse engineering of the software is prohibited.
If this documentation is delivered to a U.S. Government Agency of the Department of
Gary Williams Defense, then it is delivered with Restricted Rights and the following legend is
applicable:

Technical Contributors Restricted Rights Legend


and Reviewers
Use, duplication or disclosure by the Government is subject to restrictions for
Anna Atkinson commercial computer software and shall be deemed to be Restricted Rights software
Scott Brewton under Federal law, as set forth in subparagraph (c)(1)(ii) of DFARS 252.227-7013,
Kenneth Cooper Rights in Technical Data and Computer Software (October 1988).
Craig Hollister This material or any portion of it may not be copied in any form or by any means
Taj-ul Islam without the express prior written permission of Oracle Corporation. Any other copying
Istvan Kiss is a violation of copyright law and may result in civil and/or criminal penalties.
Peter Laseau If this documentation is delivered to a U.S. Government Agency not within the
Glenn Maslen Department of Defense, then it is delivered with “Restricted Rights,” as defined in
Monica Motley-Mosser FAR 52.227-14, Rights in Data-General, including Alternate III (June 1987).
Nagavalli Pataballa The information in this document is subject to change without notice. If you find any
Holger Dindler-Rasmussen problems in the documentation, please report them in writing to Education Products,
Glenn Stokol Oracle Corporation, 500 Oracle Parkway, Box SB-6, Redwood Shores, CA 94065.
Oracle Corporation does not warrant that this document is error-free.
Vasiliy Strelnikov
Venkat Tallapragada All references to Oracle and Oracle products are trademarks or registered trademarks
of Oracle Corporation.

Publisher All other products or company names are used for identification purposes only, and
may be trademarks of their respective owners.
Joseph Fernandez
Contents

Preface

1 Introduction
Course Objectives 1-2
Course Environment 1-4
Course Overview 1-5
About the Course Applications 1-8
Order Entry Schema 1-9
Human Resources (HR) Schema 1-10
HR Application Flow Diagram 1-11
Summary 1-12

2 J2EE Overview
Objectives 2-2
Java 2, Enterprise Edition Platform 2-3
J2EE Platform 2-4
Benefits of the J2EE Platform 2-5
J2EE Components 2-7
J2EE 1.3 Components 2-8
J2EE Architecture 2-9
Client-Tier Components 2-10
J2EE Web-Tier Components 2-11
What Is a Servlet? 2-13
What Is a JavaServer Page (JSP)? 2-14
Web-Tier Components: Summary 2-15
Business-Tier Components 2-16
Enterprise JavaBeans (EJB) 2-17
J2EE Communication APIs 2-18
J2EE Server 2-19
Oracle Application Server 10g Containers for J2EE (OC4J) 2-21
J2EE Applications 2-22
Packaging J2EE Application Components 2-23
JARs 2-24
WARs 2-25
EJB JARs 2-26
EARs 2-27
EAR File Structure for a J2EE Application: Example 2-28
OC4J Architecture 2-29
OC4J Server Configuration Files 2-30
Relation of Configuration Files 2-31

iii
Data Sources 2-32
Application Logging 2-33
J2EE Application Deployment to Oracle Application Server 10g 2-34
Oracle Enterprise Manager 2-35
JDeveloper and J2EE 2-36
Oracle JDeveloper 10g Environment 2-37
Oracle JDeveloper 10g Visual Design Tools 2-38
Summary 2-39
Practice 2-1: Overview 2-40

3 Designing J2EE Applications


Objectives 3-2
Realizing J2EE Benefits 3-3
J2EE Issues 3-4
J2EE Design Patterns 3-5
Implementing Design Patterns by Using MVC 3-6
The Model 3-7
The View 3-8
The Controller 3-9
MVC in Oracle Application Server 10g Containers for J2EE 3-10
Designing J2EE Applications 3-11
Flow Diagram: Example 3-12
Summary 3-13
Practice 3-1: Overview 3-14

4 Creating the Web Tier: Servlets


Objectives 4-2
Overview 4-3
About Java Servlets 4-4
Principal Features of Servlets 4-5
Life Cycle of Servlets 4-6
HTTP Servlets 4-7
Inside an HTTP Servlet 4-8
Servlet: Example 4-9
The doGet() Method 4-10
The doPost() Method 4-11
The HttpServletRequest Object 4-12
The HttpServletResponse Object 4-13
Methods for Invoking Servlets 4-14
Your First Servlet 4-15
Handling Input: The Form 4-16

iv
Handling Input: The Servlet 4-17
Initialization and Destruction 4-18
Error Handling 4-19
Debugging a Servlet 4-20
SingleThreadModel 4-21
JDeveloper Environment 4-23
Servlet Mapping 4-24
Servlet Mapping in JDeveloper 4-25
Invoking a Servlet 4-26
Specifying J2EE Web Module Settings 4-27
Creating a Connection to Oracle Application Server 10g 4-28
Deploying to OC4J 4-29
Summary 4-30
Practices 4-1, 4-2, and 4-3: Overview 4-31

5 Accessing the Database with Servlets


Objectives 5-2
Review of JDBC 5-3
Querying in JDBC 5-4
JDBC and Servlets 5-5
Synchronizing Shared Resources 5-6
Transaction Handling 5-7
Connection Pooling 5-9
Data Sources 5-10
Data Source Definition 5-11
data-sources.xml: Example 5-12
Using Data Sources 5-13
Summary 5-14
Practice 5-1: Overview 5-15

6 Using Advanced Techniques in Servlets


Objectives 6-2
Overview 6-3
HTTP Headers 6-4
Request Headers 6-5
Sending a Response 6-6
Response Headers 6-7
Setting Status Codes 6-8
Example 6-9
Sending Multimedia Content 6-10

v
Cookies 6-12
Setting Cookies 6-13
Retrieving Cookies 6-14
About State Preservation 6-15
State Preservation: Example 6-16
ServletContext 6-17
RequestDispatcher 6-18
RequestDispatcher: Example 6-19
Servlet Filters 6-20
Using Filters 6-21
doFilter() Method 6-22
Using Filters 6-23
Configuring Filters 6-24
Application Lifecycle Events 6-25
ServletContext Events 6-26
HttpSession Events 6-27
Example of an Event Listener 6-28
Error Handling 6-29
Summary 6-30
Practices 6-1 and 6-2: Overview 6-31

7 Maintaining State in J2EE Applications


Objectives 7-2
Overview 7-3
Session Basics 7-4
Threading 7-6
URL Rewriting 7-7
HttpSession 7-8
Session Objects 7-9
Session-Based Page Counter 7-10
Session Life Cycle 7-11
Session Tracking in OC4J 7-12
Sessions and Events 7-13
Creating Distributable Applications 7-17
Summary 7-18
Practice 7-1: Overview 7-19

8 Creating the Web Tier: JavaServer Pages


Objectives 8-2
JavaServer Pages 8-3
Comparing Servlets and JSPs 8-4

vi
Invoking JSPs 8-5
The Date JSP 8-6
The Date Servlet 8-7
Automated JSP Features 8-8
JSP Life Cycle 8-9
Basic JSP Elements 8-10
Declarations 8-11
Expressions 8-12
Scriptlets 8-13
Implicit Objects 8-14
Example 8-16
Directives 8-18
include: Example 8-19
page Directive 8-20
JSP and JavaBeans 8-22
Using JavaBeans with JSP 8-23
scope Attribute of <jsp:useBean> Tag 8-25
Accessing and Setting Bean Property 8-26
JSP XML Document 8-28
Traditional Syntax Versus XML Syntax 8-29
JDeveloper and JSPs 8-31
Creating JSPs Visually 8-32
JSP Tag Insight 8-33
Summary 8-34
Practices 8-1, 8-2, and 8-3: Overview 8-35

9 Modularizing JavaServer Pages Development with Tags


Objectives 9-2
Custom Tags 9-3
Custom Tag Library Components 9-4
Tag Handler: Example 9-5
Tag Library Descriptors 9-6
Using a Custom Tag 9-7
Tags with Attributes 9-8
Creating a Custom Tag in JDeveloper 9-9
Tag Libraries in JDeveloper 9-10
Registering Tag Libraries 9-11
Using Tag Insight 9-14
JSP Standard Tag Library (JSTL) 9-15
Core Tag Library 9-16
Utilizing Core Tags 9-18

vii
Expression Language 9-19
Using Iteration Tags 9-20
Using the URL Tags 9-21
XML Tag Library 9-23
SQL Tag Library 9-24
Accessing a Database with SQL Tags 9-25
Querying Using SQL Tags 9-26
Inserting, Updating, and Deleting Data 9-27
Formatting Tags 9-28
Internationalization Concepts 9-29
Internationalizing Strings 9-30
Formatting Numbers and Dates 9-31
Transforming XML Documents 9-34
JSTL in JDeveloper 9-35
Summary 9-36
Practice 9-1: Overview 9-37

10 Communicating in J2EE
Objectives 10-2
Overview of RMI 10-3
Role of RMI in J2EE 10-4
Communication in a J2EE Environment 10-5
How Clients Locate a Distributed Component 10-7
Java Naming and Directory Interface (JNDI) 10-8
J2EE Container and JNDI Interface 10-9
Naming Service 10-10
JNDI Terminology 10-11
Main JNDI Class and Interface
Accessing an Object in JNDI Namespace 10-13
Getting the JNDI InitialContext 10-14
Initial Context Factories 10-16
lookup() Method 10-17
Obtaining a Reference to a Local Resource 10-18
Obtaining a Reference to a Remote Resource 10-19
Setting JNDI Environment Properties 10-20
Using RMI over HTTP Tunneling 10-24
Using Environment References with JNDI 10-25
Configuring Environment Variables 10-26
Specifying an EJB Reference 10-28
Configuring EJB References 10-29

viii
Configuring Data Source References 10-31
Summary 10-33
Practice 10-1: Overview 10-34

11 Creating the Business Tier: Enterprise JavaBeans


Objectives 11-2
Enterprise JavaBeans (EJB) 11-3
When to Use EJBs 11-4
Types of EJBs 11-5
Session Beans 11-7
Entity Beans 11-9
Message-Driven Beans 11-10
EJB Architecture 11-11
EJB Server 11-12
EJB Container 11-13
Services Provided by the EJB Container 11-14
EJB Client 11-16
EJB Interfaces and Classes 11-17
Remote Interface and Remote Object 11-18
Home Interface and Home Object 11-19
Local Interface and Local Home Interface 11-20
EJB Bean Class 11-21
The EJB Deployment Process 11-22
ejb-jar.xml File 11-23
orion-ejb-jar.xml File 11-24
Creating an EJB in JDeveloper 11-25
Using the EJB Wizard 11-26
Adding Methods to the Bean 11-28
Deploying to Oracle Application Server 10g from JDeveloper 11-29
Summary 11-30
Practice 11-1: Overview 11-31

12 Implementing Business Tasks with Session EJBs


Objectives 12-2
Session Beans 12-3
javax.ejb.SessionBean Interface 12-5
Types of Session Beans 12-7
When to Use Session Beans 12-9
Life Cycle of a Stateless Session Bean 12-11
Home Interface for Stateless Session Beans 12-12
Remote Interface for Stateless Session Beans 12-14

ix
The Session Bean Class 12-15
The Session Bean Class: Business Methods 12-17
Bean Class for the Stateless Session Bean 12-18
Deployment Descriptor 12-19
Client Application 12-20
Client Application for Stateless Session Beans 12-21
Life Cycle of a Stateful Session Bean 12-25
Home Interface for Stateful Session Bean 12-26
Client Application for Stateful Session Bean 12-27
Summary 12-28
Practices 12-1 and 12-2: Overview 12-29

13 Managing Persistent Data in the Business Tier


Objectives 13-2
Entity Beans 13-3
Representing Data in Entity Beans 13-5
When to Use Entity Beans 13-6
Callback Methods to Load and Store Data 13-7
Session Beans Versus Entity Beans 13-9
Types of Entity Beans 13-11
BMP Beans Versus CMP Beans 13-12
Components of an Entity Bean 13-14
Creating, Removing, Finding, and Selecting Entity Beans 13-15
Home Interface of an Entity Bean 13-17
Creating a Bean Instance 13-18
Finding an Entity Bean Instance 13-20
Removing an Entity Bean 13-22
Home Methods of Entity Beans 13-23
Component Interfaces of an Entity Bean 13-24
Primary Key Class of an Entity Bean 13-25
Bean Class of an Entity Bean 13-26
javax.ejb.EntityBean Interface 13-28
Life Cycle of an Entity Bean 13-30
Deployment Descriptor 13-32
Summary 13-35
Practice 13-1: Overview 13-36

14 Achieving State Management in the Business Tier


Objectives 14-2
Features of BMP Entity Beans 14-3
Developing a BMP Entity Bean 14-4

x
Features of CMP Entity Beans 14-5
Implementing Methods in CMP Beans and BMP Beans 14-7
Developing a CMP Entity Bean 14-9
CMP Bean: Example 14-10
Bean Class of a CMP EJB: CMP Fields 14-11
Remote Interface: Departments 14-12
Home Interface: DepartmentsHome 14-13
Bean Class: DepartmentsBean 14-14
Deployment Descriptor ejb-jar.xml 14-17
Mapping CMP Fields to Database Table Columns 14-21
Default Mapping of CMP Fields to Database Table Columns 14-22
Explicit Mapping of CMP Fields to Database Table Columns 14-23
Client for Departments Bean 14-25
Summary 14-28
Practice 14-1: Overview

15 Container-Managed Relationships (CMRs)


Objectives 15-2
Relationships 15-3
Implementing Relationships 15-4
Cardinality and Direction of Relationships 15-5
One-to-One Relationships 15-7
One-to-Many Relationships 15-8
Many-to-Many Relationships 15-9
Oracle TopLink 15-10
TopLink: Integration of J2EE Applications with Data Sources at Run Time 15-11
TopLink: Integrated with Oracle JDeveloper 10g 15-12
Implementing Relationships 15-13
Defining Abstract Accessor Methods 15-14
Accessor Methods in 1:1 Relationships 15-15
Accessor Methods in 1:M Relationships 15-16
Checking Relationship Mappings in JDeveloper 15-17
Accessor Methods in M:N Relationships 15-18
Implementing a Relationship in the Deployment Descriptor 15-19
Implementing 1:1 Relationships 15-21
Implementing 1:M Relationships 15-23
Implementing M:N Relationships 15-25
Mapping Relationship Fields to Database 15-27
Default Mapping of Relationship Fields 15-28
Explicit Mapping of Relationship Fields 15-30

xi
Using JDeveloper to Create CMR Beans 15-31
Summary 15-32
Practice 15: Overview

16 Developing Message-Driven Beans


Objectives 16-2
Overview of Messaging Systems 16-3
Types of Message Consumption 16-4
Java Message Service (JMS) 16-6
JMS Application Architecture 16-7
Point-to-Point Model 16-8
Publish-and-Subscribe Model 16-9
Using JMS Interfaces 16-10
JMS Message Structure 16-12
Sending a Message to a Queue 16-13
Receiving Messages 16-15
Asynchronous Message Delivery 16-16
Message-Driven Beans 16-17
MDB Architecture 16-18
Associating JMS Resources with an MDB 16-19
State Diagram of an MDB 16-20
Developing MDBs 16-22
Interfaces to Be Implemented for MDBs 16-23
Implementing an MDB Class 16-24
Receiving Messages in an MDB Class 16-25
Creating the Deployment Descriptor 16-26
ejb-jar.xml: Example 16-28
Mapping in OC4J-Specific Deployment Descriptor 16-29
orion-ejb-jar.xml: Example 16-30
Creating an MDB with JDeveloper 16-31
Testing the MDB 16-34
Summary 16-35
Practice 16-1: Overview 16-36

17 Integrating J2EE Components


Objectives 17-2
Overview 17-3
Creating Remote Clients for EJBs 17-4
Importing the EJB Home Interface 17-5
Create a Reference to the EJB 17-6

xii
Passing Arguments to the EJB Method 17-7
Creating an EJB Reference 17-8
Creating Local Clients for EJBs 17-9
ejb-local-ref Element 17-10
EJB Tags 17-11
useHome Tag 17-12
useBean Tag 17-13
createBean Tag 17-14
iterate Tag 17-15
Using the EJB Tags 17-16
Deploying an Application: Web Tier 17-17
Deploying an Application: EJB Tier 17-18
Deploying an Application: EAR File 17-19
Deploying from Oracle Enterprise Manager 17-20
Summary 17-21
Practice 17-1 and 17-2: Overview 17-22

18 Distributing Modular Applications: Introduction to Web Services


Objectives 18-2
What Is a Web Service? 18-3
Web Service 18-4
Service-Oriented Architecture 18-6
Web Services Constituents 18-7
Benefits of Web Services 18-9
Web Services Model 18-11
RPC-Style Web Services 18-12
Document-Style Web Services 18-13
Oracle Support for Web Services 18-14
SOAP: XML Messaging for Web Services 18-15
Communication with SOAP 18-16
SOAP Messages 18-17
Web Services Description Language (WSDL) 18-19
WSDL 18-20
UDDI Registry 18-22
How UDDI Is Used 18-24
Searching for a Web Service by Using UDDI 18-25
UDDI Specification 18-26
tModel 18-27
UDDI Support in Oracle JDeveloper 10g 18-31
UDDI Browsing with Oracle JDeveloper 10g 18-32
UDDI Publishing and Browsing with Oracle Enterprise Manager 18-33

xiii
Utilizing External Web Services from JDeveloper 18-34
Summary 18-35
Practice 18-1: Overview 18-36

19 Distributing Modular Applications: Developing Web Services


Objectives 19-2
Oracle Application Server 10g Web Services 19-3
Developing a Web Service with a Stateless Java Class 19-4
Defining an Interface 19-5
Defining a Stateless Java Class 19-7
Creating the Web Service 19-10
Creating the Client Application 19-11
Deploying the Web Service 19-13
Testing the Web Service 19-14
Web Service Home Page 19-15
Testing the Deployed Web Service with Home Page 19-16
Testing the sayHello Operation 19-17
Serializing and Encoding Parameters and Results 19-19
Developing a Stored Procedure Web Service 19-20
Generating Wrapper Classes Using JPublisher 19-21
Exposing a Function as a Web Service by Using Oracle JDeveloper 10g 19-22
Publishing the Package as a Web Service 19-23
JMS Web Services 19-24
Summary 19-26
Practice 19-1: Overview 19-27

20 Implementing Security in J2EE Applications


Objectives 20-2
Goals of J2EE Security Architecture 20-3
Overview of J2EE Security Architecture 20-4
Java Authentication and Authorization Service (JAAS) 20-5
Authorization of a Client 20-8
JAAS Provider Types in OC4J 20-9
Configuring Security 20-10
Defining the Users, Groups, and Roles 20-11
Managing Users and Groups with the JAZN Admintool 20-13
Defining the Logical Roles 20-15
Defining and Using Logical Roles in Web Applications (web.xml) 20-16
Defining and Using Logical Roles in EJBs (ejb-jar.xml) 20-18
Mapping Logical Roles to Users and Groups 20-19
Programmatic Access to a Caller’s Security Context 20-20

xiv
Client Authentication 20-21
EJB Client Authentication with the jndi.properties file 20-22
EJB Client Authentication with a Hashtable 20-23
Setting Access Control with JDeveloper 20-24
Creating Web Application Security Roles 20-25
Web Application Login Authentication 20-26
Web Application Authorization 20-27
Creating EJB Security Roles 20-28
Setting Method Permissions 20-29
Method Access in EJB Deployment Descriptors 20-30
Creating a Mapping for the Logical Roles 20-31
Mapping JAZN Identities to a Logical Role 20-32
Mapping Results in orion-ejb-jar.xml 20-34
Accessing the EJB with New Permissions 20-35
Summary 20-36
Practice 20-1: Overview 20-37

21 Oracle Application Server 10g Transaction Support


Objectives 21-2
What Is a Transaction? 21-3
Enterprise JavaBeans (EJB) Support for Transactions 21-4
EJB Transaction Model 21-5
Demarcating Transactions 21-6
Container-Managed Transactions 21-7
CMT: Transaction Attributes 21-8
Transaction Attribute: NotSupported 21-10
Transaction Attribute: Required 21-11
Transaction Attribute: Supports 21-12
Transaction Attribute: RequiresNew 21-13
Transaction Attribute: Mandatory 21-14
Transaction Attribute: Never 21-15
CMT: The setRollbackOnly() Method 21-16
JDeveloper: Setting Transaction Attributes 21-17
Java Transaction API (JTA) 21-19
JTA: The UserTransaction Interface 21-20
Bean-Managed Transactions Demarcation 21-21
BMT Demarcation: Process 21-22
Using UserTransaction Support in EJBs 21-23
Client-Demarcated Transactions Using UserTransaction 21-24
BMT Demarcation: Restrictions 21-25
Local and Global Transactions 21-26

xv
Single-Phase Commit 21-27
Data Source Revisited 21-28
Default data-sources.xml 21-29
Emulated Versus Nonemulated Data Sources 21-30
Retrieve Connection to Data Source 21-31
Global Transaction Resource Request Flow 21-33
Resource Request Flow 21-34
Enlisting Database Resources 21-36
Summary 21-38
Practice 21-1: Overview 21-39

Appendix A: Practice Solutions

Appendix B: Schema Descriptions

Appendix C: Oracle JDeveloper 10g - Quick Reference

Appendix D: BMP Entity EJBs J2EE Connector Architecture


BMP Bean: Example D-2
Remote Interface: JobsBMP D-3
Home Interface: JobsBMPHome D-4
Primary Key Class: JobsBMPPK D-6
User-Defined Exception: JobSalException D-7
Bean Class: JobsBMPBean D-8
create() and ejbCreate() D-10
Bean Class: JobsBMPBean D-11
Deployment Descriptor D-20
Creating Data Source data-sources.xml D-22
Client Class: JobsBMPClient D-24
Overview of J2EE Connector Architecture D-26
OC4J J2EE Connector Architecture D-27
What Is a Resource Adapter? D-28
Resource Adapter Deployment Descriptors D-29
Deploying Stand-Alone Resource Adapters D-30
Deploying Embedded Resource Adapters D-31
Common Client Interface (CCI) API D-32

xvi
Preface
Preface - 2
Profile

Before You Begin This Course


Before you begin this course, you should have the following qualifications:
• Working experience with JDBC
• Familiarity with Oracle JDeveloper 10g
Prerequisites
• Oracle10g: Java Programming (D17249GC10)
• Oracle9i: SQL Basics for Developers (D16565GC10) or equivalent knowledge of basic SQL

How This Course Is Organized


Oracle 10g: Build J2EE Applications is an instructor-led course featuring lectures and hands-on
exercises. Online demonstrations and written practice sessions reinforce the concepts and skills
introduced.

Preface - 3
Typographic Conventions

Typographic Conventions in Text

Convention Element Example


Bold Emphasized words and phrases To navigate within this application, do
in Web content only not click the Back and Forward buttons.

Bold italic Glossary terms (if there is a The algorithm inserts the new key.
glossary)

Brackets Key names Press [Enter].

Caps and Buttons, Click the Executable button.


lowercase check boxes, Select the Registration Required check
triggers, box.
windows
Assign a When-Validate-Item trigger.
Open the Master Schedule window.

Carets Menu paths Select File > Save.

Commas Key sequences Press and release these keys one at a


time:
[Alt], [F], [D]

Preface - 4
Typographic Conventions (continued)

Typographic Conventions in Text (continued)

Convention Object or Term Example


Courier New, Code output, Code output: debug.seti (‘I’,300);
case sensitive SQL and PL/SQL
SQL code elements: Use the SELECT command to view
code elements, Java
information stored in the last_name column of the emp
code elements,
table.
directory names,
filenames, Java code elements: Java programming involves the
passwords, String and StringBuffer classes.
pathnames, URLs, Directory names: bin (DOS), $FMHOME (UNIX)
user input,
usernames Filenames: Locate the init.ora file.
Passwords: Use tiger as your password.
Pathnames: Open c:\my_docs\projects.
URLs: Go to http://www.oracle.com.
User input: Enter 300.
Usernames: Log on as scott.
Initial cap Graphics labels Customer address (but Oracle Payables)
(unless the term is a
proper noun)
Italic Emphasized words Do not save changes to the database.
and phrases in print For further information, see Oracle7 Server SQL
publications, titles of Language Reference Manual.
books and courses,
variables Enter user_id@us.oracle.com, where user_id is
the name of the user.
Plus signs Key combinations Press and hold these keys simultaneously:
[Control] + [Alt] + [Delete]

Quotation Lesson and chapter This subject is covered in Unit II, Lesson 3, “Working with
marks titles in cross Objects.”
references, interface
elements with long Select the “Include a reusable module component” and
names that have only click Finish.
initial caps
Use the “WHERE clause of query” property.

Preface - 5
Preface - 6
Introduction

Copyright © 2005, Oracle. All rights reserved.


Course Objectives

After completing this course, you should be able to do


the following:
• Identify the components and architecture of
Java 2, Enterprise Edition (J2EE), based on the
needs of specific applications
• Describe the Model View Controller (MVC)
architecture and create development plans for
J2EE applications
• Build a Web-based database application by using
J2EE components: servlets, JavaServer Pages
(JSP), and Enterprise JavaBeans (EJB)

Copyright © 2005, Oracle. All rights reserved.

Course Objectives
Many businesses rely on the Internet and Web applications for their daily business. Oracle
provides several tools that you can use to easily develop and deploy these applications. The
purpose of this course is to teach you how to develop applications by using the J2EE
components. These components include servlets, JSP, and EJB. Additionally, you should be
able to create applications that adhere to the MVC architecture, which provides easily
maintainable components.

Oracle 10g: Build J2EE Applications 1-2


Course Objectives

• Test J2EE components by using Web and Java


clients
• Provide versatile access to applications through
Web services, and use a published Web service in
an application
• Deploy J2EE applications to Oracle Application
Server 10g
• Manage transactions in EJB
• Implement J2EE security in applications

Copyright © 2005, Oracle. All rights reserved.

Course Objectives (continued)


Additionally, you should be able to describe how to develop client applications for your
J2EE components, and how to create Web services from your applications. This course also
explains how to deploy J2EE applications to Oracle Application Server 10g, and also
addresses the handling of security issues when deploying J2EE applications. Further,
declaratively and programmatically managing transactions when using EJB is also described
in detail.

Oracle 10g: Build J2EE Applications 1-3


Course Environment

• The development tool is Oracle JDeveloper 10g,


version 10.1.2.
• The application server is Oracle Application
Server 10g, version 10.1.2.
• The database is Oracle Database 10g.

Copyright © 2005, Oracle. All rights reserved.

Course Environment
In this course, you will use the Oracle JDeveloper 10g integrated design tool to develop
J2EE components. These components will be deployed to the Oracle Application Server 10g
Containers for J2EE (OC4J) server. The OC4J server is provided within JDeveloper, and is
also contained in a full installation of Oracle Application Server 10g. You will deploy
applications to both locations. Additionally, components will access the Oracle database
10g.

Oracle 10g: Build J2EE Applications 1-4


Course Overview

• Lesson 1: Course Overview


• Lesson 2: J2EE Overview
• Lesson 3: Design considerations for building J2EE
applications
• Lesson 4: Introduction to servlets
• Lesson 5: Using JDBC to access the database
from servlets
• Lesson 6: Advanced servlet topics
• Lesson 7: Maintaining sessions in servlets
• Lesson 8: Introduction to JavaServer Pages (JSP)
• Lesson 9: Utilizing custom tags in JSP

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 1-5


Course Overview

• Lesson 10: Communication APIs in J2EE


• Lesson 11: Introduction to Enterprise JavaBeans
(EJB)
• Lesson 12: Creating session EJBs
• Lesson 13: Creating entity EJBs
• Lesson 14: Managing persistence in EJBs (BMP,
CMP)
• Lesson 15: Specifying relationships in EJBs
(CMR)
• Lesson 16: Creating Message-Driven Beans (MDB)

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 1-6


Course Overview

• Lesson 17: Integrating servlets, JSPs, and EJBs in


a J2EE application
• Lesson 18: Introduction to Web Services
• Lesson 19: Developing and publishing Web
Services
• Lesson 20: Implementing security in J2EE
applications
• Lesson 21: Transaction support in Oracle
Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 1-7


About the Course Applications

• The course uses applications that are derived


from the Order Entry and Human Resources
sample schemas.
• In the practices, you write applications that allow
users to:
– Browse available products
– Place products in a “shopping cart” for purchase
– View employee details
– Update employee data
– Send messages to a queue
– Use a Web service to validate a credit card

Copyright © 2005, Oracle. All rights reserved.

About the Course Applications


The examples, demonstrations, and practices in this course are based on the business model
of fictional Order Entry and Human Resources applications. These schemas are installed by
default with the Oracle database.

Oracle 10g: Build J2EE Applications 1-8


Order Entry Schema

ORDER_ITEMS_ORDER_ID_FK INVENTORIES_PRODUCT_ID_FK
ORDER_ITEMS_PRODUCT_ID_FK INVENTORIES_WAREHOUSES_FK

ORDERS_CUSTOMER_ID_FK

Copyright © 2005, Oracle. All rights reserved.

Order Entry Schema


In the company’s order entry records, each customer has a unique ID. A customer might
have orders that are detailed in the ORDER_ITEMS table. These orders contain products that
are office supply products.
The company is global and has several warehouses containing inventories of various
products. Some products have photos stored in the product media schema, which is not used
in this course.
This slide and the next show a brief description of the tables in the schema; Appendix B
contains a full description of each table used in the course.

Oracle 10g: Build J2EE Applications 1-9


Human Resources (HR) Schema

EMP_DEPT_FK

DEPT_LOC_FK

DEPT_MGR_FK
*

JHIST_DEPT_FK

JHIST_JOB_FK

COUNTR_REG_FK

LOC_C_ID_FK

Copyright © 2005, Oracle. All rights reserved.

Human Resources (HR) Schema


In the company’s human resource records, each employee has a unique identification
number, e-mail address, job identification number, salary, and manager.
The company also tracks information about jobs within the organization. Each job has an
identification number, job title, and a minimum and maximum salary range for the job.
The sample company is regionally diverse, so it tracks the locations of not only its
warehouses but also of its departments. Each of the company’s employees is assigned to a
department. Each department is identified by a unique department code and a short name.
Each department is associated with one location. Each location has a full address that
includes the street address, postal code, city, state or province, and country code.
For each country where it has facilities, the company records the country name, currency
symbol, currency name, and the region where the country is geographically located.

Oracle 10g: Build J2EE Applications 1-10


HR Application Flow Diagram

Employee entity

No
View
Process Administrator?
employees
log in
process
Yes

Insert
employees
process

Copyright © 2005, Oracle. All rights reserved.

HR Application Flow Diagram


In this course, you will build an application for both an Order Entry and a Human Resources
business scenario. The Order Entry scenario is discussed in detail in later lessons. The slide
above shows a general flow diagram for the Human Resources scenario.
Employees can log in to an application to view the details of the employees in their
department. If the employee who logged in to the application is an HR administrator, then he
or she may insert new employees into the application.

Oracle 10g: Build J2EE Applications 1-11


Summary

After completing this course, you should be able to:


• Create J2EE components by using best practices
• Develop J2EE applications by using servlets,
JSPs, and EJBs
• Test J2EE components by using Web and Java
clients
• Implement J2EE security in applications
• Deploy J2EE applications to Oracle Application
Server 10g
• Develop Web services, and provide access to
them

Copyright © 2005, Oracle. All rights reserved.

Summary
In this course, you learn how to create J2EE applications by using servlets, JSP, EJB, and
Web services. You learn how to design and develop J2EE applications by using Oracle
JDeveloper 10g, and make decisions about when to use the various J2EE components.
Additionally, the applications that you create are deployed to Oracle Application Server 10g.

Oracle 10g: Build J2EE Applications 1-12


J2EE Overview

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Describe the Java™ 2, Enterprise Edition (J2EE)
platform
• Define the various components of J2EE
• Describe the deployment options for a J2EE
application
• Describe the architecture of Oracle Application
Server 10g Containers for J2EE (OC4J)
• Describe the directory structure and the uses of
the configuration files of OC4J

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson discusses each of the components of the J2EE architecture and examines its
purpose in a J2EE application. J2EE applications are deployed to a J2EE server such as
Oracle Application Server 10g. This lesson also describes the configuration and structure of
Oracle Application Server 10g Containers for J2EE.

Oracle 10g: Build J2EE Applications 2-2


Java 2, Enterprise Edition Platform

The Java 2, Enterprise Edition (J2EE) platform is a


standard for developing and implementing
enterprisewide applications:
• It provides multitier applications support.
• It is designed to help improve the process of
developing, deploying, and implementing
enterprisewide applications.

Copyright © 2005, Oracle. All rights reserved.

Java 2, Enterprise Edition Platform


J2EE is a complete application architecture for enterprise class applications. It was first
proposed by Sun Microsystems and has been included in the Java Community Process to
make it a part of the open systems movement.
J2EE emphasizes a portable, component-based approach to the creation, deployment, and
management of complex applications. J2EE supports components on four tiers: client, Web,
business, and the Enterprise Information System (EIS).

Oracle 10g: Build J2EE Applications 2-3


J2EE Platform

• Is a multitiered, distributed application model


• Supports component-based J2EE applications

Servlet

Browser JSP Page


Web clients Web components

Enterprise
Application Beans
EIS tier
EJB clients EJB components

Client tier Middle tier

Copyright © 2005, Oracle. All rights reserved.

J2EE Platform
J2EE defines a platform for developing, deploying, and executing applications in a
multitiered, distributed application model. That is, the application logic of a J2EE
application can be divided into components based on their functions and distributed to the
appropriate tier on the multitiered architecture.
The slide shows a standard multitiered J2EE application model where the application logic
is distributed into the following tiers:
• Client-tier components, such as a Web browser, run on the client machine.
• Presentation logic is built with Web-tier components such as JavaServer Pages (JSP)
and Java servlets that run on the J2EE server.
• Server-side business logic is distributed as business-tier components that run on the
J2EE server. Enterprise JavaBeans (EJB) and the J2EE framework Business
Components for Java (BC4J) are examples of business-tier components.
• Data is stored in the Enterprise Information System (EIS) tier that runs on the database
server, such as Oracle Database 10g.
The J2EE application components are developed in Java programming language. When the
J2EE platform is used, the J2EE components are assembled into a J2EE application, verified
according to the J2EE specification, and deployed to the J2EE server. The deployed
applications are run and managed by the J2EE server.

Oracle 10g: Build J2EE Applications 2-4


Benefits of the J2EE Platform

• “Write once, run anywhere” provides simplified


component development.
• Multiple server products and vendors support the
J2EE standard, thus giving more deployment
choices.
• Integration with legacy systems through standard
APIs is possible.
• J2EE separates client requirements from business
logic.
• J2EE provides multiple development and design
scenarios.

Copyright © 2005, Oracle. All rights reserved.

Benefits of the J2EE Platform


J2EE takes advantage of many features of Java 2 Platform, Standard Edition (J2SE), such as
the “write once, run anywhere” portability. This portability is ensured because there are
multiple vendors who support the J2EE specification, making it easy to integrate distributed
applications. J2EE separates business and presentation logic, making the applications easier
to maintain. There are several design choices for J2EE development, including varied client
access. This is discussed later in the course.
The vendors who provide the J2EE platform (Database, Application Server) are called
“J2EE Product Providers.” A vendor or person who creates Web components, enterprise
beans, or application clients for use in J2EE applications is called an “Application
Component Provider.” A “Tool Provider” is a vendor who creates development, assembly,
and packaging tools that are used by the Component Providers. These names are assigned
along with various other J2EE roles that are discussed in the next slide.

Oracle 10g: Build J2EE Applications 2-5


Benefits of the J2EE Platform

• J2EE separates development tasks into specific


skill areas.
• Web designers can create JSP components.
• Application behavior is created by Java
programmers.
• Business logic and rules are created by Java
programmers and business experts.
• Assembly and deployment can be assigned to
production environment teams.

Copyright © 2005, Oracle. All rights reserved.

Benefits of the J2EE Platform (continued)


The J2EE platform allows for developer specialization by component type and functionality.
For example, an EJB developer can create business logic, focusing on the business rules of
the enterprise. These EJBs are used by Web component developers, who focus on the
presentation of data and the user interface. These components are assembled by an
“Application Assembler,” who is responsible for the deployment and administration of the
application.
An “Application Deployer” is the company or person who configures and deploys the J2EE
application. An “Application Administrator” is a person who administers the computing and
networking infrastructure where the J2EE applications run.

Oracle 10g: Build J2EE Applications 2-6


J2EE Components

• J2EE is a component-based architecture for the


development and deployment of enterprisewide
applications.
• A component is an application-level software unit.
• Components can be easily updated as business
needs change.
• Components are reusable.
• There are several types of components:
– Client-side components
– Web components
– Business-tier components

Copyright © 2005, Oracle. All rights reserved.

J2EE Components
There are several types of J2EE components. This course focuses on the most widely used
components, those of the Web and the business tier. These components are reusable, that is,
they are available to other components and applications. For example, the business rules that
are included in a software component called “Process Order” can be used by multiple
applications that allow customers to order the products or services of a company.

Oracle 10g: Build J2EE Applications 2-7


J2EE 1.3 Components

The J2EE 1.3 Specification lists the following


components:
• Servlet 2.3 • Java Message Service
• JavaServer Pages 1.2 1.0.2
• Enterprise • Java Transaction API 1.0
JavaBeans 2.0 • Java Authentication and
• JDBC 2.0 Authorization Service 1.0
• RMI-IIOP • J2EE Connector
Architecture 1.0
• JNDI 1.2
• SOAP with Attachments
• Web services 1.1
API for Java 1.1

Copyright © 2005, Oracle. All rights reserved.

J2EE 1.3 Components


The slide above shows many of the components that are listed in the J2EE 1.3 Specification.
A description of these components is provided on the next page. Additionally, the following
components are also included in the specification:
• JavaMail 1.2
• Java IDL 1.0
• Java API for XML Parsing (JAXP) 1.1

Oracle 10g: Build J2EE Applications 2-8


J2EE Architecture
The J2EE architecture provides a component-based and platform-independent environment,
in which each component is assembled and deployed into its corresponding container. The
J2EE server provides services to handle transaction and state management, multithreading,
resource pooling, and other complex low-level details, in the form of these containers.
Because these underlying services are provided by the J2EE server, the developer can
concentrate on solving business problems.
J2EE components communicate with each other by using several APIs. The J2EE
architecture provides the following APIs to support remote procedure calls:
• Java Naming and Directory Interface (JNDI): Provides naming and directory
functionality to applications written in Java
• Remote Method Invocation (RMI): Enables you to create distributed Java
technology–based applications, in which the methods of remote Java objects can be
invoked from other Java virtual machines, possibly on different hosts
• Java Database Connectivity (JDBC): Enables you to access any tabular data source
such as database, spreadsheets, or flat files from the Java programming language
• Java Transaction API (JTA): Specifies standard Java interfaces between a
transaction manager and the parties involved in a distributed transaction system: the
resource manager, the application server, and the transactional applications
• Java Messaging Services (JMS): Enables applications to create, send, receive, and
read messages by defining a common set of interfaces and associated semantics that
allow programs written in the Java programming language to communicate with other
messaging implementations
• JavaMail: Provides a set of abstract classes that model a mail system. The API
provides a platform-independent and protocol-independent framework to build Java
technology-based mail and messaging applications.
• JavaBeans Activation Framework (JAF): Provides standard services to determine
the type of an arbitrary piece of data, to encapsulate access to it, to discover the
operations that are available on it, and to instantiate the appropriate bean to perform
the said operations. For example, if a browser obtains a JPEG image, this framework
enables the browser to identify that stream of data as a JPEG image. Then the browser
can locate and instantiate an object that can manipulate or view that image.
Additionally, the JavaMail API uses the JAF API for data content handling.

Oracle 10g: Build J2EE Applications 2-9


Client-Tier Components

• A Web browser:
– Is used for a Web-based J2EE application
– Downloads static or dynamic Web pages from Web-
tier components
– Is a thin client
• An application client:
– Is used for a non-browser-based J2EE application
– Executes on the client machine
– Can contain a graphical or command-line interface
– Is a thick client
– Accesses business-tier components or a servlet on
the Web tier

Copyright © 2005, Oracle. All rights reserved.

Client-Tier Components
Web Browser Client
For a Web-based J2EE application, the user’s Web browser is the client component. The
Web browser downloads static or dynamic Web pages from the Web tier to a client
machine.
Dynamic Web pages are generated by servlets and JSPs from the Web tier. JSPs do not
require Java plug-ins or security policy files to be downloaded to the client machine.
A downloaded Web page can contain an embedded applet that executes in the Java Virtual
Machine (JVM) in the Web browser. An applet may require a Java plug-in and a security
file to successfully execute in the user’s Web browser.
Web-based clients are typically thin clients, which do not perform operations such as
executing complex business rules, connecting to the database, and querying the database.
These operations are generally performed by business-tier components.
Application Client
An application client executes on a client machine for a non-browser-based J2EE
application. It can contain a graphical user interface (GUI) created from Swing or Abstract
Window Toolkit (AWT) APIs or a command-line interface. Application clients can directly
access business-tier components. They can also access a servlet that is running in the Web
tier through an HTTP connection.
Oracle 10g: Build J2EE Applications 2-10
J2EE Web-Tier Components

• A Web tier may consist of:


– Java servlets
– JSPs
• Servlets and JSPs:
– Work on a request-response model
– Generate HTML dynamically
– Access the database through JDBC
– Access the business-tier components
– Handle user-centric events, such as an HREF link or
form submission
– Usually generate visual interfaces such as a Web
page

Copyright © 2005, Oracle. All rights reserved.

Web-Tier Components
J2EE Web-tier components can be either servlets or JSPs that can statically and dynamically
generate HTML, Wireless Markup Language (WML), or Extensible Markup Language
(XML) pages. Java servlets provide a simple yet powerful API for generating Web pages by
dynamically processing the client requests and constructing responses. JSPs simplify the
process of dynamically generating the content, by allowing Java as the scripting language
inside HTML pages. JSPs are translated and compiled into Java servlets, which are then run
in a Web server like any other servlet.
Web components can access the business-tier components that access the database by using
JDBC. Web components can handle requests from the client, such as form submission.
Some advantages of using Web components are listed below:
• The HTML interface that is generated by a Web component is lightweight when
compared with the applets that require heavyweight downloads to the clients at run
time. Also, the HTML interface does not require prior installation on the client
machines, whereas the conventional clients require redeployment of the applications
on the client machines.
• The HTTP protocol, over which the client’s request for Web pages are served, can pass
through most firewalls.

Oracle 10g: Build J2EE Applications 2-11


Web-Tier Components (continued)
Thus, a combination of Web components and EJBs allows:
• Presentation logic for generating Web pages through Web components
• Transactional business logic through EJBs

Oracle 10g: Build J2EE Applications 2-12


What Is a Servlet?

Browser Servlet

Client info (host name, Process results


form data) Request (access database)

Format results and produce


Success or failure HTML

Send page back to client

Response

Copyright © 2005, Oracle. All rights reserved.

What Is a Servlet?
A servlet is a Java program that runs on a server, such as Oracle Application Server 10g, and
produces dynamic pages typically in response to client requests. The pages are then sent
back to the client’s Web browser. Typically, the output format for servlets is HTML, but any
other output format, including XML, can be used.
Before returning HTML pages, a servlet can perform any operation that a Java application
can perform. For example, in a business environment, servlets access the database through
JDBC, so that you can send custom HTML pages and forms with embedded data to your end
users.
Because servlets contain Java code, they are best suited for programs that perform more
processing than presentation. Presentation is best left to JSPs, which are discussed in the
next slide.

Oracle 10g: Build J2EE Applications 2-13


What Is a JavaServer Page (JSP)?

A JSP:
• Is a text-based document that includes:
– HTML
– JSP tags
– Java code (including calls to JavaBeans
and servlets)
• Cleanly separates content creation from
presentation logic
• Focuses on rapid development and easy
modification of the user interface
• Provides presentation-centric method of
developing servlets

Copyright © 2005, Oracle. All rights reserved.

What Is a JavaServer Page (JSP)?


JSPs are servlets that are written differently. The JavaServer Pages technology separates the
user interface from dynamic content generation, so that designers can easily change the
overall page layout without altering the dynamic content. JSP technology supports a
reusable component-based design, making it easy and fast to build Web-based applications.
A key feature of the JavaServer Pages technology is simplified page generation: HTML-like
tags and scriptlets written in the Java programming language encapsulate the logic that
generates the content for the page. By separating the presentation design from the
application logic that generates the data, JSP-enabled pages make it easier for organizations
to reuse and share application logic through custom tags and JavaBeans-based components.
This also separates the job responsibilities of the Web designer and the Java programmer.
For example, custom tags and beans can be developed by the Java programmer and
implemented by the Web designer.

Oracle 10g: Build J2EE Applications 2-14


Web-Tier Components: Summary

• Web-tier components generate dynamic content.


• Servlets:
– Extend Web server functionality
– Are designed more for processing than for
presentation
• JSPs:
– Combine HTML (or other markup) and Java
– Are designed to separate content creation from
presentation logic
– Are precompiled and converted to servlets at run
time

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 2-15


Business-Tier Components

Business-tier components:
• Are EJBs
• Handle business logic
• Receive data from client programs
• Retrieve data from database storage
• Process the data and communicate with the
database and the client program
• Can be invoked by the Web-tier components

Copyright © 2005, Oracle. All rights reserved.

Business-Tier Components
EJBs are the components that run in the business tier. These distributed components contain
business logic that meets the needs of a particular business domain such as banking, order
entry system, or human resources management. The business-tier components can receive
data from client programs, process the data, and send the processed data to the database
server for storage. The business-tier components can also retrieve data from the database,
process it, and send it back to the client program.
The Web-tier components might invoke the business-tier components where the business
logic is handled. For example, a servlet might invoke an enterprise bean to insert new
customer details and return any processed data back to the client.

Oracle 10g: Build J2EE Applications 2-16


Enterprise JavaBeans (EJB)

Enterprise JavaBeans:
• Are server-side components written in Java
• Contain the business logic of an enterprise
application
• Are hosted in EJB containers
• Are based on Remote Method Invocation (RMI)
communication
• Are platform independent
• Provide remote services for clients
• Can be exposed as Web services
• Use JDBC to connect to a database

Copyright © 2005, Oracle. All rights reserved.

Enterprise JavaBeans (EJB)


Enterprise JavaBeans (EJB) is an architecture for developing transactional applications as
distributed components in Java. EJB is a powerful development methodology for distributed
application development. When applications are developed with enterprise beans, neither the
bean developer nor the client application programmer needs to be concerned with details
such as transaction support, security, remote object access, and many other complicated and
error-prone issues. These are provided transparently for the developer by the EJB container.
EJBs offer portability. A bean that is developed on one EJB container will run on other EJB
containers that meet the EJB specification. Oracle Application Server 10g implements the
EJB specification by providing a server and a container that hosts the Enterprise JavaBeans.
EJB specifies Remote Method Invocation (RMI) as the transport protocol. EJBs access the
EIS-tier database through JDBC.
EJBs are accessed using Java’s RMI (Remote Method Invocation) framework, which can be
implemented with different network protocols. Oracle Application Server 10g provides the
RMI/Internet Inter-ORB Protocol (IIOP) protocol, as well as a platform-specific, optimized
protocol called Oracle Remote Method Invocation (ORMI).
Additionally, a stateless session EJB can be exposed as a Web service. Web services are a
standard for building interoperable distributed applications that are platform and
programming-language independent. Stateless session EJBs and Web services are discussed
in detail later in this course.
Oracle 10g: Build J2EE Applications 2-17
J2EE Communication APIs

• J2EE provides component communication


through APIs.
• The APIs include:
– RMI
– JNDI
– JDBC
• These APIs facilitate communication between the
J2EE components.

Copyright © 2005, Oracle. All rights reserved.

J2EE Communication APIs


RMI, JNDI, and JDBC are Java communication APIs. RMI and JNDI allow J2EE
components to communicate with one another, whereas JDBC allows J2EE components to
interact with the database.

Oracle 10g: Build J2EE Applications 2-18


J2EE Server

The J2EE server provides:


• Containers for each component type of a J2EE
application
• System-level services to components:
– Naming and directory services (JNDI)
– Security services for Web components and EJBs
(JAAS)
– Transaction architecture (JTA)
– Remote client connectivity:
– Enterprise beans (RMI/IIOP, ORMI)
– Servlet/JSP (HTTP, HTTPS, FTP)

Copyright © 2005, Oracle. All rights reserved.

J2EE Server
The J2EE server is the run-time portion of a J2EE product. A J2EE server provides EJB and
Web containers. The Web-tier and business-tier components can themselves be clients for
the other J2EE application components.
An advantage of the J2EE standard is that all the container providers must abide by the same
J2EE standards. This is much easier for developers because the application assembly is the
same in any J2EE-compliant environment.
The J2EE server provides system-level services to the J2EE application components:
• J2EE naming services provide the J2EE application components with access to the
Java Naming and Directory Interface (JNDI) lookup services. Using the JNDI lookup
service, the components can locate user-defined objects, environment entries,
enterprise beans, JDBC DataSource objects, and messaging connections.
• The security services enable you to configure Web-tier and business-tier components
so that only authenticated and authorized users can access the system resources.
• The transaction architecture enables you to specify relationships among methods that
make up a single transaction so that all methods in one transaction are treated as a
single unit.

Oracle 10g: Build J2EE Applications 2-19


J2EE Server (continued)
• The remote connectivity service manages the low-level communications between
clients and J2EE components. This provides location transparency to the clients. The
client accesses the components as if both of them (the client and the Web-tier or
business-tier components) are on the same Java virtual machine.

Oracle 10g: Build J2EE Applications 2-20


Oracle Application Server 10g Containers
for J2EE (OC4J)

• OC4J is the J2EE server implementation in Oracle


Application Server 10g
• Key features:
– Implements J2EE 1.3 Specification
– Runs on standard JVM
– Provides high performance and scalability
– Is productive for developers to use
– Is simple to manage and deploy
– Provides clustering for high availability and failover

Copyright © 2005, Oracle. All rights reserved.

Oracle Application Server 10g Containers for J2EE (OC4J)


Oracle Application Server 10g provides a complete J2EE server, called Oracle Application
Server 10g Containers for J2EE (OC4J). It is written in Java and executes on the standard
Java Virtual Machine (JVM). OC4J is installed in three ways:
• Is included in Oracle Application Server 10g
• Is included in Oracle JDeveloper 10g
• Is available as a stand-alone version (that is, without any other software)
In this class, OC4J is installed with Oracle Application Server 10g as well as Oracle
JDeveloper 10g. This means that you can test applications on OC4J by using JDeveloper,
and deploy them to Oracle Application Server 10g.

Oracle 10g: Build J2EE Applications 2-21


J2EE Applications

J2EE applications consist of J2EE components and


are deployed in the form of modules:
• Web modules contain the user interface: HTML,
JSP, and servlets.
• EJB modules contain reusable EJB components.
• Client modules provide access to remote
application code.
• Packaging information identifies dependencies
between modules.

Copyright © 2005, Oracle. All rights reserved.

J2EE Applications
J2EE applications are server-side applications that contain standard components such as
servlets, JSPs, and EJBs. Applications are deployed in the form of modules that package all
necessary code for deployment to a J2EE server such as Oracle Application Server 10g.
Modules are archive files in a standard format, specified by the J2EE architecture.

Oracle 10g: Build J2EE Applications 2-22


Packaging J2EE Application Components

1. ejb.jar
Bean class, Home and Remote
interfaces, other supported files, DD

2. webtier.war
Java servlets, JSP files, HTML, GIF files,
DD (references to EJBs)
J2EEapplication.ear
3. J2EEappClient.jar
J2EE application client (Java class),
DD (references to EJBs)

4. DD for J2EE application (.xml)

DD = XML Deployment 5. Resource adapter (.rar)


Descriptor

Copyright © 2005, Oracle. All rights reserved.

J2EE Application Components


The diagram in the slide shows the components of a J2EE application. A J2EE application is
typically archived into an Enterprise Archive (EAR) file. This file contains the following:
• A Java Archive (JAR) file that contains the archive of EJB components—EJB class
files, Home and Remote interfaces, and EJB deployment descriptor that contains
information about transaction attributes, security roles, and so on.
• A Web Archive (WAR) file that contains the archive of Web components—Java
servlets, JSP files, HTML, GIF files, and a deployment descriptor that contains
references of the EJBs being accessed, in ejb-ref tags.
• A JAR file that contains the archive of a J2EE application client in the form of a Java
class, and a deployment descriptor that contains references to the EJBs from which the
business methods are being accessed. The J2EE application client is a Java application
that runs in an environment that allows it to access J2EE services.
• A deployment descriptor of the J2EE application, which is a reference file for
deployment, that contains information about the .war, .jar files, and security
information.
• An optional resource adapter archive (RAR), which is a driver that either an
application server or an application client uses to connect to a specific EIS. Examples
of resource adapters are JDBC drivers to connect to a relational database, or an ERP
resource adapter to connect to an ERP system.
Oracle 10g: Build J2EE Applications 2-23
JARs

• Are simple Java Archive files


• Are used to package application files together
(for example, classes, images, and so on)
• Can be included in Web Archives (WARs) and
Enterprise Archives (EARs)
• Can be included in library paths

Copyright © 2005, Oracle. All rights reserved.

JARs
A standard JAR file has the following structure:
|-------META-INF
| -------manifest.mf
|-------Java classes
Typically, JAR files are used to hold groups of related Java packages (such as JDBC or
Swing). To simplify deployment or make operational access more efficient, you may want to
include them in EJB-JAR files, WAR files, or EAR files.

Oracle 10g: Build J2EE Applications 2-24


WARs

• Are specialized archives for packaging


J2EE-compliant Web applications
• Have a fixed directory structure
• Have a deployment descriptor for the Web
application
WEB-INF

web.xml
Contain servlet code and
classes JavaBeans not in standard
JAR files
lib Contains required classes
that are packaged in
index.html standard JAR files
welcome.jsp

Copyright © 2005, Oracle. All rights reserved.

WARs
Each WAR file is created with the Web application and its XML files, which are structured
as follows:
|-------WEB-INF
| |-------web.xml
| |-------classes
| |-------Servlet classes (may be included inside packages)
| |-------lib
|-------index.html
|-------JSPs
Note that a WAR file may contain both HTML and JSPs, as well as many other supporting
files.

Oracle 10g: Build J2EE Applications 2-25


EJB JARs

• Are specialized JARs for packaging EJBs


• Have a fixed directory structure
• Have a deployment descriptor for the EJB
components

myEJB

META-INF
ejb-jar.xml
Contain the class files
for the EJBs, usually
EJB Classes
in a package directory
Remote, Home and structure
Bean classes

Copyright © 2005, Oracle. All rights reserved.

EJB JARs
Each EJB file is created with the EJB application classes and XML files, which are
structured as follows:
|-------META-INF
| |-------ejb-jar.xml
| |-------orion-ejb-jar.xml
|
|-------EJB classes
J2EE specifications recommend the use of an application directory to locate all application-
specific XML files. This is recommended because it keeps the global and default
configuration files separate from the application-specific configuration files. The
orion-ejb-jar.xml file is used by OC4J to deploy EJBs. Its use is discussed in detail
later in the course.

Oracle 10g: Build J2EE Applications 2-26


EARs

The EAR files:


• Are specialized archives for packaging
J2EE-compliant enterprise applications for
deployment
• Have a deployment descriptor
• May have Web modules
• May have EJB modules
• May have client modules

Copyright © 2005, Oracle. All rights reserved.

EARs
As J2EE applications became larger and more complex, there was a need to simplify
distribution. The J2EE specification addresses this issue. Organizations can use EAR files to
package all the client modules—HTML pages, JSPs, Servlets, EJBs, manifest files, and
XML configuration files—that are needed to distribute an entire application. All these files
are contained in a single archive file with a standard organization.

Oracle 10g: Build J2EE Applications 2-27


EAR File Structure for a
J2EE Application: Example
<appname>
|-------META-INF
| |-------application.xml
|-------<ejb_module>
| |-------EJB classes
| |-------META-INF
| |-------ejb-jar.xml
|-------<web_module>
| |-------index.html
| |-------JSP pages
| |-------WEB-INF
| |----web.xml
| |----classes
| |-------Servlet classes
|-------<client_module>
| |-------Client classes
| |-------META-INF
| |-------application-client.xml

Copyright © 2005, Oracle. All rights reserved.

EAR File Structure for a J2EE Application: Example


The diagram in the slide indicates a suggested directory path for deploying your J2EE
applications.
The names of the META-INF and WEB-INF directories and application.xml,
ejb-jar.xml, web.xml, and application-client.xml files are predefined in
the OC4J server according to the J2EE specifications. There are separate directories to
clearly separate modules of the application. The application.xml file, which acts as
the manifest file, defines these modules.
In this example, the directories containing the separate modules (ejb_module,
web_module, and client_module), and the directory that contains the modules
(appname), may have arbitrary names. These names must match the values in the manifest
file (application.xml).
For EJB modules, the top of the module represents the start of a search path for classes. As a
result, classes belonging to packages are expected to be located in a nested directory
structure beneath this point. For example, a reference to a class in a package
myapp.ejb.demo is expected to be located in the
<appname>/ejb_module/myapp/ejb/demo directory.

Oracle 10g: Build J2EE Applications 2-28


OC4J Architecture

Oracle HTTP JNDI


HTTP Server
AJP Web JMS
AJP13
mod_oc4j container JDBC

JTA
Client
JAAS

EJB JCA
ORMI
container JavaMail
ORMI
JAF

EJB client OC4J server process

Copyright © 2005, Oracle. All rights reserved.

OC4J Architecture
OC4J implements the J2EE infrastructure. The OC4J Web container and the OC4J EJB
container use the J2EE virtual machine.
The J2EE containers perform services for applications, such as providing access to the APIs
and life-cycle management.
When Oracle HTTP Server receives a request, such as
http://myserver.com/j2ee/HelloWorldServlet, from the URL, it determines
the modules that are configured to handle this request, based on the mapping in the
configuration file (httpd.conf or mod_oc4j.conf).
In this case, Oracle HTTP Server resolves that mod_oc4j is responsible for this request,
because the /j2ee virtual path is mapped to the OC4J server. mod_oc4j then contacts a
specified OC4J instance by using Apache JServ Protocol (AJP). AJP is faster than HTTP,
through the use of binary formats and efficient processing of message headers.
Oracle Remote Method Invocation (ORMI) is the protocol through which EJB clients access
EJBs that are deployed to the container. This and the other APIs shown in the slide are
discussed in detail later in the course.
Additionally, HTTP is available directly to the OC4J process for development purposes.

Oracle 10g: Build J2EE Applications 2-29


OC4J Server Configuration Files
OC4J Server XML Files
Server Configuration
server.xml Web site
Web
Website
site
jazn.xml*
default-web-
jazn-data.xml* site.xml
data-sources.xml
rmi.xml
jms.xml

Oracle HTTP Server


configuration files

mod_oc4j.conf

Copyright © 2005, Oracle. All rights reserved.

OC4J Server Configuration Files


The OC4J server is configured by using XML-based configuration files. These files are
standard for J2EE servers. In later lessons, you see how OC4J extends these files.
These configuration files provide a way of integrating components with the OC4J
framework. There is no need to modify the XML files that are contained in JARs, WARs,
and EARs while they are being deployed.
There is an implied hierarchy to these configuration files:
server.xml
|------>rmi.xml
|------>jms.xml
|------>application.xml
| |------>principals.xml
| |------>data-sources.xml
|------>global-web-application.xml
|------>default-web-site.xml
|------>default-web-app
|------>web-app
*The jazn.xml and jazn-data.xml files describe the security configuration by using
the OC4J JAAS provider. If Java Authentication and Authorization Service (JAAS) is not
used, then these files need not be configured.
Oracle 10g: Build J2EE Applications 2-30
Relation of Configuration Files

• When an application is deployed, an entry is made in


the \config\server.xml file:
<application name="lesson02"
path="../applications/lesson02.ear" />

• For each Web module within the application, a context


root is defined in \config\default-web-site.xml:
<web-app application="lesson02" name="webapp1"
root="/lesson02"/>

• The modules of the application are defined in


\applications\lesson02\META-
INF\application.xml:
<web><web-uri>webapp1.war</web-uri></web>

Copyright © 2005, Oracle. All rights reserved.

Relation of Configuration Files


The server.xml, default-web-site.xml, and application.xml files work
together to define the configuration for an application. If an application named “lesson02” is
deployed by using a lesson02.ear file (which contains webapp1.war), the
deployment will create entries in the corresponding files, as shown in the slide above. Note
that the default-web-site.xml file is used for those applications that are deployed to
Oracle Application Server 10g installations. If the applications are deployed to the
embedded OC4J server that is installed with Oracle JDeveloper 10g, then the http-web-
site.xml file is used instead. The mod_oc4j.conf configuration file is used to specify
which OC4J instance will handle requests for each context root.

Oracle 10g: Build J2EE Applications 2-31


Data Sources

A data source is the instantiation of an object that


implements the javax.sql.DataSource interface,
which enables you to retrieve a connection to a
database server.
• OC4J data sources are defined in data-
sources.xml.
• J2EE applications use JNDI to look up these
DataSource objects.

Copyright © 2005, Oracle. All rights reserved.

Data Sources
Data sources are a portable method for creating JDBC connections. The data-
sources.xml file is preinstalled with a default data source named OracleDS. However,
you can also add your own customized data source definitions. The default data source from
data-sources.xml is listed below:
<data-source
class="com.evermind.sql.DriverManagerDataSource"
name="OracleDS"
location="jdbc/OracleCoreDS"
xa-location="jdbc/xa/OracleXADS"
ejb-location="jdbc/OracleDS"
connection-driver="oracle.jdbc.driver.OracleDriver"
username="scott" password="tiger"
url="jdbc:oracle:thin:@localhost:5521:oracle"
inactivity-timeout="30"
/>

Oracle 10g: Build J2EE Applications 2-32


Application Logging

• Application logging in Oracle Application Server


10g is configured by specifying the location of a
log file in the application.xml file:
<log>
<file path="practice02-oc4j-app.log"/>
</log>

• To create a log file formatted in XML, use Oracle


Diagnostic Logging (ODL):
<log>
<odl path="practice02-oc4j-app.log"/>
</log>

Copyright © 2005, Oracle. All rights reserved.

Application Logging
In Oracle Application Server 10g, you can use the OC4J application.xml
configuration file to specify that a log file be created. The path attribute is relative to the
location of the application.xml file. The resulting log file is useful for debugging
applications during development, as well as tracing run-time errors. An example of the
output generated in a log file is as follows:
04/02/25 01:04:35 Started
04/02/25 01:04:36 practice02-login-webapp: JDevOJSP: init
04/02/25 01:04:36 practice02-login-webapp: 10.1.2.0.0 Started
04/02/25 01:04:36 practice02-login-webapp: LoginServlet: init

Oracle 10g: Build J2EE Applications 2-33


J2EE Application Deployment to
Oracle Application Server 10g

Deploying to OC4J can be done in multiple ways:

Step 1: Create WAR, Step 2: Deploy


EAR file Step 2: Deploy
Use a command- Use Oracle Enterprise Manager
line tool (such as (installed with Oracle Application
ANT). Server 10g): Access the
Enterprise Manager Web site
Use JDeveloper – specifyhttp://localhost:1810
an
Application Server and click 'Deploy'
(requires login).
Use JDeveloper. Use JDeveloper: Specify an
application server and click
“Deploy.”

Copyright © 2005, Oracle. All rights reserved.

J2EE Application Deployment to Oracle Application Server 10g


A J2EE application can be deployed by using a command-line tool to copy WAR, EAR, and
JAR files to the proper location on the J2EE server. However, several tools are available to
make this process easier. JDeveloper supports the deployment of a J2EE application to a
J2EE server (such as Oracle Application Server 10g) by using a deployment profile.
Additionally, OC4J can be administered and applications can be deployed to an OC4J
instance by using Oracle Enterprise Manager Application Server Control. You can also
deploy by using a command-line deployment tool, such as ANT.

Oracle 10g: Build J2EE Applications 2-34


Oracle Enterprise Manager

localhost

Copyright © 2005, Oracle. All rights reserved.

Oracle Enterprise Manager


The slide above shows the OC4J home page, where you can stop and restart OC4J instances,
and also deploy applications. You can access the OC4J home page by following the
OC4J_home link from the Oracle Enterprise Manager home page on the default port 1810.

Oracle 10g: Build J2EE Applications 2-35


JDeveloper and J2EE

JDeveloper provides:
• Integrated development, deployment, and testing
support for Web-tier and business-tier
components
• A J2EE framework for rapid development
– Application Development Framework (ADF)
business components
– Data tags
• Integration with Struts
• UML modeling
• Visual editors for Web clients JDeveloper
• Easy deployment to Oracle Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

JDeveloper and J2EE


JDeveloper is an Integrated Development Environment (IDE) that is used to build, test, and
debug J2EE applications. In Oracle JDeveloper 10g, workspaces and projects are used to
organize the files that you need for your application. To effectively work with the files in
JDeveloper, you can use projects to work with individual files, and workspaces to manage
one or more projects. You must have a workspace before you can create projects. It is a
common practice to create workspaces around functions of applications, such as human
resources management; and to separate technologies into projects, such as having separate
projects for the model, view, and controller. By using the UML Modeler, you can model
business processes, build J2EE components, test and debug them, and easily deploy the
business processes to Oracle Application Server 10g or other J2EE servers.

Oracle 10g: Build J2EE Applications 2-36


Oracle JDeveloper 10g Environment

Customizable code editor

Wizards for
JSPs,
servlets, and
EJBs

Error
checking
for HTML
and JSP

EAR, WAR
deployment
to J2EE
server
Code insight

Copyright © 2005, Oracle. All rights reserved.

Oracle JDeveloper 10g Environment


JDeveloper provides you with several helpful development features. Wizards for creating
servlets, JSPs, and EJBs make it easy to start building a Web application. The code editor is
customizable and code insight makes it easy to develop code without having to remember
each package and class name. Debugging is provided in both local and remote modes, and
errors in HTML and JSPs are identified within the IDE. Additionally, JDeveloper automates
the packaging of J2EE applications into WAR or EAR files for deployment to a J2EE server.
Oracle Application Server 10g Containers for J2EE (OC4J) is provided within the tool to
test and debug the J2EE applications.

Oracle 10g: Build J2EE Applications 2-37


Oracle JDeveloper 10g
Visual Design Tools

Drag JSP and HTML


elements

Modify values
in property
Design in visual inspector
or code views

Copyright © 2005, Oracle. All rights reserved.

Oracle JDeveloper 10g Visual Design Tools


Oracle JDeveloper 10g enables you to choose between editing in code or visual views for
JSP and HTML documents. You can drag JSP and HTML elements from the component
palette to the visual or code views, and elements can be modified directly in the code or
visual editor, or in the property inspector. The code editor, visual editor, property inspector,
and another visual tool, the structure pane, are all synchronized so that a change in one
propagates immediately to all other representations of the data.

Oracle 10g: Build J2EE Applications 2-38


Summary

In this lesson, you should have learned that:


• J2EE is a set of Java technologies that support
end-to-end application development
• Components are the foundation of the J2EE
architecture
• Web components (servlets, JSPs) generate
dynamic content
• Business components (EJBs) are server-side
components that contain business logic
• Applications can be built by using Oracle
JDeveloper 10g and deployed to a J2EE server,
such as Oracle Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Summary
J2EE components include servlets, JSPs, and EJBs. These components are divided into
functions of business and presentation logic. J2EE applications can be built by using Oracle
JDeveloper 10g and deployed by using JDeveloper, Oracle Enterprise Manager Application
Server Control, or other tools.

Oracle 10g: Build J2EE Applications 2-39


Practice 2-1: Overview

This practice covers the following topics:


• Navigating to the OC4J console by using Oracle
Enterprise Manager
• Mapping a data source in OC4J
• Restarting the OC4J server instance from Oracle
Enterprise Manager
• Deploying an EAR file by using Oracle Enterprise
Manager

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 2-40


Practice 2-1
In this practice, you navigate to the Oracle Enterprise Manager console, modify the default
data source, and restart the OC4J server. Additionally, this practice gives you the
opportunity to view the files that OC4J uses to configure a J2EE application. You also
deploy an existing application by using Oracle Enterprise Manager.
1. Navigate to the Oracle Enterprise Manager console.
a. Open a browser and navigate to http://localhost:1810.
b. Enter the username ias_admin and the password welcome1.
c. Navigate to the home instance page by clicking the home link.
2. Create a data source reference.
a. Click the Administration tab and click the Data Sources link.
b. Click Create and enter these details:
Name: hrDS
Description: hr
Data Source Class: com.evermind.sql.DriverManagerDataSource
JDBC URL: The URL provided to you by your instructor
JDBC Driver: oracle.jdbc.driver.OracleDriver
In Datasource Username:
Username: oraxx (as provided to you by your instructor)
Use a cleartext password of oracle
In JNDI Locations:
Location: jdbc/hrCoreDS
Transactional location: jdbc/xa/hrXADS
EJB location: jdbc/hrDS
Leave all other fields blank or set to the default.
c. Click Create and restart OC4J when prompted.
3. Verify the change that you made to the data source.
a. Navigate to the oraas10g directory and locate the j2ee\home\config
directory.
b. Open data-sources.xml in WordPad. Note that the data source that you
added in step 2 is defined here.
c. You may also want to view application.xml, server.xml, and other
configuration files that are discussed in this lesson.
4. Deploy an existing J2EE application by using Oracle Enterprise Manager. The
application you deploy in this step is actually the application that you will build in
practice 17.
a. Click the applications tab from the OC4J home page and click Deploy EAR File.
b. Browse to the <JDEV_HOME>\jdev\mywork\practice02 directory and
select application1.ear.
c. Name the application practice02 and click Continue.
d. Modify the URL Mapping as /practice02 and click Next.
e. Enter jdbc/hrCoreDS for the JNDI location name and click Next.

Oracle 10g: Build J2EE Applications 2-41


Practice 2-1 (continued)
f. Because there is no user security defined for this application, click Next in the
following page.
g. Click Deploy to deploy the application.
h. Click OK after the application has been deployed.
5. Access the application.
a. Enter the following URL in the browser:
http://localhost/practice02/loginservlet
b. Enter 100 in the Employee ID field and King in the Employee Name field and
click Login.
c. View the Employees in King’s department and click the Insert link.
d. Enter the following information in the form.
ID: 500
First Name: Your first name
Last Name: Your last name
Email: Your e-mail account
Hire Date: A date in the format of “dd-mon-yy”
Job ID: AD_VP
e. Verify whether the employee was inserted by using SQL*Plus to query the
EMPLOYEES table.

Oracle 10g: Build J2EE Applications 2-42


Designing J2EE Applications

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Describe the various Java 2, Enterprise Edition
(J2EE) patterns
• Use the Model View Controller (MVC) architecture
to design more efficient and maintainable
applications
• Identify sample architectures and their merits and
demerits

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson deals with the design of J2EE applications. After working for several years with
the object-oriented (OO) programming concepts, developers found that the best applications
follow similar patterns. This lesson discusses these patterns and also the principles of
developing an application that adheres to best practices.

Oracle 10g: Build J2EE Applications 3-2


Realizing J2EE Benefits

To leverage the full benefits of J2EE, you must design


applications that are:
• Portable: You should be able to redeploy the J2EE
applications to different servers, databases, and
so on.
• Scalable: Web applications should be able to
handle large numbers of users.
• Maintainable: A minimum amount of coding
should be necessary for a new business rule.
• Reusable: A class that processes credit cards
should be reused by multiple applications.
• Simple: The business need should be solved with
the least amount of complexity.

Copyright © 2005, Oracle. All rights reserved.

Realizing J2EE Benefits


J2EE helps achieve portability, which is particularly important for applications that must be
clustered. Additionally, well-designed J2EE applications are scalable when the number of
users and their actions are difficult to predict, as in Internet applications. J2EE applications
must be able to accommodate new business needs in an organization, because this
application could be used within an organization for many years. Applications that allow
code reuse for minimizing duplication benefit from object-oriented design. Finally,
applications that avoid unnecessary complexity are engineered to meet the needs of the
business, without becoming overcomplicated by using the latest buzzword technology.

Oracle 10g: Build J2EE Applications 3-3


J2EE Issues

It is important to follow certain guidelines for the


design and development of any new technology:
• Implement generally accepted design patterns and
architectures.
• Focus on real business needs rather than simply
adopting new technology.
• Employ the simplest technology to solve a
business problem.

Copyright © 2005, Oracle. All rights reserved.

J2EE Issues
Developers are often directed toward J2EE as a complete, effective solution, where
scalability and portability are handled automatically, without the need for good design
patterns. Thus, many J2EE applications are built to use the latest functionality, without
solving the needs of the enterprise. For example, there is a great debate in the J2EE
community about the use of Enterprise JavaBeans (EJB). EJBs solve some problems, but
can add unnecessary complexity to an application that does not require them. The following
guidelines can help you determine when to use EJBs:
• When you are developing for a distributed architecture, and developers are
knowledgeable in the use of EJBs, use EJB to manage business objects and their life
cycle and invocation.
• If the application is designed to develop scalable, robust applications, and the
developers have little knowledge of EJBs, then you must use Web applications that do
not use EJBs.

Oracle 10g: Build J2EE Applications 3-4


J2EE Design Patterns

Recurring application development issues have led to


the acceptance of design patterns. The generally
accepted design patterns include (but are not limited
to) the following:
• Presentation-tier patterns
– Intercepting filter
– Controller servlet
• Business-tier patterns
– Business delegate
– Transfer object

Copyright © 2005, Oracle. All rights reserved.

J2EE Design Patterns


Design patterns describe solutions for common design issues. This slide is an introduction to
some of the more popular design patterns. An explanation of these patterns is as follows:
• Presentation-Tier Design Patterns
- Intercepting filter: Facilitates preprocessing and postprocessing of a request, by
applying additional services that are needed to process a request. A servlet filter
(discussed in a later lesson) is an example of an implementation of this pattern.
- Controller servlet: Provides a centralized controller for handling a request. This
is more comprehensive than the intercepting filter approach, because all requests
are maintained in the same controller.
• Business-Tier Design Patterns
- Business delegate: Decouples presentation and service tiers and provides a
façade and proxy interface to services by intervening between a remote business
object on the EJB tier and its client
- Transfer object: Facilitates data exchange between tiers by reducing network
load

Oracle 10g: Build J2EE Applications 3-5


Implementing Design Patterns by
Using MVC

MVC is a framework that separately identifies the


components of an application as:
• Business functionality (Model)
• Presentation (View)
• Control logic (Controller)

View Controller

Model

Copyright © 2005, Oracle. All rights reserved.

Implementing Design Patterns by Using MVC


MVC is an aggregate design pattern; encompassing several patterns. The result is a
framework that identifies components in an application as having different functions. Thus,
if the client is a browser in J2EE applications, the Model View Controller (MVC)
architecture helps to separate business and presentation logic within an application.
Separating application functionality in this way minimizes the need to modify business
logic, if a column name changes in the database, or if the user interface must be adapted for
a client browser, a PDA, or a cell phone. This reduces code duplication and minimizes
maintenance.

Oracle 10g: Build J2EE Applications 3-6


The Model

• The model represents the enterprise data and


business rules, handling access and updates.
• You can simplify the model by using two
mechanisms called “façade class” and “command
pattern.”
– A façade encapsulates and hides the complexity,
and coordinates the operations between
cooperating classes.
– A command pattern encapsulates each application
function in a separate class.
• The model is often implemented as EJBs.

Copyright © 2005, Oracle. All rights reserved.

The Model
The model of an application contains the business data and the operations that govern access
and modification of the data. Thus, it is often implemented as EJBs. The model notifies a
view when it changes and provides the ability for the view to query the model about its state.
The controller accesses the application functionality that is encapsulated in the model. A
session bean is often used to create the façade. For example, a session façade bean provides
the required interfaces (while hiding the complexities of the interfacing classes from the
client), and manages the relationships between the objects. A command pattern bean
provides the business logic of the interfaces that a session façade bean implements.

Oracle 10g: Build J2EE Applications 3-7


The View

• The view focuses on presentation and is


responsible for maintaining consistency between
data presentation and model changes. It enables:
– Presentation to be changed without altering
programming logic
– Development by Web page authors having only
visual design skills
• The view is commonly implemented as JSPs.

Copyright © 2005, Oracle. All rights reserved.

The View
The view of an application renders the contents of a model and specifies how data should be
displayed. The view forwards the user input to a controller. For example, a view component
might display rows from a database. The actual querying of the data should be left to the
model, but formatting the data for the client is left to the view. For this reason, view
components are usually JSPs. An application might be designed to accept query parameters
from user input. In this example, the parameters would be passed to the model from the
controller (discussed in the next slide), and the resultant data would be displayed in the
view.

Oracle 10g: Build J2EE Applications 3-8


The Controller

• The controller provides interaction with the client,


serving as a “glue” between the model and the
view.
• The controller:
– Interprets user requests, and controls business
objects to fulfill these requests
– Removes navigation coding from the view
– Can be implemented in the client, Web, or EJB tier
or in a combination of these tiers
• The controller is usually implemented as a servlet.

Copyright © 2005, Oracle. All rights reserved.

The Controller
A controller defines application behavior. It dispatches user requests and selects views for
presentation. The controller determines what happens when the user interacts with the
component, for example, what occurs when the user clicks a button. In the example on the
previous page, the controller would accept the user’s query parameters and pass them to the
model. A servlet is best suited for this MVC component, because it contains coding logic for
accepting user input and passing it to a model, with little or no presentation coding, such as
HTML. In this way, the controller makes the application more maintainable as a whole. The
database column names or the preferred formatting style could change, without affecting the
navigation and functionality of the application. A developer would simply change either the
model or the view, respectively.

Oracle 10g: Build J2EE Applications 3-9


MVC in Oracle Application Server 10g
Containers for J2EE

View Controller Model

Selected Method
view invocation

Return
result
JSP Servlet Enterprise
JavaBeans
HTTP HTTP
request response
Browser

Copyright © 2005, Oracle. All rights reserved.

MVC in Oracle Application Server 10g Containers for J2EE


OC4J separates the model, the view, and the controller by using different containers for each
type of J2EE component. A JavaServer Page (JSP) creates dynamic HTML, which is
rendered in a browser. When the user interacts with the JSP (for example, by submitting a
form), the request is processed by the controller. The controller invokes the methods in the
EJBs, and the EJBs return the result to the controller. This result is then passed on to the
view and displayed as specified in the JSP.

Oracle 10g: Build J2EE Applications 3-10


Designing J2EE Applications

Use the following techniques when designing J2EE


applications:
• Use case analysis: Identify the operations that
each component will perform.
• Decide how to distribute application functionality
across tiers:
– A JSP or servlet can access the database by using
JDBC, without interfacing with the EJB tier.
– Creating EJBs relieves the developer from the task
of managing transactions.

Copyright © 2005, Oracle. All rights reserved.

Designing J2EE Applications


When outlining applications, design analysts must examine the business problems that an
application should solve. This leads to use case analysis, which is the act of outlining each
of the business processes for a desired application, and deciding how these processes will
interact with each other. The designer must then decide how to distribute these processes
across multiple tiers. In the case of J2EE, the MVC architecture outlines a best practice for
dividing these processes based on the most suitable J2EE components.

Oracle 10g: Build J2EE Applications 3-11


Flow Diagram: Example

Receive
Customer order Administrator
status

Place
Log in Fill orders
orders

Browse Update
products inventories

Vendor

Copyright © 2005, Oracle. All rights reserved.

Flow Diagram: Example


The slide above shows a sample flow diagram for the following business scenario:
An office supply store wants to sell its products to customers on the Internet. Customers
access a Web site that provides an interface for purchasing office products. Customers can
also track their orders. The interface sends orders to the fulfillment center, and updates the
inventories accordingly. Before a purchase, the application displays the order items,
quantities, and pricing for each item, along with the total cost. Because customers are
businesses, they must log in to the application to ensure that proper discounts are applied to
their orders.
Though most tasks are handled automatically, administrators access another interface for
performing managerial tasks in the application, such as updating inventories. There are eight
warehouses in different parts of the world, and one vendor in Sydney who is external to your
company. This vendor should be provided access to the application to update the
inventories.

Oracle 10g: Build J2EE Applications 3-12


Summary

In this lesson, you should have learned how to:


• Consider generally accepted patterns when
designing J2EE applications
• Identify the model, the view, and the controller
components for a J2EE application

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 3-13


Practice 3-1: Overview

This practice covers using J2EE design patterns and


the MVC architecture to identify components for a
proposed application.

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 3-14


Practice 3-1
In this practice, you identify the MVC components for a sample application by using the
design patterns and architectures that are discussed in this lesson.
Using the sample flow diagram given in slide 12, decide how the processes are implemented
in the J2EE components. Match each process to its possible implementation:

a. EJB methods that query and update


Log in inventories in various warehouses

Receive
b. An EJB that maintains the orders
order in each customer’s shopping cart
status

Place c. A “front controller” servlet, accessing


the database by using JDBC
orders

Browse d. An EJB that delivers a message


that there is a new order
products

e. A JSP that displays


Fill orders the available items for sale

Update f. A servlet or JSP that accesses the


customer’s outstanding orders
inventories

Oracle 10g: Build J2EE Applications 3-15


Creating the Web Tier: Servlets

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Define the role of servlets in a J2EE application
• Describe the servlet life cycle
• Describe the request and response architecture
• Implement HTTP servlet methods
• List J2EE servlet mapping techniques
• Handle errors in a servlet
• Create and run a servlet in JDeveloper
• Deploy a J2EE application to Oracle Application
Server 10g

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson explains the servlet technology architecture, and discusses the creation of a
servlet in JDeveloper.

Oracle 10g: Build J2EE Applications 4-2


Overview

Requests Connects to

Client Web browser Servlet

Generates

Responds to

Dynamic HTML

Copyright © 2005, Oracle. All rights reserved.

Overview
The basic concepts of servlets are straightforward. A Web browser invokes a URL, which
calls the servlet. The servlet then generates dynamic HTML, Extensible Markup Language
(XML), or other content. The dynamic text may have been generated by connecting to the
database. The following questions arise:
• How can multiple clients be satisfied efficiently?
• How can the programmer’s task be simplified, although the program remains powerful
enough to handle all situations?
This lesson discusses the answers to these questions.

Oracle 10g: Build J2EE Applications 4-3


About Java Servlets

• A servlet is a Java class that implements the


Servlet interface.
• A servlet runs in the context of a special process
called a servlet engine.
• Servlets can be invoked simultaneously by
multiple clients.

Java application, Request


Servlet, JSP, Servlet engine
or HTML Response

Client
Server

Copyright © 2005, Oracle. All rights reserved.

About Java Servlets


A servlet is a Java object that implements the servlet API. These classes are found in the
javax.servlet package. When you use the servlet API, it takes care of some of the
common tasks that are involved in responding to a request from a client. For instance, the
API supports preinstantiating objects in a Java virtual machine (JVM) if multiple clients
must simultaneously access a particular functionality that you provide as a Java class. This
feature is referred to as the servlet life cycle.
Just as applets run in the context of a Web browser, a servlet runs in the context of a servlet
engine. The Web browser and the servlet engine contain a JVM that is usually functional all
the time. Unlike an applet, a servlet does not use any user interface features of the Java
language, such as the classes in the java.swing package.
As shown in the slide, a multitude of clients can invoke a servlet and can use different
protocols. For example, it is possible to write a servlet that implements the FTP server
protocol.

Oracle 10g: Build J2EE Applications 4-4


Principal Features of Servlets

• Concurrent requests are possible and common.


• Servlet methods are run in threads.
• Servlet instances are shared by multiple client
requests.

Request 1

Request 2

Request 3
Clients Server

Copyright © 2005, Oracle. All rights reserved.

Principal Features of Servlets


This slide shows the main features of a servlet. Two or more requests for the same servlet
are run in multiple threads. This means that you should develop the servlet to be thread-safe.
Similarly, when there are no more requests for a servlet, the instance is not extinguished.
Instead, in anticipation of future requests, the memory and other resources are reused when
necessary.

Oracle 10g: Build J2EE Applications 4-5


Life Cycle of Servlets

• All actions are carried out inside the server.


• After initial setup, the response time is less.

1 2 3

Load Initialize Execute


init() service()

4
Destroy
destroy()

Copyright © 2005, Oracle. All rights reserved.

Servlet Life Cycle


The life cycle of a servlet has the following characteristics:
• Many servlet engines execute within a single Java virtual machine. Additionally, with
Oracle Application Server 10g, you can use multiple Java virtual machines.
• Servlets persist between requests as object instances. If an object instance makes a
connection to a database, then there is no need to make another connection for the
second request. Threads also persist as in any Java program, unless they die in the
natural thread life cycle.
• You can override the init() method, which is invoked by the servlet engine before
the servicing of client requests, and the destroy() method, which is invoked after
the engine removes the servlet.
• A servlet can also be explicitly written in a single-threaded model. In this case, if two
requests are received at the same time, the servlet engine uses another instance. This is
discussed in detail in a later lesson.

Oracle 10g: Build J2EE Applications 4-6


HTTP Servlets

• HTTP servlets extend the HttpServlet class,


which implements the Servlet interface.
• A client makes an HTTP request, which includes a
method type that:
– Can be either a GET or POST method type
– Determines what type of action the servlet will
perform
• The servlet processes the request and sends back
a status code and a response.
Request

Response
Client HTTP protocol Servlet

Copyright © 2005, Oracle. All rights reserved.

HTTP Servlets
HTTP servlets extend the javax.servlet.http.HttpServlet class, which extends
the GenericServlet class. The GenericServlet class implements the Servlet
interface. These servlets provide more features than just providing fast responses to clients.
For instance, the GET parameters that are passed through a Web browser to a Web server are
available to the user of the servlet API. Similarly, data submitted by means of a form is sent
to the servlet by using the doPost() method.

Oracle 10g: Build J2EE Applications 4-7


Inside an HTTP Servlet

• The servlet overrides the doGet() or the


doPost() method of the HttpServlet class.
• The servlet engine calls the service() method,
which in turn calls one of the appropriate doXxx()
methods.
• These methods take two arguments as input:
– HttpServletRequest
– HttpServletResponse
HttpServlet subclass
doGet()
Request
Browser service()
Response

Copyright © 2005, Oracle. All rights reserved.

Inside an HTTP Servlet


When an HTTP servlet is invoked, the servlet engine calls the service() method in your
servlet. This is possible because you have implemented the Servlet interface. If the Web
browser has invoked the GET method in the HTTP protocol, then the service() method
invokes the doGet() method in your object. Therefore, it makes sense to override this
method, which has two parameters as input. Similarly, if the browser invokes the POST
method in the HTTP protocol (for example, when the user submits an HTML form), the
service() method invokes the doPost() method. Sometimes, the functionality that
you want is the same; you often see servlets in which doPost() calls doGet(). Many
examples mention only doGet(), even though the concept is equally applicable for the
doPost() method.
The servlet engine provides the Web browser input to your doGet() method and,
therefore, you do not have to worry about the difference between the two HTTP protocol
methods. This is another advantage of using the servlet API.
Note that other methods are available in servlets, such as doPut() and doDelete(), for
FTP operations.

Oracle 10g: Build J2EE Applications 4-8


Servlet: Example

import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;
public class SimplestServlet extends
HttpServlet
{
public void doGet(HttpServletRequest
request, HttpServletResponse response) throws
ServletException, IOException
{
PrintWriter out = response.getWriter();
out.println("Hello World");
}
}

Copyright © 2005, Oracle. All rights reserved.

Servlet: Example
The code in the slide shows the simplest form of a servlet. This servlet prints the plain text
“Hello World” when invoked.

Oracle 10g: Build J2EE Applications 4-9


The doGet() Method

• The most common HTTP request method type


made to a Web server is GET.
• The service() method in your servlet invokes
the doGet() method. The service() method is
invoked on your behalf by the Web server and the
servlet engine.
• The doGet() method receives two parameters as
input:
– HttpServletRequest
– HttpServletResponse
• Pass parameters by appending them to the URL
http://www.oracle.com/servlet?param1=value1

Copyright © 2005, Oracle. All rights reserved.

The doGet() Method


The doGet() method, which receives two parameters as input, is usually the first method
that you must modify from the JDeveloper-generated stubs. This slide reviews the
doGet() method. Request parameters are passed to the doGet() method by appending
them to the URL, for instance:
http://www.oracle.com/servlet?param1=value1. Multiple parameters can
be accessed by using the following:
http://www.oracle.com/servlet?param1=value1&param2=value2.
Additionally, a helper class, java.net.URLEncoder, exists for encoding the parameters
that are passed in the URL. The encode(String s, String enc) method of this
class converts a string “s” using the character encoding “enc” and returns the converted
string. This is helpful for passing parameters that include special characters.
GET requests are generated by a browser in the following instances: when a user enters a
URL in the address line; when a user follows an HREF link from another page; when a user
submits an HTML form that does not specify a method; when the method is specified as
GET: <FORM METHOD="GET">.

Oracle 10g: Build J2EE Applications 4-10


The doPost() Method

• The doPost() method can be invoked on a servlet


from an HTML form via the following:
<form method="post" action=…>
• The service() method in your servlet invokes
the doPost() method. The service() method is
invoked by the Web server and the servlet engine.
• The doPost() method receives two parameters as
input:
– HttpServletRequest
– HttpServletResponse
• Pass parameters using the form field names
<input type="text" name="param1">

Copyright © 2005, Oracle. All rights reserved.

The doPost() Method


The doPost() method is used in conjunction with an HTML form. When the user clicks
“Submit,” any specified parameters are passed to the servlet that is specified in the action
tag. Like the doGet() method, the doPost() receives two parameters as input,
HttpServletRequest and HttpServletResponse. Parameter name–value pairs
are passed to the Web server in an additional HTTP request header (discussed later in this
course), and not by appending them to the URL. Therefore, the advantages of using POST
include the following:
• Parameters (like passwords) are not visible in the browser’s URL field.
• You cannot bookmark a URL containing the parameter values.
• Web servers usually limit the amount of characters that can be passed in the URL (2–4
kilobytes), but there is no theoretical limit to the size of POST parameters.

Oracle 10g: Build J2EE Applications 4-11


The HttpServletRequest Object

• The HttpServletRequest object encapsulates


the following information about the client:
– Servlet parameter names and values
– The remote host name that made the request
– The server name that received the request
– Input stream data
• You invoke one of several methods to access the
information:
– getParameter(String name)
– getRemoteHost()
– getServerName()

Copyright © 2005, Oracle. All rights reserved.

The HttpServletRequest Object


The doGet() and doPost() methods take the HttpServletRequest object as a
parameter. The following table describes several methods in the HttpServletRequest
object and their purposes, based on the example URL:
http://bighost:80/finance/servlet/Ledger/June?region=east

Request methods Return values


getServerName() bighost
getServerPort() 80
getPathInfo() /finance/servlet/Ledger/June.class
getServletPath() /servlet/Ledger.June
getContextPath() /finance
getRequestURI() /finance/servlet/Ledger.June

Oracle 10g: Build J2EE Applications 4-12


The HttpServletResponse Object

• The HttpServletResponse object encapsulates


information that the servlet has generated:
– The content length of the reply
– The MIME type of the reply
– The output stream
• You invoke one of several methods to produce the
information:
– setContentLength(int length)
– setContentType(String type)
– getWriter()

Copyright © 2005, Oracle. All rights reserved.

The HttpServletResponse Object


The second parameter for the doGet() and doPost() methods is the
HttpServletResponse object. The first bullet describes that an HTTP response
consists of a status line (whether or not the call to the servlet was successful), one or more
headers (the content type and optional content length), and the actual output, in that order.
The following table describes several methods that are available in the
HttpServletResponse object and their purposes:

setContentType() Sets the Content-Type header for the document. Must be


used for servlets that return document content. Common settings
include text/html, application/pdf, and image/gif.

setContentLength() An optional method that sets the Content-Length header,


useful for persistent HTTP connections

sendRedirect() Sets the Location header and sets the status code to 302.
Status codes are discussed in detail later in the course.

Oracle 10g: Build J2EE Applications 4-13


Methods for Invoking Servlets

• Invoke servlets from a client by:


– Typing the servlet URL in a browser
– Embedding the servlet URL in an HTML or a
JavaServer Page (JSP) page, or another servlet (an
href link)
– Submitting a form to the servlet (via the action tag)
– Using URL classes in client Java applications
• Invoke servlets inside the J2EE container by
defining a chain of servlets or JSPs.

Copyright © 2005, Oracle. All rights reserved.

Methods for Invoking Servlets


You can use the following methods to invoke a servlet:
• You can directly type the URL in a browser.
• Any HTML page can contain a servlet URL by using either the <a href=> or the
<FORM action=> tag.
• JSPs provide yet another way of invoking a servlet. The JSP can have Java code
directly embedded in it. JSPs are covered in depth later in this course.
• A servlet can be invoked by another servlet through chaining. A servlet chain is a
sequence of servlets in which the output of a servlet is sent to the next servlet in the
chain. The last servlet produces the actual output that is seen by the Web browser. A
servlet chain has the same advantages that the pipe command has in an operating
system. Any number of servlets can be chained together. Additionally, servlet filters
can intercept the request and pass the output to the next filter or servlet in the filter
chain. Servlet filters are covered in detail later in the course.

Oracle 10g: Build J2EE Applications 4-14


Your First Servlet

import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;
public class HelloWorld extends HttpServlet {
public void doGet(
HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException{
response.setContentType ("text/html");
PrintWriter out = response.getWriter();
out.println ("<html>");
out.println ("<body>");
out.println ("Hello World!");
out.println ("</body></html>");
}
}

Copyright © 2005, Oracle. All rights reserved.

Your First Servlet


The example in this slide shows the content of a typical doGet() method. The code:
• Sets the MIME type of the resulting output to text/html
• Obtains a reference to the PrintWriter object
• Writes a series of HTML texts to this object
When the resulting HTML text is received by the browser, it displays the "Hello
World!" string.
The slide also shows that the HttpServletRequest and HttpServletResponse
objects, for example, are derived from the javax.servlet.http package.

Oracle 10g: Build J2EE Applications 4-15


Handling Input: The Form

You can use an HTML form and the doPost() method


to modify the HelloWorld servlet.
<html><body>
<form method="post" action="newhelloworld">
Please enter your name. Thank you.
<input type="text" name="firstName"> <P>
<input type="submit" value="Submit">
</form>
</body>
</html>

Copyright © 2005, Oracle. All rights reserved.

Handling Input: The Form


The previous example did not use the HttpServletRequest parameter, although it was
passed as an argument. In this slide, an HTML form is used, which passes the input to the
Web server. Your task is to process this input. The HTML output is shown below.

Oracle 10g: Build J2EE Applications 4-16


Handling Input: The Servlet

public class NewHelloWorld extends HttpServlet {


public void doPost(
HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException{
res.setContentType("text/html");
PrintWriter out = res.getWriter();
out.println ("<html><body>");
String name = req.getParameter("firstName");
if ((name != null) && (name.length() > 0))
out.println ("Hello: " + name +
" How are you?");
else
out.println ("Hello Anonymous!");
out.println ("</body></html>");
}}

Copyright © 2005, Oracle. All rights reserved.

Handling Input: The Servlet


The previous slide shows an HTML form that passes some input. This slide shows how you
can process the input. Note that the content type, res.setContentType("text/html"),
is set before submitting the document. In the above example, getParameter() is used to
retrieve the case-sensitive firstName parameter as a string from the HTML form. If no
value is found, an empty string is returned, and null is returned if there is no parameter by
that name. getParameter() is used in the same way for GET and POST requests.
Additionally, getParameterValues() can be used to return an array of strings if the
parameter can have more than one value.
What would happen if we ran this servlet directly and not via the previous form?

Oracle 10g: Build J2EE Applications 4-17


Initialization and Destruction

Servlets also define the init() and destroy()


methods in addition to the service() method.
• init():
– Can be used to retrieve initialization parameters
– Takes a ServletConfig object as a parameter
– Is invoked when the servlet instance is created
– Is useful for obtaining database connections from a
connection pool
• destroy():
– Takes no arguments
– Is invoked when the servlet is about to be unloaded
– Is useful for releasing resources

Copyright © 2005, Oracle. All rights reserved.

Initialization and Destruction


The ServletConfig object of init() can be used to find the initialization parameters
that are associated with the servlet. It uses the getInitParameter() method to retrieve
the name of the initialization parameter. Note that you must call super.init() in the
init() method if you use the ServletConfig object, because the ServletConfig
object can be used elsewhere in the servlet. For instance,
public void init(ServletConfig config) throws
ServletException
{ super.init(config);
... // your initialization here }
In a J2EE Web application, an initialization parameter is defined in the web.xml file as
follows:
<init-param>
<param-name>message</param-name>
<param-value>Hello From Init Parameter</param-value>
</init-param>

Oracle 10g: Build J2EE Applications 4-18


Error Handling

• ServletException:
– Is generated to indicate a generic servlet problem
– Is subclassed by UnavailableException to
indicate that a servlet is unavailable, either
temporarily or permanently
– Is handled by the servlet engine in implementation-
dependent ways
• IOException: Is generated if there is an input or
output error while processing the request

Copyright © 2005, Oracle. All rights reserved.

Error Handling
The doXxx() methods throw both the ServletException and the IOException.
The init() method throws the ServletEception. These exceptions contain the same
constructors as the Exception class. Generally, an IOException is returned only when
there is some kind of stream operation on the servlet (in the case of working with applets, for
example). ServletException is returned if the servlet cannot be reached. For
additional exceptions, an error page can be set for error codes in the <web-app> element
of web.xml, as follows:
<error-page>
<exception-type> java.lang.NumberFormatException
</exception-type>
<location>MyExceptionServlet</location>
</error-page>

Oracle 10g: Build J2EE Applications 4-19


Debugging a Servlet

Servlets can be debugged in the following ways:


• Setting breakpoints and using the debugger in
JDeveloper
• Viewing the source of the generated HTML

Copyright © 2005, Oracle. All rights reserved.

Debugging a Servlet
Servlets can be debugged in JDeveloper by setting breakpoints in the code (by clicking the
line number that you want to set) and then by right-clicking the servlet name in the navigator
and selecting Debug in the menu. Additionally, selecting View > Source in the browser
displays the generated HTML of the servlet.
Note that you can also debug servlets or other J2EE components that are running in a
different JVM. The detailed steps to do this are located in the online help of JDeveloper, in
the topic “Remote Debugging.” There is a wizard to create a project that is configured for
remote debugging.
Typically, you perform these tasks:
1. Specify the source directory and any necessary libraries.
2. Copy the jdev-rt run-time libraries to the remote server.
3. Bind the Web sites in the J2EE server configuration files.
4. Run the servlet (with breakpoints set) in the remote server.
5. Start the debugging process in JDeveloper as in the slide above.
6. Begin debugging the servlet.

Oracle 10g: Build J2EE Applications 4-20


SingleThreadModel

• You can implement the SingleThreadModel


interface to prevent multithreaded access of data.
public class HelloWorld extends HttpServlet
implements SingleThreadModel{
public void doGet…
}

• Each concurrent request then has its own


dedicated servlet instance, which is randomly
assigned.

Copyright © 2005, Oracle. All rights reserved.

SingleThreadModel
Normally, the servlet engine creates a new thread for each request. If the servlet implements
the SingleThreadModel interface, then there will never be more than one request
accessing a single instance of the servlet. In this case, the developer need not synchronize
access to fields and other shared data, such as instance variables. The
SingleThreadModel interface is a solution for low-volume servlets that handle
unsynchronized data and cannot be accessed simultaneously by requests, such as when
creating a userID.

Oracle 10g: Build J2EE Applications 4-21


SingleThreadModel (continued)
The following table describes types of variables and attributes and whether they are thread
safe:

Variable/Attribute Thread Safe?


Local variables Thread safe
Instance variables Not thread safe, because a single servlet instance may be
servicing multiple requests at any given time
Class variables Not thread safe, because multiple servlets and requests may
try to access a class variable concurrently
Request attributes Thread safe, because the request object is a local variable
Session attributes Not thread safe, because sessions are scoped at web app
level
Context attributes Not thread safe, because the same context object can be
accessed concurrently

Oracle 10g: Build J2EE Applications 4-22


JDeveloper Environment

The Servlet Wizard in JDeveloper makes it easy for you


to write servlets. The wizard:
• Provides the doGet() and doPost() method
skeletons
• Provides an environment for running the servlet
within the integrated development environment
(IDE)
• Dynamically creates the web.xml file for running
the servlet from the IDE
• Allows the creation of a deployment file that aids
in deploying to an OC4J server

Copyright © 2005, Oracle. All rights reserved.

JDeveloper Environment
The Servlet Wizard in JDeveloper gives you an easy way to start your servlet development.
It also creates an environment for running and debugging your servlet.

Oracle 10g: Build J2EE Applications 4-23


Servlet Mapping

• Mapping a servlet refers to how a client can


access a servlet.
• You can map a servlet:
– To any URL that begins with a certain directory
name
– By using the direct URL:
http://host:port/<context-
root>/servlet/<package>.<servlet>
– By using the mapped URL:
http://host:port/<context-
root>/servlet/<mappedservletname>
• <context-root> is the mapping for the Web module

Copyright © 2005, Oracle. All rights reserved.

Servlet Mapping
The example servlet shown earlier shows how JDeveloper invokes a servlet. Servlet
mapping refers to the process by which a servlet is invoked. This is application server–
dependent, but in general you can map a servlet:
• To any URL that begins with a certain directory name. In this case, all class files under
the directory are treated as servlets.
• By using the direct or mapped URLs:
http://host:port/<context-root>/servlet/<package>.<servlet>
http://host:port/<context-root>/servlet/<mappedservletname>
where host is the host name or IP address of the server machine, and port is the
port number of the server (for example, Apache’s default port is 80; OC4J’s default
port is 8888)
The context root is the mapping for the J2EE Web module. This is created by default in
JDeveloper as: <Workspacename>-<ProjectName>-context-root and can be changed
in the http-web-site.xml configuration file.

Oracle 10g: Build J2EE Applications 4-24


Servlet Mapping in JDeveloper

JDeveloper provides the standard J2EE model for


mapping servlets by using the web.xml file:
<?xml version = '1.0' encoding = 'UTF-8'?>
<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web
Application 2.2//EN" "http://java.sun.com/j2ee/dtds/web-app_2_2.dtd">
<web-app>
<servlet>
<servlet-name>MyFirstServlet</servlet-name>
<servlet-class>package1.HelloWorld</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>MyFirstServlet</servlet-name>
<url-pattern>/helloworld</url-pattern>
</servlet-mapping>

</web-app>

Copyright © 2005, Oracle. All rights reserved.

Servlet Mapping in JDeveloper


The web.xml file is primarily used to map a servlet to a virtual directory and name it. This
standard J2EE file is created automatically when a servlet is created in JDeveloper, and the
appropriate XML tags are included in the file. To modify the file, right-click the web.xml
file and choose Properties from the context menu. In the above example, the servlet named
HelloWorld.class is mapped to a virtual directory of /helloworld. Therefore, this
servlet can be accessed with either of the following URLs:
• http://localhost:8989/<context-
root>/servlet/package1.HelloWorld
• http://localhost:8989/<context-root>/helloworld
The virtual directory of /servlet comes from the J2EE Web server configuration. It is
included automatically when running a servlet that is mapped in the web.xml file. Note
that in OC4J, this mapping is set in the global-web-application.xml file.

Oracle 10g: Build J2EE Applications 4-25


Invoking a Servlet

Copyright © 2005, Oracle. All rights reserved.

Invoking a Servlet
This slide shows an example of how a servlet can be invoked in JDeveloper. When the
servlet is run, the J2EE server installed with JDeveloper is started, the mapping is retrieved
from the web.xml file, and the resulting servlet is displayed from the default browser.
Note: The context root of this application is demos-lesson04-context-root.

Oracle 10g: Build J2EE Applications 4-26


Specifying J2EE Web Module Settings

Copyright © 2005, Oracle. All rights reserved.

Specifying J2EE Web Module Settings


The slide shows the J2EE Web module settings for a project in JDeveloper. This is accessed
by right-clicking the project and selecting “Project Properties.” The slide shows the default
settings for the lesson04 project in the demos workspace, and can be changed as
necessary.

Oracle 10g: Build J2EE Applications 4-27


Creating a Connection to Oracle
Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Creating a Connection to Oracle Application Server 10g


As stated previously, you can use several methods for deploying an application to Oracle
Application Server 10g. To deploy from JDeveloper, it is necessary to create a connection to
the server.
Select New > Connections > Application Server Connection, and give the connection a
name, as shown in the slide above. Select the type of connection (a local Oracle Application
Server 10g instance in this case), and then the location of ORACLE_HOME for that server.
You can now deploy an application directly from JDeveloper to Oracle Application
Server 10g.

Oracle 10g: Build J2EE Applications 4-28


Deploying to OC4J

Copyright © 2005, Oracle. All rights reserved.

Deploying to OC4J
After the connection is created, deploying to OC4J is simple. Right-click the deployment
profile and select Deploy to <yourappserverconnection>.
Note: If you use Oracle Enterprise Manager to deploy an application, then you can still use
the deployment profile to create the application WAR or EAR file.

Oracle 10g: Build J2EE Applications 4-29


Summary

In this lesson, you should have learned how to:


• Describe the servlet life cycle
• Develop and run a servlet in JDeveloper
• Map a servlet in a J2EE server
• Collect information from a client
• Respond to the client
• Handle errors in a servlet
• Deploy a servlet to Oracle Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 4-30


Practices 4-1, 4-2, and 4-3: Overview

These practices cover the following topics:


• Creating a servlet that invokes the doPost()
method and running it from an HTML form
• Creating a servlet that invokes the doGet()
method to create an HTML form
• Deploying a servlet to Oracle Application
Server 10g

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 4-31


Practice 4-1
The purpose of this practice is to create the login form for the J2EE application that you are
developing. You create and run an HTML form and an HTTP servlet. Run JDeveloper by
using the desktop shortcut. Open the practice04 workspace in the practice04 folder
and navigate to the login project.
1. Modify an HTML form for logging in to an application.
a. Expand the login project and the Web Content folder. Open the
login.html file in the code editor by double-clicking the file.
b. There are two text areas in this form (you can switch between the visual and code
views using the “Design” and “Source” tabs) . The text areas have labels but no
names. Complete the <input type="text" name=""> code to include a
name for both the text areas. These are the values that you pass to the request
object and, therefore, it is important to follow standard naming conventions so
that you can refer to the value later. You can perform this step by using the code
editor, or by selecting the text item box in the visual editor and modifying the
name property in the property inspector.
c. Modify the form so that the action tag points to firstservlet. You create
the servlet in the next step.
d. Optionally, modify the form’s layout. Add a style sheet by selecting CSS from
the component palette dropdown list and then dragging a style sheet to the
.html file.
e. Save the login.html file.
2. Create a new HTTP servlet.
a. With the login project selected, Select File > New from the menu. Select the
Web Tier > Servlets category and then the HTTP Servlet item and click OK.
b. Click Next to dismiss the first page of the wizard.
c. Ensure that the package name is login and name the class FirstServlet.
d. Because you are sending a POST action from the form, select the doPost()
method in the Servlet Wizard, in addition to doGet(). This ensures that the
doPost() skeleton code is generated. Click Next.
e. Click Next to leave the servlet parameters empty for now.
f. The last step in creating a servlet is the mapping details. Select the check box to
specify a name for the servlet, and accept the default values.
g. Click Finish. You have created FirstServlet.java, a servlet with skeleton
code for the doGet() and doPost() methods.
h. Open the web.xml file in the code editor. Note that login.FirstServlet
is mapped to “/firstservlet”.
3. Modify the HTTP servlet to handle the login.
a. Add code to the doPost() method to retrieve the “Customer Name” parameter
from the request object. Remember that the value being passed is the
parameter that you specified in step 1.b, not “Customer Name.” Remove the
out.println statement containing "The servlet has received a POST…"

Oracle 10g: Build J2EE Applications 4-32


Practice 4-1 (continued)
b. Add code to the doPost() method to greet the customer by using his or her
name in the greeting. If the customer does not enter a name, the name is an
empty string. In this case, greet an anonymous user.
Hint: Use the skeleton code that is provided as a template, to properly format
your document by ensuring that the appropriate HTML tags are used.
c. Right-click FirstServlet.java and select Make to compile the class.
4. Run login.html to test the functionality.
a. Right-click login.html and select Run.
b. Enter any name (ignore the Customer Id field), and click Login.
c. The name that you enter should be welcomed by the doPost() method of the
servlet.

Oracle 10g: Build J2EE Applications 4-33


Practice 4-2
In this practice, you use the doGet() method to combine the login process completed in
Practice 4-1 into a single servlet. The servlet creates the login form and runs initially, rather
than login.html.
1. Create a servlet to handle the login process.
a. In the login project, create a new servlet as in step 2 of practice 4-1.
b. Select login as the package name and name the class LoginServlet.
c. Select the doGet() and doPost() methods in the Servlet Wizard. This
ensures that the skeleton codes of both the methods are generated as in
Practice 4-1.
d. Click Next to leave the servlet parameters empty.
e. This servlet contains an HTML form that references the doPost() method. As
before, the URL pattern for this servlet matches the virtual path in the action
tag of the doGet() method. Create a mapping for this servlet as
/loginservlet.
f. Click Finish and you have created LoginServlet.java, with skeleton code
for the doGet() and doPost() methods.
2. Modify the doPost() method.
a. Copy the doPost() method from FirstServlet.java and paste it into
the doPost() method of LoginServlet.java. This ensures that the login
process remains the same, whereas the URL being called to log in changes.
b. Right-click inside the code editor and select Make to compile
LoginServlet.java.
3. Modify the doGet() method to create the form that is used in login.html.
a. Create a variable to store the servlet’s Uniform Resource Identifier (URI) from
the request.getRequestURI() method.
b. Copy the contents of login.html and paste into the doGet() method of
LoginServlet.java, just below the line PrintWriter
out=response.getWriter();. Remove the out.println statement
containing "The servlet has received a GET…"
c. Modify the HTML code so that it is wrapped in out.println statements. This
also involves eliminating quotes from the HTML and adding escape characters
where necessary. Specify the variable you created in step 3a for the value of the
action tag. For example, the first four lines of the statements should be:
out.println("<html>");
out.println("<head><title>Login to Order
Entry</title>");
out.println("<link rel=stylesheet
href=\"css/oracle.css\" media=\"screen\"/></head>");
out.println("<body>" + "<form method=\"post\" " +
"action=" + <yourservleturivariable> + ">"
d. Continue to concatenate statements and eliminate extraneous quotes until the
HTML is formatted properly in the servlet.

Oracle 10g: Build J2EE Applications 4-34


Practice 4-2 (continued)
4. Run LoginServlet.java to test the functionality.
a. Right-click LoginServlet.java and select Run.
b. Enter a name (ignore the Customer Id field), and click Login.
c. The name that you enter should be welcomed by the doPost() method of the
servlet.

Oracle 10g: Build J2EE Applications 4-35


Practice 4-3
In this practice, you deploy the application that you built in the previous practices.
1. First, create a connection to your Oracle Application Server 10g instance.
a. Click the Connections tab in the Application Navigator. Right-click Application
Server and select New Application Server Connection.
b. Name the connection OracleAS10g and specify Oracle Application Server 10g
as the connection type. Click Next.
c. Provide welcome1 as the password for the ias_admin user and click Next.
d. Accept the default host name and port and specify the ORACLE_HOME directory
for the Oracle Application Server 10g install, E:\oraas10g, and click Next.
e. Click Next and in the following page, click Test Connection. When the status
message indicates success, click Finish.
2. Create a deployment profile for the application.
a. Right-click the login project and select New.
b. Select Deployment Profiles within the General category and create a WAR file
deployment profile for this project.
c. Name the deployment profile login and click OK.
d. Specify the J2EE Web Context Root as /practice04, accept all other default
settings, and click OK.
3. Deploy the application.
a. Right-click the deployment profile and deploy to the OracleAS10g connection
that you created in step 1.
b. When you see the text “Deployment Finished” in the message window, the
application is deployed.
c. Access the application by using the following URL:
http://localhost/practice04/loginservlet
d. Navigate to E:\oraas10g \j2ee\home\config and view the contents of
default-web-site.xml in WordPad. This is where the application that you
deployed is specified.

Oracle 10g: Build J2EE Applications 4-36


Accessing the Database with Servlets

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Load and register a JDBC driver
• Connect to an Oracle database by using data
sources
• Navigate in a ResultSet
• Use PreparedStatement
• Create a pool of connections

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson focuses on accessing the database by using Java Database Connectivity (JDBC)
from a servlet. This method is recommended when J2EE applications do not use EJBs or
when the functionality of the servlet is not complex. Note that JSPs can also access a
database in a similar manner to that of servlets. JSPs are discussed later in the course.

Oracle 10g: Build J2EE Applications 5-2


Review of JDBC

• JDBC is a standard interface for connecting to


relational databases from Java.
• The JDBC classes and interfaces are in the
java.sql package.

Copyright © 2005, Oracle. All rights reserved.

Review of JDBC
The java.sql package contains a set of interfaces that specify the JDBC API. This
package is a core part of Java and is supported by JDeveloper. Database vendors implement
these interfaces in different ways, but the JDBC API itself is standard. Oracle provides four
drivers: a thin-client driver, an Oracle Call Interface driver for the middle tier, a Java
Transaction Service–enabled driver for applications that span multiple databases, and a
server-based driver in the Oracle database.
By using JDBC, you can write code that:
• Connects to one or more data servers
• Obtains metadata from the data server
• Executes any SQL statement
• Obtains a ResultSet object so that you can navigate through query results

Oracle 10g: Build J2EE Applications 5-3


Querying in JDBC

import java.sql.*;
Connect DriverManager.registerDriver(…)
Connection conn =
DriverManager.getConnection(
"jdbc:oracle:thin …
Query Statement stmt =
conn.createStatement ();
ResultSet rset =
stmt.executeQuery (
Process results "select * from EMPLOYEES");
while (rset.next ())
System.out.println(
rset.getString (2));
Close rset.close();
stmt.close();
conn.close();

Copyright © 2005, Oracle. All rights reserved.

Querying a Database with JDBC


The slide shows the four main steps in querying a database with JDBC.
1. JDBC drivers must register themselves with the driver manager. Use the
registerDriver() method of the DriverManager class. A Connection
object is obtained by using the getConnection() method as shown. You must
pass the username and the password to authenticate yourself, and you must also pass
the JDBC URL that dictates the type of JDBC driver that you are using.
2. A Statement object is obtained only after you have a Connection object, after
which you can invoke the executeQuery() method for SELECT statements or the
executeUpdate() method for INSERT, UPDATE, DELETE, and DDL statements.
JDBC also provides the PreparedStatement object for precompiled SQL
statements. When you declare a Statement object and initialize it by using the
createStatement() method, you implement the Statement interface that is
supplied by the driver you are using.
3. The slide shows an executeQuery() method on the Statement object, which
returns a ResultSet containing the results of your query. A ResultSet maintains
a cursor pointing to its current row of data. Use next() to step through the
ResultSet row by row, and use getString(), getInt(), and other methods,
to assign each value to a Java variable.
4. The Result Set, Statement, and Connection should then be closed.
Oracle 10g: Build J2EE Applications 5-4
JDBC and Servlets

• There are three ways to use JDBC in a servlet:


– Register the JDBC driver within the servlet by hard
coding the driver name in either the servlet or in a
properties file.
– Use the JDBC driver from the data-sources.xml
file that is provided with Oracle Application
Server 10g.
– Use a properties file to store connection details.
• In all cases, optimize the connection:
– Initialize the database connection in the servlet’s
init() method (or retrieve from a pool).
– Close the database connection in the destroy()
method (or return to a pool).

Copyright © 2005, Oracle. All rights reserved.

JDBC and Servlets


When you use JDBC, you can establish connections in the init() method of the servlet.
Therefore, when you start a Web server, it already has a connection to a database, enabling
fast database access.
Closing Connection and ResultSet Objects
ResultSet objects that were obtained from the execution of a query are automatically
closed if they were not previously explicitly closed. Explicitly close a ResultSet by
calling close() after you have finished using it.
Closing a connection involves calling the close() method of the Connection object
that represents the database connection that you would like to close.

Oracle 10g: Build J2EE Applications 5-5


Synchronizing Shared Resources

• Reuse PreparedStatement objects.


• Sharing Statement objects may not be
thread safe.
• Use a synchronized block.
PreparedStatement ps = …

synchronized (ps) {
ps.clearParameters();
ps.setInt(1,3);
ps.setDouble(2, 3.14);
ps.executeUpdate();
}

Copyright © 2005, Oracle. All rights reserved.

Synchronizing Shared Resources


You can use the PreparedStatement class to improve performance of the statement by
embodying the PreparedStatement objects as local variables in the doGet() method
of your servlet. However, all instance variables are available for multiple requests,
potentially causing conflicts. The PreparedStatement objects consist of several
method invocations (unlike normal Statement objects). Therefore, you must place these
invocations in a synchronized block, as shown in the slide. You should close a
Statement or PreparedStatement object when you are done using it.
Note that Oracle Application Server 10g Containers for J2EE (OC4J) supports statement
caching, where the same statement does not have to be parsed each time servlet executes it
on behalf of different users. To use statement caching, use the PreparedStatement or
CallableStatement objects.

Oracle 10g: Build J2EE Applications 5-6


Transaction Handling

Initialize Connection in the servlet’s init() method.


• Problems with transactions:
– The Connection object in the servlet’s init()
method is shared.
– The commit() method depends on the Connection
object.
• Solutions for transactions:
– Create a new Connection object.
– Use the synchronized keyword.
– Use the SingleThreadModel interface.
– Use session tracking.

Copyright © 2005, Oracle. All rights reserved.

Transaction Handling
If your application has transactional elements, such as committed updates, then the strategy
of having a preestablished connection to a database is a problem. This is because the handle
to this Connection object is available to multiple threads corresponding to multiple client
invocations. The slide shows four possible solutions.
• Create a new Connection object every time a servlet is invoked, and close the
connection every time. In general, this solution is acceptable only in a few cases, such
as in debugging situations. Connection Pooling for this option is discussed later in this
lesson.
• Create a Connection object in the init() method, but serialize the use of this
object by using the synchronized keyword. If there are few concurrent client
accesses to the Web server, then this may be an acceptable solution.
• Implement the SingleThreadModel interface. When a servlet implements this
interface, the servlet engine is alerted not to allow multiple threads for the doGet()
method in this servlet object. If multiple requests are made at the same time to the Web
server, the servlet engine instantiates a new servlet object. The servlet engine is free to
spawn multiple instances beforehand. Therefore, this solution is acceptable if there is
an expected limit to the number of concurrent accesses to this servlet (for example, the
number of students in a class).

Oracle 10g: Build J2EE Applications 5-7


Transaction Handling (continued)
• Use session tracking. Session tracking is covered later in the course. The idea is to
track the identity of the client who is making a request. This solution does not ensure
better performance than the previous solution, but it does ensure accuracy. It also
allows requests to span multiple HTTP requests from the same client. Session tracking
can be used in conjunction with any other solution.
Note: Transactions can also be handled by using transaction services that are available when
using EJBs in OC4J. This is discussed in detail later in the course.

Oracle 10g: Build J2EE Applications 5-8


Connection Pooling

Pooled Connection objects are used and released by


servlet instances. A connection pool performs the
following tasks:
• Preallocates database connections
• Manages available connections
• Allocates new connections
• Closes connections that are no longer in use

Copyright © 2005, Oracle. All rights reserved.

Connection Pooling
The most elegant solution is to implement connection pooling, in which a pool of
(preinstantiated) Connection objects are awarded to different requests. When a client is
finished with the request, it is returned to the connection pool. This solution resembles the
SingleThreadModel solution with prespawned connections, except that the amount of
connection pool objects that are instantiated is dynamic and controlled by a program (which
can be adaptive).
Connection pools have a low-water mark (the minimum number of Connection objects
that must always be present, whether in use or not) and a high-water mark (maximum
number of active connections). They are useful only if connections are created relatively
frequently and released soon after use.

Oracle 10g: Build J2EE Applications 5-9


Data Sources

• Data sources provide logical mappings of


databases:
– Developer uses the logical representation of a
database.
– Deployer maps to the physical data sources.
• J2EE applications use published DataSource
objects by:
– Looking up the published name via Java Naming
and Directory Interface (JNDI).
– Using JDBC Connection methods to connect to the
database.
• Data sources are published in the JNDI tree.
• Data sources come in different varieties.

Copyright © 2005, Oracle. All rights reserved.

What Are Data Sources?


A data source is a Java object that has the properties and methods that are specified by the
javax.sql.DataSource interface. Data sources are factories that return JDBC
connections. J2EE applications use JNDI to look up DataSource objects that can be
bound into an external JNDI namespace. Data sources have been introduced with JDBC 2.0,
and are the preferred way for connecting a J2EE application to a data server, over the earlier
JDBC DriverManager class. Because data sources have logical names, applications that
use them are more portable.

Oracle 10g: Build J2EE Applications 5-10


Data Source Definition

• Global data sources are defined in the


OC4J_HOME/config/data-sources.xml file.
– You specify each data source by using an XML tag.
– Attributes specify values for the data source.
• Application-specific data sources: Use the <data-
sources> tag in the application.xml file.

OC4J_HOME/applications

myapp

application.xml
Points to
data-sources.xml

Copyright © 2005, Oracle. All rights reserved.

Data Source Definition


As stated earlier, data sources are objects that are used for connecting to a database. You can
set up each data source to contain connection information for the database. In addition, you
can create special types of DataSource objects to provide the following functionality:
• Connection pooling: Mapping pools of JDBC connections to the database for
increased scalability
• JTA: Cooperate with Java Transaction API (JTA) to support container-managed
transactions for EJBs
There is one global configuration file (OC4J_HOME/config/data-sources.xml)
that establishes data sources at the OC4J server level. OC4J parses this file when it starts,
instantiates the data source objects, and binds them into the server JNDI namespace. Thus,
as seen in the lesson titled “Creating the Web Tier: Servlets”, if you add a new data source
specification to this file, then you must restart the OC4J server to make the new data source
available for lookup.
Each application also has a separate JNDI namespace. The web.xml and orion-
web.xml files contain entries that can be used in mapping application JNDI names to data
sources. The XML definition for each data source includes a JDBC connection string, and
optionally a database account. After deployment, the application accesses the data sources at
run time through a JNDI lookup.
Oracle 10g: Build J2EE Applications 5-11
data-sources.xml: Example

<data-source
class="com.evermind.sql.DriverManagerDataSource"
connection-driver="oracle.jdbc.driver.OracleDriver"
name="OracleDS"
location="jdbc/OracleCoreDS"
xa-location="jdbc/xa/OracleDS"
ejb-location="jdbc/OracleDS"
min-connections="5"
max-connections="25"
username="oe"
password="oe"
url="jdbc:oracle:thin:@<host>:<port>:<SID>"
/>

Copyright © 2005, Oracle. All rights reserved.

data-sources.xml: Example
In the example, the attributes of the data-source tag are defined as follows:
• class defines the DataSource class that is to be used.
• connection-driver defines the JDBC driver for this data source.
• name is used to identify this data source. The default is the value of location.
• location defines the logical name for the data source. It returns a DataSource
class as specified in the class attribute.
• xa-location is a mandatory attribute if ejb-location is present. This defines
the logical name for the XA-enabled data source.
• ejb-location is the logical name for the entity bean data source. This is the JNDI
name that should be used for looking up data sources for any J2EE component.
• min-connections controls the minimum size of the connection pool. The default
value is zero.
• max-connections controls the maximum size of the connection pool.
• url indicates the JDBC connection URL, and optionally the username and password.
OC4J provides a wrapper for DataSource objects that returns an appropriate
DataSource object for the requested data source location.
Note that the pooled-location tag defines the JNDI location of a pooled-connection
data source.
Oracle 10g: Build J2EE Applications 5-12
Using Data Sources

To use a defined data source in a servlet:


1. Use the lookup method of the
javax.naming.Context class to retrieve the
named data source class.
2. Create the connection.
try {
Context ic = new InitialContext();
DataSource ds =
(DataSource)ic.lookup("jdbc/OracleDS");
Connection conn = ds.getConnection();
} catch (SQLException se) { … }
catch (NamingException ne) {… }

Copyright © 2005, Oracle. All rights reserved.

Using Data Sources


To establish the connection to a named data source in data-sources.xml, use the
Context.lookup() method of the javax.naming package. Next, create the
connection. By using this connection, JDBC code can now be included in the servlet as
usual. If the data source does not provide a username and password, then
ds.getConnection (String user, String pwd) can be used to obtain a
connection.
JDeveloper automatically creates data source references in the data-sources.xml file
based on the database connections you create within the integrated development
environment (IDE). For example, if a connection named “Connection1” is created in
JDeveloper, then the ejb-location attribute is set to “jdbc/Connection1DS”.

Oracle 10g: Build J2EE Applications 5-13


Summary

In this lesson, you should have learned how to:


• Create a servlet to connect to the database by
using JDBC
• Load and register a JDBC driver
• Connect to an Oracle database by using data
sources
• Navigate in a ResultSet
• Use PreparedStatement
• Improve database performance by using
connection pooling

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 5-14


Practice 5-1: Overview

This practice covers the following topics:


• Connecting to the database by using JDBC
• Retrieving database information and formatting it
for output in a servlet

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 5-15


Practice 5-1
The purpose of this practice is to create a servlet that interacts with a database by using
JDBC. The customer number and name provided in LoginServlet.java is validated in
the CUSTOMERS table of the database, and the customer is shown a list of his or her existing
orders. In JDeveloper, open the practice05.jws workspace.
1. Create the connection to use as the data source for the servlet.
a. Select File > New and select Connections from the General category.
b. Select Database connection and click OK.
c. Name the connection oe and specify an Oracle JDBC connection type.
d. The username is orann (as indicated by your instructor) and the password is
oracle. The password should be deployed at run time.
e. Enter the host, port, and SID as indicated by your instructor.
f. Test the connection and click Finish to close the wizard.
g. You are now able to look up this data source reference by using its <ejb-
location> name, jdbc/oeDS.
2. Modify LoginServlet.java to include the new functionality.
a. Double-click the verifylogin project and navigate to the Libraries tab to add
the Oracle JDBC library to your project.
b. Open LoginServlet.java in the verifylogin project.
c. Import the javax.naming (for the resource lookup), javax.sql (for the
DataSource class), java.sql (for the Connection class), and
oracle.jdbc packages to the LoginServlet.
d. Create instance variables for the Connection (as conn), the DataSource
(as ds), and the PreparedStatement (as ps) objects.
e. In a try/catch block of the init() method, use the lookup method of the
Context class to retrieve the data source that you created in step 1.
f. Catch a NamingException if the name is not found.
g. In the try block, initialize the connection object. Catch a SQLException.
h. Also in the try block, create a PreparedStatement object from the
Connection object that is stored in the PreparedStatement object
declared in step 2.d. The query string should select all columns from the
ORDERS table for all orders with the CUSTOMER_ID equal to a bind variable
parameter.
i. Create the destroy() method to close the connection and prepared statement
objects that you created in a try/catch block. Catch a SQLException.
3. Create the functionality to validate the provided name and ID.
a. Create a new synchronized boolean method in the servlet to verify the customer
information. This method accepts the connection, the customer ID, and the
customer name as arguments, and throws a SQLException.
b. Create a method variable to initialize the customer ID.
c. Create an instance of the Statement object.

Oracle 10g: Build J2EE Applications 5-16


Practice 5-1 (continued)
d. Create a variable to store the query for this method. The query should select the
customer_id and cust_last_name from the CUSTOMERS table, where
the customer_id and cust_last_name match those that are provided as
arguments to the method.
e. Use the executeQuery() method of the Statement object that you created
in step d. Assign this value to a ResultSet variable.
f. While iterating through ResultSet, retrieve the customer ID.
g. Close the ResultSet and return true if the customer ID is not null or an
empty string. Otherwise, return false.
4. Create the functionality to query the database for the customer’s existing orders.
a. Create a new synchronized method to get the orders for a customer. This method
accepts the Connection and the customer ID as arguments, and throws a
SQLException.
b. Declare one method variable of type String. Initialize the variable to a string
with a length of zero ("").
c. Use the setString() method of the PreparedStatement object to pass
the value of the method argument to the query statement created in step 2h.
d. Execute the query from the PreparedStatement object, and store the results
in a ResultSet object.
e. By using a while loop, loop through all records in the ResultSet object. As
you iterate through each row, fetch the column values and save them into three
string variables named orderId, orderStatus, and orderTotal.
f. In the while loop, add the following code by replacing
yourStringVariableName with the name that you chose in step b.:
yourStringVariableName += "<tr><td>" + orderId +
"</td><td>" + orderStatus + "</td><td>" + orderTotal +
"</td></tr><p>";
Note that you are appending the variables to the String object that you
declared in the first step, and formatting the data in a table.
g. Close your ResultSet object outside the while loop.
h. Return yourStringVariableName. Note that this represents a string of
HTML output, including a list of all the orders placed by a given customer.

Oracle 10g: Build J2EE Applications 5-17


Practice 5-1 (continued)
5. Modify the doPost() method to call the new methods.
a. Create an instance variable to retrieve the customer ID from the request
object.
b. Delete the if/else block for checking if a customer name was entered.
c. If the return of the method you created in step 4 is true, then include the return
value from the method that you created in step 5, formatted in an HTML table.
Pass the Connection object and customer ID variable to this method. If the
return value is false, then alert the customer that the login is invalid.
d. Catch a SQLException.
6. Compile to test and run the application from LoginServlet.java. Note that not
all customers have current orders in the database. Valid customer IDs and names that
have orders are listed below:

101 Welles
102 Pacino
103 Taylor
104 Sutherland
105 MacGraw
106 Hannah
107 Cruise
108 Mason
109 Cage
116 Martin
117 Edwards
118 Mahoney
119 Hasan
120 Higgins
121 Sen
122 Daltrey
123 Brown

Oracle 10g: Build J2EE Applications 5-18


Using Advanced Techniques in Servlets

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Use a cookie in a servlet
• Send HTTP headers to the client
• Use servlet filters
• Define event listeners

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson discusses additional topics in creating a servlet.

Oracle 10g: Build J2EE Applications 6-2


Overview

Request

getCookies()
getHeader()

Response
Client Web Servlet
setHeader()
browser
addCookie()

Error handling

Copyright © 2005, Oracle. All rights reserved.

Overview
The request and response objects provide methods for sending and retrieving data such as
parameters (as seen in the lesson titled “Creating the Web Tier: Servlets”), cookies for
obtaining state information, and headers for setting status codes and redirecting the user.
This lesson covers the use of these methods, as well as the techniques for handling errors.

Oracle 10g: Build J2EE Applications 6-3


HTTP Headers

• Headers are HTTP details that are passed between


the browser and the server.
• They can be response or request headers.
• The getHeader() method of
HttpServletRequest retrieves the string value of
the header.
• The setHeader() method of
HttpServletResponse sends a header to the
browser.

Copyright © 2005, Oracle. All rights reserved.

HTTP Headers
The HTTP request and response headers manipulate the HTTP connection between the
browser and the server. For example, in the previous lessons, setContentType was used
to set the content type header for the browser. Note that because headers can change the
content of the response, they need to be set before the output is generated.

Oracle 10g: Build J2EE Applications 6-4


Request Headers

Additional request headers include the following:


Accept Specifies MIME types that the browser
supports
Accept- Specifies the browser’s preferred language
Language
Cookie Returns cookies to servers that previously
sent them to the browser
Referer Indicates the URL of the referring Web page,
for tracking users
User-Agent Identifies the browser that is making the
request, for checking browser features

Copyright © 2005, Oracle. All rights reserved.

Request Headers
Retrieving the value of request headers is helpful for designing servlets that cater to browser
preferences. For instance, if a servlet is written to produce content in more than one
language, request.getHeader("Accept-Language") could be used to verify a
standard language code (en-us, da, and so on). Thus, the response could be modified
according to the browser settings, without having to ask the user for a form value or other
parameter. The following is a complete list of request headers:
Accept Accept-Charset Accept-Encoding
Accept-Language Authorization Cache-Control
Connection Content-Length Content-Type
Cookie Expect From
Host If-Match If-Modified-Since
If-None-Match If-Range If-Unmodified-
Since
Pragma Proxy-Authorization Range
Referer(misspelled Upgrade User-Agent
due to HTTP author Via Warning
error)

Oracle 10g: Build J2EE Applications 6-5


Sending a Response

There are three aspects to sending a response:


• Sending HTTP headers
• Sending a status code (an integer denoting the
nature of response)
• Sending multimedia content

Copyright © 2005, Oracle. All rights reserved.

Sending a Response
A servlet must also send data back to the browser. There are three aspects to this, as shown
in this slide. These aspects are explained in detail in the following slides.

Oracle 10g: Build J2EE Applications 6-6


Response Headers

• The HttpServletResponse class is used to send


headers.
• You have seen an example of setting header
information: setContentType("text/html");.
• Other headers are set by using the setHeader()
method.
• Do not confuse HTTP headers with the HEAD tag in
HTML pages.

Copyright © 2005, Oracle. All rights reserved.

Response Headers
The following table shows some standard HTTP response headers. Common headers have
shortcut methods, such as setContentType, setContentLength, addCookie, and
sendRedirect.

Header Usage

Location Specifies a new location of a document, usually used with the


SC_MOVED_TEMPORARILY and
SC_MOVED_PERMANENTLY status codes

Content-Encoding Is used to encode the response body. Example values are x-


gzip and x-compress.

Cache-Control Specifies any special treatment that a caching system should


give to this page. Example values are no-cache and max-
age=(time in seconds).

Oracle 10g: Build J2EE Applications 6-7


Setting Status Codes

• If a servlet does not specify a status code, then


the Web server sends the default status code
(200).
• You can explicitly set a status code by using the
setStatus() method.
Example:
int pageVersion =
Integer.parseInt(req.getParameter("pageVersion"));
if (pageVersion >= currentVersion){
response.setStatus(response.SC_NO_CONTENT);
}else{
//Send original page
}

Copyright © 2005, Oracle. All rights reserved.

Setting Status Codes


The setStatus(int StatusCode) method in the HttpServletResponse object
is used to set status codes. The default code is 200, which the end user never sees.
Paradoxically, a code that the user often sees is the infamous 404 code, “Resource not
found.” Two shortcut methods exist for setStatus: sendError (int code,
String message) and sendRedirect(String URL), which generates a 302
response with a location header for the new URL.
Mnemonic Constant Code Default Meaning
Message
SC_OK 200 OK The client’s request was successful, and
the server’s response contains the
requested data.

SC_NO_CONTENT 204 No Content The client’s request was successful, but


there was no new response data.

SC_MOVED_TEMPORARILY 302 Temporary The requested resource has temporarily


Move moved to another location, but future
references should use the original URL.

Oracle 10g: Build J2EE Applications 6-8


Example

• Assume that the randomSite() method generates


a Web site randomly.
For example, http://www233.oracle.com
• Requests to www.oracle.com can be sent to this
site to provide load balancing.
public void doGet(
HttpServletRequest req,HttpServletResponse res)
throws IOException, ServletException{
String tempSite = this.randomSite();
// implementation not shown
res.setStatus(res.SC_MOVED_TEMPORARILY);
res.setHeader("Location", tempSite);
}

Copyright © 2005, Oracle. All rights reserved.

Example
The slide shows an example of a servlet sending HTTP headers back to the client. For the
purpose of this example, the browser sends a request to www.oracle.com. The servlet
receiving this request dispatches the browser to a new site for the purposes of load
balancing.
The first servlet generates a random site that is capable of serving the same request. In this
example, it is www233.oracle.com.
• It sets the status code to SC_MOVED_TEMPORARILY.
• It supplies the new location by sending the Location HTTP header.

Oracle 10g: Build J2EE Applications 6-9


Sending Multimedia Content

• Multimedia content usually contains binary


response data.
• Use the getOutputStream() method instead of
the getWriter() method if you want to send
binary data, such as images.
• Use the setContentType() method with the
image/gif MIME type to send a GIF-encoded
image.
• Use other MIME types to send other types of
multimedia content.

Copyright © 2005, Oracle. All rights reserved.

Sending Multimedia Content


To build multimedia content, you must create the image window, draw the image, and then
send the image in the specified content type to the output stream. To send the image to the
output stream, use the javax.imagio package and convert a java.awt.Image to a
java.awt.image.BufferedImage, as in the following example:
import javax.servlet.*; import javax.servlet.http.*;
import java.awt.*; import java.awt.image.*;
import java.io.*; import javax.imageio.*;

public class ImageServlet extends HttpServlet {


public void doGet(HttpServletRequest req,HttpServletResponse res)
throws ServletException,IOException
{
res.setContentType("image/jpg");

Oracle 10g: Build J2EE Applications 6-10


Sending Multimedia Content (continued)
OutputStream out=res.getOutputStream();
Frame frame=null;
Graphics g=null;
try
{
//Step 1: Create the frame and window.
frame=new Frame();
frame.addNotify();
//Step 2: Draw the Image.
Image image=frame.createImage(400,60);
g=image.getGraphics();
g.setFont(new Font("Serif",Font.ITALIC,48));
g.setColor(Color.red);
g.drawString("Hello Class!!!",10,50);
BufferedImage bImg = new
BufferedImage(400,60,BufferedImage.TYPE_INT_RGB);
g = bImg.getGraphics();
g.drawImage(image,0,0,null);
ImageIO.write(bImg,"jpg",out);
}
finally
{
//clean up resources
if(g!=null) g.dispose();
if(frame!=null) frame.removeNotify();
}
}
}

Oracle 10g: Build J2EE Applications 6-11


Cookies

• A cookie is a name or value pair sent by a servlet


to a browser in the header.
• Cookies are persistent (the information sent is
stored on the client, to be retrieved later).
• Cookies are often used to obtain state information,
such as a username or preference.

Copyright © 2005, Oracle. All rights reserved.

Cookies
The following table describes the methods that are available for use with cookies and their
purposes:
get/setMaxAge This method controls the cookie expiration time in seconds. The
default value is negative, which indicates that the cookie will last only
until the user closes the browser. Setting the value to zero (0) instructs
the browser to delete the cookie.
get/setName This method gets or sets the name of the cookie.
get/setPath This method gets or sets the path to which the cookie applies. Default
is to return the cookie only to the URLs that are in or below the
directory containing the page that sent the cookie.
get/setValue getValue() looks up the value that is associated with the cookie.
setValue() specifies the value.
get/setDomain This method controls the domain for which the cookie is applied. The
browser will only return cookies to the exact host name that sent them.
Use setDomain() to return cookies to other hosts within the same
domain.

Oracle 10g: Build J2EE Applications 6-12


Setting Cookies

• Use the Cookie() constructor to create a new


cookie.
• Use the addCookie() method in the
HttpServletResponse class to add and send the
cookie to a browser.
Cookie userCookie = new Cookie ("user", "fred");
userCookie.setMaxAge(60*60); //one hour
response.addCookie(userCookie);

Copyright © 2005, Oracle. All rights reserved.

Setting Cookies
The Cookie constructor takes two strings: name and value. Note that if a user has a
browser that does not support cookies, or if the user has disabled cookies in his or her
browser, then you need to use URL rewriting, hidden form fields or session tracking to keep
track of visitors to your site. These topics are covered in a later lesson. Additionally, because
cookies are not encrypted when sent, retrieved, or stored, they should not be used for
sensitive information such as passwords.

Oracle 10g: Build J2EE Applications 6-13


Retrieving Cookies

Use the getCookies() method to fetch an array of


Cookie objects.
Cookie[] cookies = request.getCookies();
if (cookies != null) {
String readValue;
for (int i = 0; i < cookies.length; i++)
readValue = cookies[i].getValue();

Copyright © 2005, Oracle. All rights reserved.

Retrieving Cookies
The code in the slide shows how to read the cookie object from the browser. To use the
cookie object rather than just read the value, use the getCookie() method.

Oracle 10g: Build J2EE Applications 6-14


About State Preservation

• Usually, the servlet engine instantiates the servlet


only once.
• Any number of requests can be handled by the
same instance of the servlet class.
• Values of any instance variable in the class persist
between HTTP requests from multiple browsers.
• Values of variables in the doGet() or doPost()
method do not persist between multiple browser
requests.

Copyright © 2005, Oracle. All rights reserved.

About State Preservation


As discussed in the lesson titled “Creating the Web Tier: Servlets”, the Servlet object is
instantiated only once (unless the servlet implements the SingleThreadModel interface.
Any number of requests can be handled by different threads at the same time to process
multiple requests. The next slide shows how to use instance variables.
Instance variables in your servlet class persist between invocations. This makes sense, given
that the object is instantiated only once. Local variables in the doGet() and doPost()
methods do not persist.

Oracle 10g: Build J2EE Applications 6-15


State Preservation: Example

public class StateServlet extends HttpServlet {


int counter = 0; //persistent variable
public void doGet(HttpServletRequest req,
HttpServletResponse res) throws IOException,
ServletException{
res.setContentType("text/html");
PrintWriter out = res.getWriter();
String name = req.getParameter("firstName");
// name is transient variable
out.println ("<html><body>");
out.println ("Hello: " + name);
out.println ("Hit count is: " + ++counter);
out.println ("</body></html>");
}}

Copyright © 2005, Oracle. All rights reserved.

State Preservation: Example


The example in this slide demonstrates how states can be preserved by using the ideas in the
previous slide. If a request is made to this servlet, then it stores the name of the user in the
name instance variable of String type, after the firstName parameter is available.
Next, the value of the counter instance variable is incremented and displayed. Though the
code in the slide shows how to preserve state, it is not thread safe. The synchronize
keyword should be used to ensure simultaneous requests do not have access to the same
counter instance variable. Though it is usually okay for users to receive the same value for a
counter variable, there are occasions where this is clearly not desirable (for example, when
creating user IDs). Later lessons cover more sophisticated ways of preserving states.

Oracle 10g: Build J2EE Applications 6-16


ServletContext

• The ServletContext interface defines the servlet


within the Web application.
• Methods in ServletContext allow for retrieving
the MIME type of a file, dispatching requests to
other servlets, or writing to a log file.

Copyright © 2005, Oracle. All rights reserved.

ServletContext
The following table provides some of the methods of ServletContext and their uses:

Method Purpose
getContext(String) Returns the ServletContext object for the specified
URL
getMimeType(String) Returns the MIME type of the specified file as
determined by the configuration of the servlet
container, or as specified in the web.xml file
getRequestDispatcher(String) Returns a RequestDispatcher object that acts as a
wrapper for the resource located at the given path.
RequestDispatcher is used to forward or include
the request or response.
getServerInfo() Returns the name and version of the servlet container
getServletContextName() Returns the name of the corresponding Web application
as specified in the deployment descriptor for this Web
application by the display-name element

Oracle 10g: Build J2EE Applications 6-17


RequestDispatcher

• To forward the request to another servlet or JSP,


use the RequestDispatcher interface:
getServletContext().getRequestDispatcher(String
url).
• RequestDispatcher contains two methods:
forward() and include().
– Use the forward() method to transfer control to
the associated URL.
• These methods take HttpServletRequest and
HttpServletResponse as arguments.

Copyright © 2005, Oracle. All rights reserved.

RequestDispatcher
You have seen that a user can be redirected to another resource by using
sendRedirect(). However, this does not automatically preserve the request data.
Instead, you can use the RequestDispatcher interface, passing in the URL for the new
resource. Use the forward() method of RequestDispatcher to completely transfer
control to the associated URL.
For example, if a user accesses a login form of an application and does not have an account,
the request could be forwarded to an application page for the user to complete. The
include() method is used to get an output of the content of the associated URL, after
which control is returned to the servlet. Note that for both the forward() and
include() methods, POST requests cannot be forwarded to static HTML pages, because
forwarded requests use the same request method as the original request. This can be avoided
by renaming the HTML document to a .jsp extension that can handle the POST request.
JavaServer Pages (JSP) is covered in detail later in this course.

Oracle 10g: Build J2EE Applications 6-18


RequestDispatcher: Example

public void doPost(HttpServletRequest request,


HttpServletResponse response) throws
ServletException, IOException
{
String name = request.getParameter("firstName");
if (name == null){
String url = "/loginerror.jsp";
RequestDispatcher dispatcher =
getServletContext().getRequestDispatcher(url);
dispatcher.forward(request, response);
else {out.println ("Hello: " + name) ;}
}

Copyright © 2005, Oracle. All rights reserved.

RequestDispatcher: Example
By using the StateServlet example seen in the section “State Preservation: Example”
earlier in this lesson, assume that the user does not enter a name in the HTML field. You
may then want to display an HTML form with details about appropriate values. To forward
to a static HTML page, use a RequestDispatcher. The slide shows how
RequestDispatcher is obtained by calling the getRequestDispatcher()
method of ServletContext. The RequestDispatcher can then forward or include
the content to a static HTML page, a JSP, or to another servlet.

Oracle 10g: Build J2EE Applications 6-19


Servlet Filters

Filters dynamically change the content or header of a


request or response. A filter is used to:
• Intercept a request before a servlet is called
• Modify the request, response, and header values
• Optionally, customize the response

Copyright © 2005, Oracle. All rights reserved.

Servlet Filters
Servlet filters are a new feature of the Servlet 2.3 API, and can be used to intercept and
modify a servlet’s response. They can be configured to be invoked when one or many
servlets are called. This enables the programmer to modify production servlet functions
without changing existing code. Note that filters work with servlets and JSPs, but are not
servlets themselves, because they do not actually create a response. Instead, they pass the
response to the calling servlet. Filters can be used for several reasons, including
authenticating user identity, tracking users of an application, and compressing data.
JDeveloper contains wizards for creating filters.

Oracle 10g: Build J2EE Applications 6-20


Using Filters

The javax.servlet.Filter interface is implemented


to use a filter, and contains three methods:
• void init(FilterConfig)
• void doFilter(ServletRequest,
ServletResponse, FilterChain)
• void destroy()

Copyright © 2005, Oracle. All rights reserved.

Using Filters
You must implement the javax.servlet.Filter interface and define the
init(FilterConfig), destroy(), and doFilter() methods to use a filter. The
init() method is called once to initialize the filter. Pass the FilterConfig object to
init() to pass the initialization parameters. The doFilter() method is then called for
each request that is specified to use the filter. This method is responsible for actions such as
examining request and response headers and customizing the response as necessary.
FilterChain can be used to call multiple filters in succession. If there are no filters
defined or if the current filter is the last filter in the chain, then the target servlet is called.
The server calls the destroy() method to discontinue the use of the filter.

Oracle 10g: Build J2EE Applications 6-21


doFilter() Method

The doFilter() method:


• Examines the request header
• Modifies request headers by wrapping the
request object
• Modifies the response by wrapping the response
object
• Invokes the next filter in the filter chain

Copyright © 2005, Oracle. All rights reserved.

doFilter() Method
Use the doFilter() method to modify the request headers, the response, and to
optionally invoke the next filter in the filter chain. The request and response objects are
wrapped in the filter class by implementing HttpServletRequest or
HttpServletResponse. The next entity (a filter or a servlet) is invoked by calling the
doFilter() method on the FilterChain object, passing in the request and response
that it was called with, or wrapped versions that it may have created. The filters are called in
the same order that they are listed in the web.xml file. Note that if the current filter is the
last filter in the filter chain, then the filter invokes the servlet that called the filter.

Oracle 10g: Build J2EE Applications 6-22


Using Filters

import javax.servlet.*; import javax.servlet.Filter;


import java.io.*;
public class HelloFilter implements Filter {
private FilterConfig filterConfig;
public void init(FilterConfig filterConfig){
System.out.println("Filter Initialized");
}
public void doFilter (ServletRequest request,
ServletResponse response, FilterChain chain) throws
IOException, ServletException {
System.out.println("Hello from Filter");
chain.doFilter(request, response);
}
public void destroy(){}
}

Copyright © 2005, Oracle. All rights reserved.

Using Filters
In this example, the Filter interface is implemented, and the init(), doFilter(),
and destroy() methods are created to display a message when the filter is initialized. Just
before passing the request and response objects, a “Hello from Filter” message will be
displayed in the console.

Oracle 10g: Build J2EE Applications 6-23


Configuring Filters

To use a servlet filter, the web.xml deployment


descriptor is modified to include the <filter> tag:

<filter>
<filter-name>HelloFilter</filter-name>
<filter-class>filterpackage.HelloFilter
</filter-class>
</filter>
<filter-mapping>
<filter-name>HelloFilter</filter-name>
<servlet-name>StateServlet</servlet-name>
</filter-mapping>

Copyright © 2005, Oracle. All rights reserved.

Configuring Filters
The web.xml file is used to configure a filter for use. In the example given in the slide, the
filter class, HelloFilter, intercepts the request when StateServlet is accessed. A
filter can also be configured to run whenever any request (static or dynamic) is made to the
Web application:
<filter-mapping>
<filter-name>HelloFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
Initialization parameters can be specified for a filter by using the <init-params>
element.

Oracle 10g: Build J2EE Applications 6-24


Application Lifecycle Events

• Lifecycle Events are a new feature of the Servlet


2.3 API.
• Event listeners are used to check for state
changes.
• There are two types of events: ServletContext
and HttpSession.
• Event listeners can be notified when objects are
initialized, destroyed, or when their attributes
change.

Copyright © 2005, Oracle. All rights reserved.

Application Lifecycle Events


The application lifecycle events feature provides notification to “listening” objects when a
change in the ServletContext or HttpSession is identified. For example, an event
to create a pool of database connections could be called whenever the first
ServletContext of a Web application is created. There are four listeners available:
• javax.servlet.ServletContextListener
• javax.servlet.ServletContextAttributeListener
• javax.servlet.http.HttpSessionListener
• javax.servlet.http.HttpSessionAttributeListener
Note that JDeveloper contains wizards for creating servlet listeners.

Oracle 10g: Build J2EE Applications 6-25


ServletContext Events

Implement one or more ServletContext listener


interfaces to respond to ServletContext events. The
following methods are invoked when a
ServletContext event occurs:
• contextInitialized()
• contextDestroyed()
• attributeAdded()
• attributeRemoved()
• attributeReplaced()

Copyright © 2005, Oracle. All rights reserved.

ServletContext Events
The following table describes the types of methods that are invoked for each type of
ServletContext event:

Events Methods
ServletContext is contextInitialized()or
created or is shutting contextDestroyed() methods of the
down. ServletContextListener class
An attribute has been attributeAdded(),
added, removed, or attributeRemoved(), or
replaced. attributeReplaced() methods of the
ServletContextAttributeListener
class

Oracle 10g: Build J2EE Applications 6-26


HttpSession Events

Implement one or more HttpSession listener


interfaces to respond to HttpSession events. The
following methods are invoked when an HttpSession
event occurs:
• sessionCreated()
• sessionDestroyed()
• attributeAdded()
• attributeRemoved()
• attributeReplaced()

Copyright © 2005, Oracle. All rights reserved.

HttpSession Events
Sessions are a way to maintain a continuous connection within a Web application, and are
covered in depth later in the course. For now, just note that the following methods are
available for tracking session events:

Events Methods
An HttpSession has sessionCreated() or
been activated or is sessionDestroyed() methods of the
about to be destroyed. HttpSessionListener class
An attribute has been attributeAdded(),
added, removed, or attributeRemoved(), or
replaced. attributeReplaced() methods of the
HttpSessionAttributeListener
class

Oracle 10g: Build J2EE Applications 6-27


Example of an Event Listener

public class ConnectionManager implements


ServletContextListener {
public void
contextInitialized(ServletContextEvent
event) {
Connection conn = // create connection
event.getServletContext().setAttribute("conn",
conn);
}

Copyright © 2005, Oracle. All rights reserved.

Example of an Event Listener


The slide shows an example event listener to ensure that a database connection is available
for every new servlet context. To use this listener, add the following to the web.xml file:
<web-app>
<listener>
<listener-class>ConnectionManager</listener-class>
</listener>
<servlet>

</servlet>
</web-app>
Note that the listener attribute must directly precede the servlet element in the
web.xml file.

Oracle 10g: Build J2EE Applications 6-28


Error Handling

• Java prevents a servlet from unintentionally or


maliciously damaging the servlet engine.
• The Servlet API allows:
– Logging of errors
– Sending HTTP status codes to the client
• In the doGet() method, Java requires that any
method that generates any exceptions must be
handled explicitly.
– You can let the servlet engine handle only
IOException and ServletException, and not
any other exceptions (for example,
InterruptedException).

Copyright © 2005, Oracle. All rights reserved.

Error Handling
As in any program, error handling is very important in a servlet. For example, errors can
occur if:
• The client sends malformed data to the servlet
• A resource made available by the operating system becomes unavailable or corrupt
When an error occurs, you should limit the damage to the server and inform the Web
browser appropriately. The following example illustrates how you could manipulate the
response status line in a servlet, by using the previously referenced StateServlet:
String name = request.getParameter("firstName");
if ((name.equals("") {
reportError (response, "Missing Name Parameter");
return; }
private void reportError(HttpServletResponse response,
String errmessage) throws IOException {
response.sendError (response.SC_NOT_FOUND, errmessage);
}

Oracle 10g: Build J2EE Applications 6-29


Summary

In this lesson, you should have learned how to:


• Send headers and other content to the client
• Use filters to modify servlet response
• Handle state preservation
• Handle errors that might arise during the
execution of your servlet

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 6-30


Practices 6-1 and 6-2: Overview

These practices cover the following topics:


• Creating a servlet that uses cookies
• Using servlet filters to manipulate headers

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 6-31


Practice 6-1
The purpose of this practice is to use cookies within multiple servlet instances. You modify
the LoginServlet.java file that you created in practice 5. This servlet uses a cookie to
store the user’s name and retrieve that value when the user accesses the servlet. Open the
practice06.jws workspace and navigate to the newlogin project. Open
LoginServlet.java in the code editor.
1. Add code to the doPost() method of LoginServlet.java servlet to create a
cookie.
a. Create a new Cookie object named “LoginCookie.” The cookie value will be
the variable that holds the custName value.
b. Set the cookie’s maximum age to two minutes.
c. Add the cookie to the response object to send it to the browser.
2. Retrieve the cookie from the browser. Add the following code to the doGet()
method of LoginServlet.java:
a. Create a variable to store the value of the cookie.
b. Use the getCookies() method to fetch the array of Cookie objects. Then,
verify whether the request returned any cookies.
c. If so, use iteration to loop through the array of cookies. For each iteration, test to
see if the cookie’s name is “LoginCookie.” If so, retrieve the cookie value into
the variable that you created in step 2.a. and break out of the loop.
d. Test whether the cookie was found. If not, display the form that is already created
in the doGet() method. If it is found, add code to welcome the user back to the
Order Entry application by using the value of the cookie for personalization.
e. Compile LoginServlet.java.
3. Test and run the application.
a. Run LoginServlet.java. You should see the form that was created in the
previous practice. Enter a valid name and ID in the fields (refer to practice 5 for
valid name and ID entries) and click Login.
b. You should see the orders displayed for the customer as in the previous practice.
However, the name is now stored as a cookie for two minutes.
c. Run LoginServlet.java the second time to test whether the cookie is being
correctly set. You should be welcomed back to the application.
d. To ensure that your cookie is expiring correctly, wait for two minutes and then
run LoginServlet.java. You should see the form as in step a.

Oracle 10g: Build J2EE Applications 6-32


Practice 6-2
The purpose of this practice is to redirect a user by sending a header to the response.
Suppose that the contract between your company and customer number 104 is currently
being reviewed, and as the developer, you have been instructed to temporarily block this
customer from entering the Order Entry application. You can do this by modifying the
servlet code to check for this customer and redirect him or her to an appropriate error
message. However, this would mean modifying the servlet itself. Therefore, to incorporate
this business rule, use a servlet filter.
1. Select File > New > Web Tier > Servlets and create a new Servlet Filter in the
newlogin project. Name the filter and the class LoginFilter, and ensure the
package name is newlogin. Map this filter to every servlet in the URL pattern.
2. Use the Properties class of the java.util package to create an instance
variable named “blockUser.”
a. Create an instance variable of type java.util.Properties. Note that you
will need to import this package.
b. Use blockUser.setProperty to define the business rule that you are
creating: the “name” property with a value of “Sutherland”.
c. Additionally, create an instance variable to store the value of
javax.servlet.ServletContext. Note that you must import this
package.
3. Modify the init() method.
a. Set the context for this method as
filterConfig.getServletContext(); and write to the context log
that the filter has been initialized. Use filterConfig.getFilterName()
to retrieve the name of the filter.
4. Modify the doFilter() method to check for the supplied customer name.
a. Loop through the enumeration returned from the keys() method of
blockUser and look for the String value of this variable. Use the
hasMoreElements() method of java.util.Enumeration to
increment in the loop.
b. Retrieve the custName parameter from the request object, and set it to a
temporary String variable.
c. Verify whether the value of the variable created in the previous step matches the
value that is retrieved from the enumeration.
d. If the values match, send an error message by using
javax.servlet.http.HttpServletResponse to the browser,
indicating that the service is unavailable. Additionally, include a message in the
error to indicate that the value specified has been temporarily rejected. Send this
error message text to the context log.
e. Finally, pass the doFilter() method down the filter chain.
5. Compile the filter and test by running LoginServlet, and by supplying a customer
number of 104 and a name of “Sutherland”. The filter should modify the response
so that a service_unavailable error is sent in the response.

Oracle 10g: Build J2EE Applications 6-33


Maintaining State in J2EE Applications

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Maintain persistent activity from clients by using a
browser
• Use the HttpSession object
• Describe state preservation

Copyright © 2005, Oracle. All rights reserved.

Objectives
Although the HTTP protocol is stateless, servlets allow your application to “remember”
previous visitors and the data that they have created in the past. This lesson shows you how
to use this capability.

Oracle 10g: Build J2EE Applications 7-2


Overview

First request

Chris

Servlet
Second request

Chris

First request

Michelle

Copyright © 2005, Oracle. All rights reserved.

Overview
The standard HTTP server is stateless, and cannot distinguish whether two requests come
from the same client. You may want to know if the same client has accessed your servlet
before. This question is more complex than it may seem:
• If Chris accesses your servlet from a Netscape browser and an Internet Explorer
browser at the same time, then should the servlet consider the two requests to be from
the same client?
• If Michelle accesses your servlet today, and again a month later from the same
browser, then should the servlet consider the two requests to originate from the same
client? Assume that the browser has not been shut down in this period.

Oracle 10g: Build J2EE Applications 7-3


Session Basics

• The HTTP protocol is stateless.


• The session mechanism guarantees that the
object that serves the client knows which client
has made a request.
• User requests from the same browser are
considered to be from the same client.

Copyright © 2005, Oracle. All rights reserved.

Session Basics
Two requests originating from the same browser within a short period of time are considered
to be from the same client. When considering sessions, think about the shopping cart
scenario of many online applications. Requests from different browsers are considered to be
from different clients (as in the previous slide, with requests coming from Chris and
Michelle).

Oracle 10g: Build J2EE Applications 7-4


Session Basics

• Options for identifying the client: Cookies, URL


rewriting, hidden fields, HttpSession
• Result: A unique identity assigned to every client
• Options for implementing sessions on the server:
– Single-threaded model (not scalable)
– HttpSession with a multithreaded server
(Each thread uses the unique identity to process the
request.)

Copyright © 2005, Oracle. All rights reserved.

Session Basics (continued)


A Web server can identify a client by using mechanisms, such as cookies, and by assigning
that client a unique object identity number. This number may expire after some time.
However, clients can disable cookies on their browsers. When you use URL rewriting, you
must always append the client-specific data to the URL, and the server must complete
expensive processing. Hidden fields are useful, but they work only if every page in your
application is dynamically generated.
One way to make sure that a servlet does not overwrite the data provided by different clients
is to create a new servlet instance for every unique object identity number. For instance, the
servlet engine could force you to declare your servlet to be a SingleThreadModel
servlet if you want unique sessions.
However, this method is not scalable. An alternative approach is to associate a unique
HttpSession object with every HttpServletRequest object, but allow multiple
threads to go through the body of the service() method.

Oracle 10g: Build J2EE Applications 7-5


Threading

Multithreaded model Single-threaded model

Client 1

Servlet instance 1 Client 1

Servlet instance 2 Client 2


Client 2

Both clients using Both clients using


unique sessions, but unique sessions and
sharing the same unique instances
servlet instance

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 7-6


URL Rewriting

• URL rewriting:
– Every URL that is accessed by the client is rewritten
so that it has the session ID.
– Use the encodeURL() method to re-create the path
dynamically.
• URL rewriting is used when a client turns off
cookie support in the browser.

Copyright © 2005, Oracle. All rights reserved.

URL Rewriting
Use response.encodeURL() when sending a URL from your site to the client. The
browser header information can then be retrieved by using the request object. If you are
using sendRedirect, then a corresponding method called encodeRedirectURL
exists for this purpose. For instance:
String originalURL = someURL;
String encodedURL = response.encodeRedirectURL(originalURL);
Response.sendRedirect(encodedURL);

Oracle 10g: Build J2EE Applications 7-7


HttpSession

• The unique identity for the client is an


HttpSession object.
• The object is created by using the getSession()
method of the HttpRequest object.
HttpSession session = req.getSession(true);

• Any servlet that responds to a client request can


create this object.
• An object can be potentially shared across several
servlets. (Every servlet within an application can
identify with this client.)

Copyright © 2005, Oracle. All rights reserved.

HttpSession
The HttpSession class is an interface. The object is obtained by using the
getSession() method in the HttpServletRequest object. This is done by
extracting a userID from a cookie or attached URL data, and then by using that ID as a key
into a table of previously created session objects. However, all this is done automatically for
you, and all you need to do is create a new session (if there is no existing session) by using
the code that is listed in the slide. If you pass “false” to the getSession() method, it will
return null if there is no existing session.
The servlet specification states that HttpSession objects can be shared by different
servlets in a servlet engine. Therefore, HttpSession objects must be synchronized by
the implementation. For example:
HttpSession session = request.getSession(true);
ShoppingCart cart =
(ShoppingCart)session.getAttribute(session.getId());
if (cart == null) {
cart = new ShoppingCart();
session.setAttribute(session.getId(), cart); }

Oracle 10g: Build J2EE Applications 7-8


Session Objects

• With session objects, you can:


– Put items into the object (values persist across
multiple invocations from the same client)
– Access items from the object
– Obtain the session identity
– Find out when the session was last accessed
• Items put in a session object can:
– Implement the Serializable interface
– Be relocated to a different server
– Persist across servlet crashes

Copyright © 2005, Oracle. All rights reserved.

Session Objects
The table below describes the methods in the HttpSession class and their meanings:

getLastAccessedTime() A long object denoting when the session


was last accessed by the client.
getId() A string denoting the unique identity of a
client.
setAttribute(String name, Places an object with the name alias in the
Object value) HttpSession object. (You must make
sure that the name is unique across all
possible servlets in the engine.)
getAttribute(String name) Retrieves the previously stored value from
the session object.
isNew() A Boolean method that returns “false” if
the session existed previously for the
client, and “true” otherwise.

Oracle 10g: Build J2EE Applications 7-9


Session-Based Page Counter

public void doGet(…)… {


response.setContentType("text/html");
PrintWriter out = response.getWriter();
HttpSession session = request.getSession(true);
String sessionid = session.getId();
Integer sessionCount =
(Integer)session.getAttribute("sessionCount");
if (sessionCount == null) {
sessionCount = new Integer(0);
} else { sessionCount =
new Integer(sessionCount.intValue() + 1);
}
session.setAttribute("sessionCount", sessionCount);
out.println("<p>Number of requests for the session with
the id of " + "<b>" + sessionid + "</b> is: " +
sessionCount);
}

Copyright © 2005, Oracle. All rights reserved.

Session-Based Page Counter


Compare this example with the one you saw earlier in the lesson titled “Using Advanced
Techniques in Servlets.” In this example, obtaining the correct number of hits made to your
servlet during a session is guaranteed (as opposed to during the lifetime of the servlet).

Oracle 10g: Build J2EE Applications 7-10


Session Life Cycle

• A session can expire automatically, or you can


explicitly invalidate a session.
• The HttpSession object gets invalidated when a
session expires.
Date dayAgo = new Date(
System.currentTimeMillis() - 24*60*60*1000);
Date hourAgo = new Date(…) // an hour ago
Date created = new Date(
session.getCreationTime());
Date accessed = new Date(…)
if (created.before(dayAgo)||
accessed.before(hourAgo)) {
session.invalidate(); session = … //create new
}

Copyright © 2005, Oracle. All rights reserved.

Session Life Cycle


The example in this slide invalidates a session if it is too old. A session is considered “old”
in this example if it either has not been accessed for a long time (an hour) or was created a
long time (a day) ago. In this case, the servlet creates a new session after invalidating the
old one.
A session becomes invalid automatically based on settings in the Web server. Refer to the
Web server documentation for information about how to set the session invalidation time.
You can also use the getMaxInactiveInterval (int seconds) method to set
the duration (in seconds) for which an unused session should be kept active before being
invalidated. This timeout is maintained on the server, in contrast to the cookie expiration
time, which is sent to the client.

Oracle 10g: Build J2EE Applications 7-11


Session Tracking in OC4J

• J2EE server vendors handle session tracking in


different ways.
• Oracle Application Server 10g Containers for J2EE
(OC4J):
– Uses cookies as the default method for session
tracking (can be disabled by a user or within the
application deployment descriptor)
– Does not support auto-encoding, where session IDs
are automatically encoded into the URL by the
container (an expensive process)
– Causes a session to expire in 20 minutes by default
(modified in the deployment descriptor)

Copyright © 2005, Oracle. All rights reserved.

Session Tracking in OC4J


OC4J first attempts to accomplish session tracking through cookies. If the cookies are
disabled, then the sessions can be maintained by using only the encodeURL() and
encodeRedirectURL() methods. Cookies can be disabled for an application by adding
the following line to global-web-application.xml or orion-web.xml:
<session-tracking cookies="disabled"> </session-tracking>
OC4J does not support the nonstandard and expensive method of encoding the session ID
into a URL.
Sessions last for 20 minutes by default. To change this, modify the web.xml file as
follows:
<session-config>
<session-timeout>5</session-timeout>
</session-config>
This changes the session timeout to five minutes. A value of 0 (zero) or less specifies that a
session never gets timed out.

Oracle 10g: Build J2EE Applications 7-12


Sessions and Events

When a servlet stores an object in a session or


removes an object from a session, the session checks
whether that object implements the
HttpSessionBindingListener interface. If it does,
then the servlet notifies the object that it has been
either:
• Bound to the session (by calling the object’s
valueBound() method, which is a good place for
initializing client-specific resources)
Or
• Unbound from a session (by calling the object’s
valueUnbound() method, which is a good place
for releasing resources)

Copyright © 2005, Oracle. All rights reserved.

Sessions and Events


When an application stores an object in a session by using setAttribute(), or removes
an object from a session by using removeAttribute(), the session checks whether the
object implements the HttpSessionBindingListener interface. If it does, then the
servlet notifies the object that it has been bound to, or unbound from, the session.
Notifications are sent after the binding methods are completed.
Note that for sessions that are invalidated or expire, unbound notifications are sent when the
session has been invalidated or has expired. For instance, you can create a connection in the
valueBound() method, and close it in the valueUnbound() method, after the user’s
session has expired.

Oracle 10g: Build J2EE Applications 7-13


Sessions and Events

• An object is bound to a session after the object is


passed into the session.setAttribute()
method.
• An object is unbound from a session:
– After the object is removed by using the
session.removeAttribute() method
– When a session is invalidated

Copyright © 2005, Oracle. All rights reserved.

Sessions and Events (continued)


The removeValue() and removeAttribute() methods trigger the
valueUnbound() method when implementing the
HttpSessionBindingListener. Note that removeAttribute() is used to
remove a value without replacing it, whereas setAttribute() replaces any previous
value. To explicitly end a session, use the session’s invalidate() method.

Oracle 10g: Build J2EE Applications 7-14


Sessions and Events

To use the event mechanism, you must perform the


following steps:
1. Create a class that implements the
HttpSessionBindingListener interface.
2. Instantiate the class.
3. Insert the instantiated object into the
HttpSession object by using the
setAttribute() method.

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 7-15


Sessions and Events

Example:
public class EventObject
implements HttpSessionBindingListener {
public void valueBound(
HttpSessionBindingEvent event) {
// connect to the database using this client
sess = event.getSession()//which session?
// get values from this session object to
// identify client information
}
public void valueUnbound(
HttpSessionBindingEvent event) {
// release resources
}
}

Copyright © 2005, Oracle. All rights reserved.

Sessions and Events (continued)


In this example, the HttpSessionBindingListener interface is implemented.
Therefore, the valueBound() method of the HttpSession object (which in this case is
event) will be called immediately after setAttribute() is called on that object.
Similarly, the valueUnbound() method will be called for the event object when the
session becomes inactive.

Oracle 10g: Build J2EE Applications 7-16


Creating Distributable Applications

Applications are deployed as “distributable” by


specifying the <distributable/> tag in the web.xml
file. These applications should be developed to run in
a distributed servlet container (such as OC4J) as
follows:
• Because the ServletContext attributes exist
locally in one Java virtual machine (JVM), the
information that must be shared between servlets
should be placed in a session, a database, or an
EJB.
• HttpSession objects must implement the
Serializable interface to be sent between JVMs.

Copyright © 2005, Oracle. All rights reserved.

Creating Distributable Applications


A distributable application is one that uses multiple JVMs or clusters to scale properly.
These applications should be written with the assumption that information stored in one
JVM may not be available in another. Further, because the requests from one client can be
received by any of the running JVMs, the session objects must be consistent. To maintain
this, the container replicates the state of each session. This means that your session attributes
must implement the Serializable interface, to be sent between JVMs.

Oracle 10g: Build J2EE Applications 7-17


Summary

In this lesson, you should have learned how to:


• Instantiate the HttpSession object
• Use the HttpSession object
• Implement the HttpSessionBindingListener
interface

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 7-18


Practice 7-1: Overview

This practice covers the following topics:


• Creating an HttpSession object
• Tracking an order based on the HttpSession
object

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 7-19


Practice 7-1
In this practice, you create a shopping cart application to track a customer’s orders in the
Order Entry application. You create a link to the LoginServlet that displays the
products. Each product can then be added to a shopping cart by passing in the productID
and name of the selected product. You create a class to store the products that are selected
for each session, and display them by using a servlet. Open the practice07.jws
workspace and select orderproducts.
1. Create a servlet to display the products that are available for order.
a. Create a new servlet named ProductsServlet in the orderproducts
package. Generate a doGet() method for this servlet and use the default
mappings.
b. Import the javax.naming.*, javax.sql.*, java.sql.*, and
oracle.jdbc.* packages.
c. Create instance variables for the Connection (as conn) and DataSource
(as ds).
d. Create a new method in ProductsServlet.java to retrieve the
PRODUCT_ID, PRODUCT_NAME, and PRODUCT_DESCRIPTION from the
PRODUCTS view, ordering by the CATEGORY_ID. You must use coding similar
to that used in the init() and verifyCustomer() methods of
LoginServlet.java.
e. Loop through the result set and retrieve the values of the columns into variables.
f. Set the return value for this method by creating a table to store the variables that
are returned in step 1d in a table format. Include an href link at the end of each
row that points to showcartservlet, and allows the customer to add this
product to his or her shopping cart. You create this servlet later in the practice.
Close the result set object and return the variable name.
Hint: Include two parameters in the URL, using the variables you created in the
previous step:
<yourreturnvaluename> += "<tr><td>" + var1 + "</td><td>" +
var2 + "</td><td>" + "<a href=\"showcartservlet" +
"?param1=" + var1 + "&param2=" + var2 + "\"/> + Add to
Shopping Cart" + "</a></td></tr><p>";

g. Modify the doGet() method to call the method that you have created in a
try/catch block. Make sure to create table headings for the product name and
description.
2. Create a link from LoginServlet to ProductsServlet.
a. Below the code for displaying orders for a customer (in the doPost() method),
insert an href link to point to the ProductsServlet. You can use the URL-
pattern mapping name that is generated for you, described in the web.xml file.
Note that the cookie functionality created in the last practice has been removed to
prevent any confusion.
3. Create a ShoppingCart class to store the selected products in a Hashtable.
a. Create a new class file by selecting Java Class from the Simple Files category
(within the General category). Name the class ShoppingCart and click OK to
accept the default package and attributes.
b. Import the java.util.* package because you will be using a Hashtable
from that package.
Oracle 10g: Build J2EE Applications 7-20
Practice 7-1 (continued)
c. Declare two instance variables in the class definition: items and
numberOfItems. Declare items as a Hashtable and numberOfItems
as type int, initializing to null and zero, respectively.
d. In the class constructor, initialize items as a new Hashtable object.
e. Create a method named add(). This method should return void and pass in two
arguments, prodid and name, both strings.
f. Add code to this method to store the prodid and name arguments in the
Hashtable object that you created in step 3d, and increment the
numberOfItems variable.
g. Create a second method named getNumberOfItems(). This method should
return numberOfItems.
h. Create a third method named getItems(). This method should return an
enumeration of elements in the items hashtable.
i. Compile ShoppingCart.java.
4. The next step is to create a servlet to display the products in the user’s shopping cart.
a. Create a new servlet and name it ShowCartServlet. Change the package
name to orderproducts and create servlet mappings as in previous practices.
b. Add code to the doGet() method to create a new session object if one does not
already exist.
c. Next, retrieve the user’s shopping cart as cart from the session object. Use the
getId() method of the session to find the unique identifier of the session.
d. If the user does not have an existing shopping cart, create a new one by passing
in the session’s unique identifier and cart object.
e. Create two variables to retrieve the prodid and name parameters from the
request object.
f. Add these values to the cart object by calling the add() method of the
ShoppingCart class and passing in the prodid and name arguments.
g. Create an int variable to retrieve the number of items that are ordered from the
ShoppingCart class.
h. Add HTML to display the number of items in the user’s shopping cart, and create
a table to display the elements in the cart. Note that the getItems() method
returns a java.util.Enumeration of items in the Hashtable. You need
to import this package. Use the hasMoreElements() method to verify items
in the getItems() method. Remove the skeleton HTML code.
i. Compile ShowCartServlet.java.
5. Save and compile the project, and test the application by running
LoginServlet.java.

Oracle 10g: Build J2EE Applications 7-21


Creating the Web Tier: JavaServer Pages

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Compare servlets and JavaServer Pages (JSP)
• Build a simple JSP
• Describe the JSP life cycle
• List the basic JSP elements
• Develop JSPs with declarations, expressions, and
scriptlets
• List implicit objects
• Use JavaBeans with JSP

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson discusses JavaServer Pages (JSP). You learn how to differentiate between
servlets and JSPs. You learn about the life cycle of a JSP, and also the various elements in a
JSP. You should be able to develop simple JSPs with declarations, expressions, and
scriptlets, and learn how to use JavaBeans with JSP. You also learn how Oracle JDeveloper
10g can be used to develop JSPs.

Oracle 10g: Build J2EE Applications 8-2


JavaServer Pages

Request Connects to

JSP
Database
Client
Generates

Dynamic content

Response EJB

Copyright © 2005, Oracle. All rights reserved.

JavaServer Pages
The idea behind servlets and JavaServer Pages technology is to separate the presentation
logic and business logic and, therefore, have thin clients. JSPs are based on Java servlet
technology and are an extension of servlets. JSPs can generate dynamic content just like
servlets; however, a JSP has its own advantages.
The advantage of the JSP model is that Web designers need not be familiar with the Java
programming language to create JSPs. Programmers can provide JavaBeans and custom tags
to Web designers who are familiar with HTML. In this model, there are well-defined job
roles for Web page designers and application programmers.
Given that JSP builds on servlets, the focus of JSP is on improving the programmer’s
productivity. JSP leverages the benefits of component technologies and, therefore, simplifies
the task of the programmer.
The graphic in the slide shows that a client invokes a JSP with a URL. Note that JSPs
function by using the request/response model, like servlets. Depending on the request from
the client, the JSP connects to a database, or calls an Enterprise JavaBean (EJB), which in
turn can connect to a database. The JSP then creates dynamic content by using the output
from the database or an EJB, and returns it to the client.

Oracle 10g: Build J2EE Applications 8-3


Comparing Servlets and JSPs

Servlets: JavaServer Pages:


• Are Java programs • Are HTML pages
with embedded with embedded Java
HTML code or they can be
• Generate dynamic pure XML
content • Generate dynamic
• Do not separate content
static and dynamic • Separate static and
content dynamic content

Copyright © 2005, Oracle. All rights reserved.

Comparing Servlets and JSPs


A JSP is an HTML page with embedded Java code. JSPs can also be pure Extensible
Markup Language (XML). A JSP takes an HTML page, adds a few tags, and automatically
generates dynamic content. A servlet also generates dynamic content, but it is not an HTML
page. A servlet is a Java program with embedded HTML code. Because a servlet is a Java
program, the programmer must take care of the syntax and semantics while developing a
servlet. The servlet must be compiled before it is executed.
Though you must know Java programming language and the API well before you can
develop a servlet, you need not be an expert in Java to develop a JSP. A Web page designer
can develop a JSP, because JSPs mainly contain HTML/XML tags and additional JSP tags
containing the Java code.
In servlets, most of the Java code is written in the service method. However, in JSPs, the
Java code is embedded in JSP tags. This enables separation of the static and dynamic
content in JSP. All the static content is in the HTML tags, and the dynamic content (Java
code) is in the JSP tags.
Because a servlet is a Java program, the .class file must be created before it can be
invoked. A JSP is automatically compiled into a servlet when it is invoked for the first time.
You need not explicitly compile the source. However, if you are using integrated
development environment (IDE) to develop JSPs, the JSPs are automatically compiled when
you run them.
Oracle 10g: Build J2EE Applications 8-4
Invoking JSPs

HTML
Invoke

JSP

Servlet

JSP

Copyright © 2005, Oracle. All rights reserved.

Invoking JSPs
You can invoke a JSP in different ways, depending on the needs of your application:
• Invoking a JSP with a URL: You can invoke a JSP directly with the URL
http://host:port/context-root/main.jsp.
In the URL:
- host is the name/IP address of the machine where JSP is running
- port is the port number on which the server is running
- context-root is the name with which the document is mapped to a client
- main.jsp is the name of the JSP file
You invoke a JSP directly with the URL if a home page or login page is designed with
JSP. You can also use it for testing purposes.
• Invoking a JSP from an HTML page, a servlet, or a JSP: In a practical scenario, the
first page is designed as a controller servlet, which invokes a JSP depending on user
inputs. You can also invoke a JSP from another JSP.

Oracle 10g: Build J2EE Applications 8-5


The Date JSP
<%@ page contentType="text/html;charset=WINDOWS-1252"%>
<html> <head>
<meta http-equiv="Content-Type" content="text/html;
charset=WINDOWS-1252">
<title> Show Date </title>
</head>
<body>
<h2> The current time is: </h2>
<p> <%= new java.util.Date() %> </p>
</body>
</html>

Copyright © 2005, Oracle. All rights reserved.

The Date JSP


The slide shows the JSP code for displaying the current time and date, and the result of
invoking the JSP. Note that the code mainly contains HTML tags. The Java code that is
highlighted in the slide displays the date and time dynamically. The content in the HTML
tags form the static part of this page.
JSP is primarily component-centric and not page-centric. The page-centric model is easy to
learn and allows rapid development. However, people eventually realized that this is not the
way to build large, scalable Web applications. The logic that is written for the scripted
environments is locked inside pages. Presentation logic is mixed with business and data
logic, making application maintenance difficult as programmers attempted to modify the
look and feel of an application without breaking the tightly coupled business logic. As Web
application complexity increased, the limitations of the page-centric model became obvious.
At the same time that people were looking for better ways to build Web applications,
components were being actively developed in the client/server world. Java and Windows
application developers were using JavaBeans and ActiveX, respectively.
JSP is primarily a component-centric platform. Components can be shared across JSPs, and
both non-Java developers and Java developers can use them.

Oracle 10g: Build J2EE Applications 8-6


The Date Servlet

...
public void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException,
IOException
{
response.setContentType(CONTENT_TYPE);
PrintWriter out = response.getWriter();
out.println("<html>");
out.println("<head><title>Show Date
</title></head><body><h2>The current time
is:</h2><p>");
out.println(new java.util.Date());
out.println("</body></html>");
out.close();
}
...

Copyright © 2005, Oracle. All rights reserved.

The Date Servlet


You have already seen Date.jsp. Consider writing a servlet instead of JSP to display
date. The code in the slide shows the doGet() method of the date servlet. Observe that all
the HTML tags (highlighted in the slide) and their data are passed to the println()
method as a java.lang.String. This is a simple servlet that displays the date, but still
includes many println statements. It is too cumbersome to design a complex page, which
includes both static and dynamic content.
Note that a single println statement can replace all the println statements in the
servlet:
out.println("<html><head><title>Show
Date</title></head><body><h2>The current time
is:</h2><p>"+ new java.util.Date()+ "</body></html>");
However, if you split the HTML tags with different println statements, it is much easier
to revisit or debug the servlet.

Oracle 10g: Build J2EE Applications 8-7


Automated JSP Features

• A JSP is automatically converted into a servlet the


first time it is invoked:
– Java source files are generated.
– Java class files are generated.
– The Java Just-In-Time compiler can be used.
• A JSP can contain extensible components:
– Tags: Libraries such as OC4J JSP (OJSP) or
custom-developed tags.
– JavaBeans (Beans are reused and their properties
are automatically introspected.)

Copyright © 2005, Oracle. All rights reserved.

Automated JSP Features


Unlike servlets, you need not compile the JSPs. When you invoke a JSP for the first time,
the JSP is automatically converted into a servlet. The dynamic content (Java code) in the
JSP is put into the _jspService method of the servlet and the static content remains
untouched. Therefore, the first time that a JSP is invoked, your response time is likely to be
slow. With subsequent requests, however, you obtain the full benefits of the servlet
technology.

Oracle 10g: Build J2EE Applications 8-8


JSP Life Cycle

J2EE container

Yes
OC4J First
1
time

Create servlet
http://host/date.jsp
No date.java

Compile servlet
date.class
3
Servlet life cycle

Copyright © 2005, Oracle. All rights reserved.

JSP Life Cycle


When the Web server receives a request, the server deciphers the request to determine if the
request is for a JSP. The JSP engine verifies whether the corresponding servlet class exists.
If the servlet does not exist, then this is the first time the JSP has been requested. Thus, the
JSP life cycle is traversed as follows:
1. The JSP is translated into a servlet. During the translation phase, each tag in the JSP is
handled differently, because some of the tags provide instructions for the container and
some are used to create dynamic content.
2. After the translation is done, the servlet source file is compiled and a servlet class file
is generated.
3. The server then executes the servlet by following the life cycle of the servlet.
If the servlet already exists, then the servlet is executed as mentioned in step 3.

Oracle 10g: Build J2EE Applications 8-9


Basic JSP Elements

A JSP contains three main elements:


• Text elements
• Directives
• Scripting elements
– Declarations
– Expressions
– Scriptlets

Copyright © 2005, Oracle. All rights reserved.

Basic JSP Elements


Text elements: Text elements represent the static portion of the page and are formatted
through standard HTML or XML.
Directives: These elements provide instructions to the JSP at run time. The JSP container
processes the instructions that are provided in the directives while compiling the JSP.
Scripting elements: These elements represent the dynamic portion of the page. They
contain Java code. They are used to perform computation and to generate dynamic content.
They include tags called scriptlets, expressions, and declarations. The code in these scripting
elements are put in the _jspService method, which in turn is called by the service
method of the servlet when the JSP is translated to a servlet.

Oracle 10g: Build J2EE Applications 8-10


Declarations

• Are used to define methods or variables


• Begin with the sequence <%!
• End with the sequence %>
• Are inserted into the body of the servlet class
during translation
• Are used in conjunction with expressions or
scriptlets
<%! private int i=3; %>
<%! private String a="Hello", b=" World"; %>

Copyright © 2005, Oracle. All rights reserved.

Declarations
As the name indicates, the JSP declarations are used to declare the methods or variables.
This is inserted into the main body of the servlet class outside the _jspService method.
The example in the slide shows how to declare an integer variable and string variables.
Observe that these variables are declared as well as initialized in the declaration. It is
mandatory to terminate a declaration with a semicolon before closing it with %>. Note that
declaring a variable does not write anything to the output.
The variables declared in this manner are static by default. As previously discussed, the JSP
file is translated and compiled into a servlet class. When multiple clients request the same
servlet, multiple threads are created to handle the requests. However, they operate on the
same instance of the servlet if the servlet does not implement SingleThreadModel.
Each thread calls the service method of the same instance, and this instance has a single
variable. Therefore, any changes made to the variable by one thread are reflected in the
other threads. This is as good as modifying a static variable.

Oracle 10g: Build J2EE Applications 8-11


Expressions

• Begin with the sequence <%=


• Contain Java expressions that are evaluated and
inserted into the servlet’s output
• End with the sequence %>
• Do not end with a semicolon
<%= i+1 %> 1
<%= a + b %>
<%= new java.util.Date() %> 2

Copyright © 2005, Oracle. All rights reserved.

Expressions
Expressions are used to insert values directly into the output. The expression is evaluated
first and the result is converted to a string. For every expression in the JSP, a print
statement is inserted in the _jspService method. Therefore, the resultant string is then
written to the output. The expressions are evaluated at run time.
1. Variable i is declared and initialized to 3 (in the previous slide). Therefore, this
expression prints the value 4. Similarly, a is initialized to “Hello” and b is initialized
to “World”. The expression a + b prints “Hello World”. This is same as
<%= "Hello" + " World" %>.
2. This expression prints the current time and date.
The slide shows three expressions. The corresponding translated code that is put in the
_jspService method, is as follows:
out.print(i+1);
out.print(new java.util.Date());
out.print("Hello" + " World");

Oracle 10g: Build J2EE Applications 8-12


Scriptlets

• Begin with the sequence <%


• Contain a block of Java code that is executed
every time a request is made
• End with the sequence %>
<% if (i<3)
out.print("i<3");
if (i==3)
out.print("i==3");
else
out.print("i>3");
%>

Copyright © 2005, Oracle. All rights reserved.

Scriptlets
Scriptlets enable you to write blocks of Java code inside the JSP. This code is executed
every time the JSP is invoked. The code inside the scriptlet is inserted exactly as it is written
into the _jspService method. A scriptlet can contain any valid Java code. Any errors in
the scripting elements are thrown during translation time or compilation time.
The slide shows an example for scriptlet. You can alternatively write the code shown below:
<%if (i<3) %>
i<3
<%if (i==3) %>
i==3
<%else %>
i>3
In this code, whatever is not enclosed within the scriplet is treated as HTML code and gets
converted to print statements during translation. Therefore, you need not enter the print
statements repeatedly.
In the example shown in the slide, the out variable, which has not been declared so far, is
being used. The following slide discusses this variable.

Oracle 10g: Build J2EE Applications 8-13


Implicit Objects

There are eight implicit objects, also known as


predefined variables, in JSP:
• request • application
• response • config
• session • pageContext
• out • page

Copyright © 2005, Oracle. All rights reserved.

Implicit Objects
In JSP, implicit objects are provided. You can use these predefined variables without
explicitly declaring them. Implicit objects are created by the container, and contain
information related to a particular request, page, or session.
request: This variable is the HttpServletRequest object that is associated with the
request. You can access the request parameters, such as request type, HTTP headers, and so
on, with this variable.
response: This variable is the HttpServletResponse object that is associated with
the response to the client.
session: This variable is the HttpSession object that is associated with the request.
Sessions are created automatically; you can also disable the sessions if you do not want to
associate a session with each client.
out: This variable is the PrintWriter object that is used to send the output to the client.

Oracle 10g: Build J2EE Applications 8-14


Implicit Objects (continued)
application: Servlets and JSPs store persistent data in the ServletContext
object. The application variable is the ServletContext object.
config: This variable is used to store the ServletConfig object for the page.
pageContext: The pageContext object is used to give a single point of access to page
attributes.
page: The page object is a synonym for this. It is useful if the JSP is not scripted in
Java.

Oracle 10g: Build J2EE Applications 8-15


Example

Copyright © 2005, Oracle. All rights reserved.

Example
You have learned about declarations, expressions, and scriptlets. This slide shows the result
of putting them all together. The code for the example is as follows:
<%@ page contentType="text/html;charset=windows-1252"%>
<html>
<head><meta http-equiv="Content-Type" content="text/html;
charset=windows-1252">
<title> Declaration Expression and Scriptlet </title>
</head><body bgcolor="pink">
<h3> Declarations </h3>
<b> Declare i </b> &lt%! private int i=3; %&gt
<%! private int i=3; %> <br>
<b> Declare Strings a and b </b>&lt%! private String a="Hello",
b=" World"; %&gt
<%! private String a="Hello", b=" World"; %>
<h3> Expressions </h3>
&lt%= i+1 %&gt <b> output </b>
<%= i+1 %> <br>&lt%= a + b %&gt
<b> output </b>
<%= a + b %>

Oracle 10g: Build J2EE Applications 8-16


Example (continued)
<h3> Scriptlet </h3>
&lt% if (i<3 out.print("i<3");
<br> if (i==3) out.print("i==3"); <br>
else out.print("i>3"); %&gt
<b> output </b>
<% if (i<3)out.print("i<3");
if (i==3)out.print("i==3");
else out.print("i>3"); %>
</body> </html>

Oracle 10g: Build J2EE Applications 8-17


Directives

• Are used to set global values such as class


declaration, method implementations, and so on
• Begin with the sequence <%@
• End with the sequence %>
• Are of the following types:
– page
– include
– taglib

Copyright © 2005, Oracle. All rights reserved.

Directives
JSP directives contain messages to the JSP container. They are used to set global values. All
the directives have the scope of the JSP that contains the directives.
The page directive: The page directive is used to define important attributes for a JSP.
You can include a page directive any number of times in a JSP. You learn about the
various attributes of the page directive later in this lesson.
The include directive: This directive is used to include files in the current JSP. The file
output occurs at the location of the directive in the JSP file. Whatever file you include is
interpreted when the JSP is translated into a servlet. Typically, you use the include
directive to include files that rarely change (such as a navigation bar). For example:
<%@ include file=“/navigation.jsp” %>
You cannot include another dynamic page with the include directive.
The URL that is specified for the file is interpreted relative to the path of the JSP page.
The taglib directive: This directive is used to specify custom markup tags.

Oracle 10g: Build J2EE Applications 8-18


include: Example

Copyright © 2005, Oracle. All rights reserved.

include: Example
The slide shows the result of including an HTML page in a JSP. The include directive is
used to include the file, and the file attribute is used to hold the path of the file. The
HTML file is included as follows:
<HTML><HEAD>
<META HTTP-EQUIV="Content-Type" CONTENT="text/html;
charset=windows-1252"/>
<TITLE>untitled</TITLE>
</HEAD><BODY >
<b><font color="red" size="3" >CONTENT FROM INCLUDED FILE
</font> </b>
</BODY>
</HTML>
The JSP code that is used to include the file is as follows:
...
<body>
<b>Including the content from a file here, using the &lt%@
include file=" " %> tag </b>
<br><%@ include file="includefile.html" %>
</body> ...

Oracle 10g: Build J2EE Applications 8-19


page Directive

You can define the following attributes by using the


page directive:
• import • extends
• contentType • info
• isThreadSafe • errorPage
• session • isErrorPage
• buffer • language
• autoflush

Copyright © 2005, Oracle. All rights reserved.

page Directive
The page directive can specify several attributes for the JSP:
• import: This attribute takes a list of packages or classes, separated by commas, that
must be imported by the servlet class created for a JSP.
• contentType: This attribute sets the Multipurpose Internet Mail Extensions
(MIME) type for the response of the JSP. The default is text/html.
• isThreadSafe: If this attribute is set to “false,” then the client requests are queued
for processing because the generated servlet implements SingleThreadModel.
The default value is “true.”
• session: If this attribute value is false, a client’s request is not associated with a
session. The default value for a session attribute is “true.”
• buffer: The buffer attribute can take a size in KB or the value none for the
amount of data that is to be buffered before the page is sent to the client. The default is
8 KB.
• autoFlush: If the autoFlush attribute is set to “false,” a run-time exception is
raised to indicate buffer overflow. The default value is “true,” in which case the buffer
to the client is flushed automatically when it is full.

Oracle 10g: Build J2EE Applications 8-20


page Directive (continued)
• extends: The extends attribute is used to specify the class name that the
generated servlet class must extend.
• info: This attribute is used to define a string that can be retrieved from the generated
servlet by using the getServletInfo() method.
• iserrorPage: This attribute is used to specify whether or not the JSP is an error
page. If it is an error page, then the implicit variable exception is available. This
page can be invoked by another JSP when an unchecked run-time exception is thrown.
• errorPage: This attribute defines the URL to another JSP, which is an error page
that is invoked when an unchecked run-time exception is thrown.
• language: This attribute defines the scripting language that is to be used in JSP.

Oracle 10g: Build J2EE Applications 8-21


JSP and JavaBeans

package lesson08;
import java.lang.*;
import java.util.*;
public class LuckyNumberBean {
private int luckyNum;
public LuckyNumberBean() {
luckyNum = (int) (1000 * Math.random());
}
public int getLuckyNum() {
return luckyNum;
}
public void setLuckyNum(int luckyNum) {
this.luckyNum = luckyNum;
}
}

Copyright © 2005, Oracle. All rights reserved.

JSP and JavaBeans


It has already been mentioned that JSP is component-centric. You can use reusable
components, such as JavaBeans, in a JSP. JSP provides tags to use JavaBeans. In simple
applications, a JSP includes the presentation logic as well as the business logic. The Date
JSP is an example of such a page. When there is more code involved, it is important to
separate business logic and presentation logic. You can use JavaBeans to implement the
business logic and return data to the JSP, which in turn formats the data and displays it in the
browser. The following are the benefits of using JavaBeans in JSP pages:
• JavaBeans are reusable components. Therefore, different applications can use these
components.
• Using JavaBeans results in the separation of business logic and presentation logic.
The slide shows an example of JavaBeans. According to the JavaBean specification, a
JavaBean should:
• Have a zero argument constructor
• Have no public instance variables
• Have accessor methods to set/get a value for instance variables
The example shown in the slide has a zero argument constructor. The LuckyNumberBean
has a luckyNum property. getLuckyNum() and setLuckyNum(int ) are the
accessor and mutator methods, respectively, for the luckyNum property.

Oracle 10g: Build J2EE Applications 8-22


Using JavaBeans with JSP

Accessing JavaBeans with the <jsp:useBean> tag:

<jsp:useBean id="myBean" scope="session"


class="lesson08.LuckyNumberBean" />

Copyright © 2005, Oracle. All rights reserved.

Using JavaBeans with JSP


Actions are specific tags that affect the run-time behavior of the JSP and affect the response.
Observe that these tags are in XML format. The action tags in JSP are:
• <jsp:useBean>
• <jsp:setProperty>
• <jsp:getProperty>
• <jsp:include>
• <jsp:forward>
• <jsp:plugin>
• <jsp:param>
<jsp:useBean>, <jsp:setProperty>, and <jsp:getProperty> tags are the
action tags that are used with JavaBeans. The code given in the slide is used to instantiate an
object of the LuckyNumberBean class, and bind it to the myBean variable. The
<jsp:useBean> tag hides the Java syntax and makes it easier to associate request
parameters with Java objects. You can also share the objects among multiple requests.
The attributes of the <jsp:useBean> tag are:
• id: This attribute is used to specify a name for the object of the class.

Oracle 10g: Build J2EE Applications 8-23


Using JavaBeans with JSP (continued)
• scope: This attribute defines the scope of the object. You learn more about this
attribute in the following slide.
<jsp:include>: This tag includes a file (usually .html or .jsp) in a JSP at request
time.
<jsp:include page="{relativeURL | <%= expression %>}" />
<jsp:forward>: This tag is used to send a request to a file. A JSP file can use this tag to
forward the client request to an HTML file, a JSP file, or a servlet for processing.
For example:
<jsp:forward page="{ relativeURL | <%= expression %> }“ />
<jsp:plugin>: This tag downloads a Java plug-in to the client Web browser to execute
an applet or bean:
<jsp:plugin type=" bean| applet " code=" classFileName "
codebase="classFileDirectoryName" [ name=" instanceName "
][ archive="URIToArchive, ..." ][ align=" bottom |top|
middle|left| right" ][ height=" displayPixels " ]
[ width="displayPixels " ][ hspace=" leftRightPixels " ]
[ vspace=" topBottomPixels "][ jreversion="
JREVersionNumber | 1.1 " ] [ nspluginurl="URLToPlugin " ]
[ iepluginurl=" URLToPlugin "] >[ <jsp: params> [ <jsp:
param name=" parameterName " value=" parameterValue " />
]+ </ jsp: params> ][ <jsp: fallback> text message for
user </ jsp: fallback> ]</ jsp: plugin>
<jsp:param>: This tag is used with <jsp:plugin> to specify values for the applet
parameters.

Oracle 10g: Build J2EE Applications 8-24


scope Attribute of <jsp:useBean> Tag
Client
Request Response

Request

Response

Forward

Page 1 Page 2 Page 3

page scope page scope page scope

request scope request scope

session scope

Copyright © 2005, Oracle. All rights reserved.

scope Attribute of the <jsp:useBean> Tag


The scope attribute determines the life of the bean object depending on the context to
which it is bound. The scope attribute can have the following values:
• page: This is the default value. The bean object is placed in the pageContext
object and the servlet code can access it by calling the getAttributes() method
on the predefined pageContext variable.
• request: The bean object is placed in the ServletRequest object. Use the
request object to include the bean from any JSP that is processing the same request
(until the JSP sends a response to the client, or forwards the request to another file).
You can use the request object to access the bean.
• session: The bean object is stored in the HttpSession object that is associated
with the client. It can be retrieved by using the getSession() method.
• application: The bean object is stored in the shared ServletContext. The
ServletContext is shared by all servlets in the same Web application. You can
use the getAttribute() method to retrieve values from ServletContext.

Oracle 10g: Build J2EE Applications 8-25


Accessing and Setting Bean Property

• Accessing bean property:


<jsp:getProperty name="myBean"
property=“luckyNum" />

• Setting bean property:


<jsp:setProperty name="myBean"
property=“luckyNum" value="10" />

Copyright © 2005, Oracle. All rights reserved.

Accessing and Setting Bean Property


Accessing Bean Property
The <jsp:getProperty> action is used to access bean property as shown in the slide.
The value of the name attribute should match the value of the id that is given in the
<jsp:useBean> tag. The property attribute identifies the property of the bean that is
being accessed. You can also use the following code to retrieve the bean property:
<%= myBean.getLuckyNum() %>
You can use this when you are using loops, conditional statements, and so on.
Setting Bean Property
The <jsp:setProperty> action is used to set the bean property. The value of the name
attribute should be the name of the bean instance that is defined by the <jsp:useBean>
tag. The property attribute holds the name of the property that is being changed, and the
value attribute holds the new value for the property.

Oracle 10g: Build J2EE Applications 8-26


Accessing and Setting Bean Property (continued)
The property in a bean can be set:
• From request parameters
• From expressions
• From a specified string
Example:
<jsp:setProperty name="myBean" property="luckyNum"
value='<%= Integer.parseInt(request.getParameter("num"))
%>' />

Oracle 10g: Build J2EE Applications 8-27


JSP XML Document

• Contains <jsp:root> as its root element


• Includes only XML syntax and does not include
the traditional JSP tags
• Can be processed directly by the JSP container
• Can be used with XML development tools

Copyright © 2005, Oracle. All rights reserved.

JSP XML Document


Traditional JSP tags cannot be used within an XML document. JSP 1.1 defines JSP syntax
that is compatible with XML. For example, the XML syntax for a traditional declaration tag
is: <%! %>, is <jsp:declaration> </jsp:declaration>.
In JSP1.1, a JSP can contain both traditional syntax and XML syntax. However, JSP1.2 does
not allow intermixing of these tags in a page. A JSP that contains the XML syntax is called a
JSP XML document or a JSP document. A JSP document is well formed and contains only
the XML syntax. <jsp:root> is the root element of this document. The three important
goals of the root element are:
• Establishing the document as a JSP XML document, so that the JSP container can
process it
• Identifying the namespaces for the XML syntax and custom tag libraries through the
xmlns attribute
• Specifying a JSP version number

Oracle 10g: Build J2EE Applications 8-28


Traditional Syntax Versus XML Syntax

Traditional: XML:
• No root element • <jsp:root> is the root
element
• page directive • <jsp:directive.
<%@ page %> page />
• Declaration tag • <jsp:declaration>
<%! %> </jsp:declaration>
• Expression tag • <jsp:expression>
<%= expression %> </jsp:expression>
• Scriptlet • <jsp:scriptlet>
<% %> </jsp:scriptlet>

Copyright © 2005, Oracle. All rights reserved.

Traditional Syntax Versus XML Syntax


The slide shows the XML syntax for some of the traditional tags described in this lesson.
You have already learned that <jsp:root> is the root element of a JSP document. You
now see how to use the XML syntax in a JSP document.
<jsp:root xmlns:jsp=“http://.....”
xmlns:temp=“http://...”
version=“1.2” >
body elements
</jsp:root>
The page Directive and include Directive
<jsp:directive.page language=“ “ import=“ “ />
<jsp:directive.include file=“ “ />
Declaration Tag
<jsp:declaration>
public void setCount(int i) { if(i &lt; 10) count=i;}
</jsp:declaration>
Expression Tag
<jsp:expression> (user==null)? “ “:user </jsp:expression>

Oracle 10g: Build J2EE Applications 8-29


Traditional Syntax Versus XML Syntax (continued)
Scriptlet
<jsp:scriptlet>
if (request.getParameter(“name”).equals(“ “))
{........}
</jsp:scriptlet>
The JSP action tags, such as <jsp:useBean>, <jsp:forward>, and so on, are XML
compatible.
Text Element
When a JSP container encounters the text element, <jsp:text>, it passes the contents to
the current JSP out object. The code <jsp:text> Hello World </jsp:text>
displays “Hello World” when you run the JSP document.
JSP XML View
In JSP1.2, the JSP document can be directly processed by a JSP container. The container
creates an XML version, called XML view, of the parsing result. This XML view is the
mapping of a JSP (either a traditional page or a JSP XML document) into an XML
document that describes it. The XML view can be used by validator classes to validate a
page.

Oracle 10g: Build J2EE Applications 8-30


JDeveloper and JSPs

• Use the JSP Wizard in JDeveloper to create JSPs


containing skeleton code.
• The structure pane helps to ensure that the JSP
and HTML tags are properly formatted.
• Tag Insight automatically inserts end tags after
starting a scriptlet.
• JSP code is automatically created and recompiled.
• JDeveloper increases productivity while
debugging JSPs:
– Automatically includes source Java files such as
your JavaBean source
– Enables you to set breakpoints and watch
expressions in JSPs

Copyright © 2005, Oracle. All rights reserved.

JDeveloper and JSPs


JDeveloper gives you many tools for simplifying your JSP development.
• The JSP Wizard creates a JSP that contains skeleton code.
• The Structure Pane and Tag Insight features help you develop syntactically correct
JSPs.
• When you launch your JSP, the code is re-created when needed, and recompiled.
• The integrated debugger enables you to systematically run the JSP that you have
written, while viewing the generated servlet code and any JavaBeans.

Oracle 10g: Build J2EE Applications 8-31


Creating JSPs Visually

Copyright © 2005, Oracle. All rights reserved.

Creating JSPs Visually


JDeveloper 10g provides a visual editor for creating JSPs and HTML. This makes
development much easier because you drag items from the component palette to the visual
editor, and the elements are rendered appropriately. HTML tables are quickly created and
modified, and text can be modified much like an HTML authoring tool. Additionally,
rendering styles from CSS style sheets is supported, and you can drag images from the file
system to the visual editor. The design and source views are synchronized so that a change
in one editor is immediately propagated to the other.

Oracle 10g: Build J2EE Applications 8-32


JSP Tag Insight

Copyright © 2005, Oracle. All rights reserved.

JSP Tag Insight


When using the code editor, you need not remember complicated syntax and another
language because the Tag Insight feature is provided to aid development. In this example,
the developer entered <jsp:, and the tag insight selection list appeared with all valid tags.

Oracle 10g: Build J2EE Applications 8-33


Summary

In this lesson, you should have learned how to:


• Differentiate between servlets and JSPs
• Build a simple JSP
• Describe the JSP life cycle
• Use JSP elements and implicit objects
• Develop JSPs with declarations, expressions, and
scriptlets
• Use JavaBeans with JSP

Copyright © 2005, Oracle. All rights reserved.

Summary
In this lesson, you should have learned about the various elements of a JSP. You should also
have learned how to use Oracle JDeveloper 10g to build JSPs.

Oracle 10g: Build J2EE Applications 8-34


Practices 8-1, 8-2, and 8-3: Overview

These practices cover the following topics:


• Creating a JSP that counts the occurrence of each
character in a given string
• Using JavaBean to calculate an equal discount on
the total amount of purchase
• Creating a JSP that displays product_id,
product_name, and price in the form of a table

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 8-35


Practice 8-1
The purpose of this practice is to familiarize you with expressions and scriptlets that you
have learned in the lesson. You generate a simple HTML form that displays a text field and
a Submit button. Name this form Form.html. Develop a Charcounter.jsp file that
counts the occurrence of each character in a string. The HTML form should invoke the
Charcounter.jsp file when the string is entered in the text field, and the Submit button
is clicked. The JSP should obtain the string and count the occurrence of each character and
display the characters. Open the practice08.jws workspace and navigate to the
countchars project.
1. Generate the Charcounter.jsp file:
a. Right-click countchars and select New. Expand the Web Tier node under
Categories.
b. Select JavaServer Pages under Web Tier and select JSP Page from Items. Click
OK.
c. Enter Charcounter.jsp in the File Name field. Click OK. You see the JSP
file in the Web Content folder.
2. Edit the Charcounter.jsp file:
a. Select the CSS category from the Component Palette, and drag the Oracle style
sheet to the page.
b. Switch to the Source view and change the title to “Character Counter.”
c. Add code to declare the following variables (use the scriptlet tag):
- A string (inputString) to hold the input parameter
- A character array (inputArray) to hold the characters of the string
- An integer (len) to hold the length of input string
- An integer array (count) and a character array (c), both with sizes equal to
the length of the string
- An integer (lastpos)
- A Boolean variable (done) initialized to false
d. Add code to count the occurrences of each character in the string and display it.
Use the scriptlet tag to code the logic.
Note: You can implement the logic to count the occurrences of characters in
different ways. The solution provided for this practice is only one way of doing
it.
3. Open Form.html in the visual editor:
a. Select HTML from the Component Palette and insert tags to create a form that
displays a text box with a name attribute of “input”, and a Submit button.
b. Select the form in the visual editor and change the value of the action attribute in
the Property Inspector to Charcounter.jsp.
4. Test and run the application:
a. Run the Form.html file: Right-click Form.html in the System Navigator
and select Run.
b. Enter a string in the text field and press [Enter] or click the Submit button.

Oracle 10g: Build J2EE Applications 8-36


Practice 8-1 (continued)
5. Sample Input/Output
- Input: STATISTICS
- Output: S 3
T 3
A 1
I 2
C 1

Oracle 10g: Build J2EE Applications 8-37


Practice 8-2
The purpose of this practice is to use JavaBeans in JSPs. You develop a JavaBean,
DiscountBean.java, which calculates equal discount on the total amount of purchase
and returns the new price. You also design a JSP, CallDiscountBean.jsp, which uses
the JavaBean. The total amount of purchase (original price) is passed with the URL to the
JSP. The JSP then invokes the bean method, which calculates the price after discount by
passing the price, and displays the price after discount. Navigate to the discountbean
project in practice08.jws.
1. Open DiscountBean.java in the code editor:
a. Add code to declare three instance variables: discount, price, and
priceAfterDiscount of double type. Initialize discount to 10.5.
b. Implement the set() method for price. Optionally, you can also implement
the get() method.
c. Implement the get() method for priceAfterDiscount. Write code to
calculate the price depending on the value of discount and return the new
price.
2. Open the CallDiscountBean.jsp file in the editor. Look for comments and
insert the tags as instructed, using either the design or source view:
a. Insert an expression to get the price from the URL.
b. Declare a string called price with the declaration tag and write a scriptlet to get
the value of parameter price from the URL and assign it to the string price.
c. Insert a useBean tag to instantiate the DiscountBean class.
d. Insert a JSP expression to display the price.
e. Insert the setProperty tag to set the value of price.
f. Insert the getProperty tag to get the price after discount.
3. Test and run the application:
a. Run CallDiscountBean.jsp: Right-click CallDiscountBean.jsp in
the System Navigator and select Run.
b. You see java.lang.NullPointerException because you have not
passed any parameter. Note the target URL for this JSP and append the following
to the URL in the browser to invoke the JSP:
?price=1000
4. Sample Input/Output:
a. Input: <target-url>?price=1000.
For example: http://localhost:8988/practice08-
discountbean-context-root/
CallDiscountBean.jsp?price=1000
b. Output:
USING A JAVABEAN TO CALCULATE PRICE AFTER DISCOUNT FOR
A PURCHASE OF $1000
price before discount: 1000$
price after discount: 895.0$

Oracle 10g: Build J2EE Applications 8-38


Practice 8-3
The purpose of this practice is to create a JSP that interacts with a database by using JDBC.
You design a JSP to display PRODUCT_NAME and LIST_PRICE from the
PRODUCT_INFORMATION table. The information about the products is displayed in
the form of a table. The Java class ProductInfo is responsible for retrieving the data
from the database and returning the productnames and listprice in the form of
vectors. This class contains get() methods to retrieve the vector. The product.jsp
file invokes the get() method to obtain the details and display them in the form of a
table. Navigate to the product project in practice08.jws.
Note: Use the oe database connection that you created in Practice 5-1.
1. Set up the project to use this connection (optional):
a. Right-click the web.xml file in product.jpr and select Properties.
b. Select Resource Environment References and click Add to add this connection to
the project as a data source.
c. Name the environment reference jdbc/oeDS and specify the type as
javax.sql.DataSource.
d. You are now able to look up this data source reference by using jdbc/oeDS.
2. To add the Oracle JDBC library to the project, double-click the product project and
navigate to the Libraries tab under the Development node. Add the Oracle JDBC
library to the Selected Libraries for the project.
3. Open ProductInfo.java in the code editor:
a. Import the java.sql, javax.sql, javax.naming, and java.util
packages.
b. Declare the following private variables:
Vector productnames and listprice
ResultSet rs
Statement st
Connection c
c. Implement an establishConnection() method with no parameters, and
void as return type. This method should establish the JDBC connection to the oe
schema with the data source oeDS that you created in practice 5.
Start a try block. Create a Context object.
Look for the data source jdbc/oeDS and create an instance of data source, ds.
Call the getConnection()method on the ds data source object using the
Connection object c you declared in previous step. Create the statement
object with this connection. Close the try block. The operations can throw
SQLException or NamingException. Provide catch blocks for
SQLException and NamingException.
d. Create a new method to close the Connection at the end of the processing. The
method should be public, return void and be named closeConnection.
Create a try block. Inside the block call the close() method on the
connection object. Add a catch block to catch any Exception object. If there
is an Exception caught, call system.out.println() and issue a message that shows
an error closing the connection.

Oracle 10g: Build J2EE Applications 8-39


Practice 8-3 (continued)
e. Implement a private method getData() with no arguments, and void as the
return type. Initialize productnames and listprice declared earlier.
Start a try block. Use the Statement object created in the
establishConnection() method to execute a query. This query should
select product_name, and list_price from the
PRODUCT_INFORMATION table where product_status is orderable and
list_price is not null. Populate the productnames Vector with the
product_name in the Resultset, and listprice Vector with
list_price in the result set. Close the try block. Provide a catch block to
catch a generic exception.
f. Invoke the methods establishConnection(), getData(), and
closeConnection()in the constructor.
g. Implement the getProductnames()method, which returns Vector
productnames.
h. Implement the getListprice()method, which returns Vector
listprice.
4. Open Product.jsp:
a. Include page directive to import the product package, which contains the
ProductInfo class. Also, import the java.util package.
b. Include a scriptlet tag to do the following:
Instantiate the ProductInfo class.
Declare two variables, productnames and listprice, of Vector type.
Invoke the getProductnames()and getListprice()methods of the
ProductInfo class to populate productnames and listprice
respectively. Enumerate through the Vector elements and add the elements as
rows to the table.
5. Test and run the application: Right-click Product.jsp and select Run.

Oracle 10g: Build J2EE Applications 8-40


Modularizing JavaServer Pages
Development with Tags

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Define a custom tag
• Use custom tags in a JavaServer Page (JSP)
• Use the customizable Component Palette for JSP
• Develop a JSP using the JSP Standard Tag Library
(JSTL)

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson discusses the use of custom tags in JSPs.

Oracle 10g: Build J2EE Applications 9-2


Custom Tags

• Custom tags are developed in Java and defined


and used with XML syntax.
• Tags are used in a JSP to reduce or constrain the
amount of Java scriptlets in the page.
• Tags are useful for defining custom actions such
as:
– Accessing a database
– Defining recurring tasks
– Sending e-mail
• Collections of tags are grouped into JAR files
called Tag Libraries.

Copyright © 2005, Oracle. All rights reserved.

Custom Tags
Custom tags are a feature of JSP 1.1 and later versions. Custom tags enable you to create
your own tags for use in JSP applications. Tags provide encapsulation of complex behaviors
much like JavaBeans, but they can also manipulate JSP content. This is useful because JSPs
can often have a large amount of scriptlet code to maintain, and can eventually lose their
reusability. Custom tags are useful because they have simpler syntax than scriptlets and are
reusable. Therefore, they can be developed by Java programmers and used in JSPs by Web
application developers using XML syntax.
Similar to HTML tags, there are custom tags without a body:
<tagName attribute1="value1" attribute2="value2" />
There are also tags that have matching end tags and, therefore, include a body:
<tagName attribute1="value1" attribute2="value2" >
…tag body…
</tagName>
Note that both types of tags may have attributes to customize the behavior of the tags.

Oracle 10g: Build J2EE Applications 9-3


Custom Tag Library Components

Custom Tag Libraries contain:


• One or more tag handler class files
– May contain additional supporting classes
• A tag library descriptor (taglib.tld)
– XML formatted
To use a tag in a JSP, perform the following:
1. Invoke the tag library by using the
<jsp:taglib/> directive.
2. Call the tag in the content of the JSP.
3. Include the location of the taglib.tld file in the
web.xml file.

Copyright © 2005, Oracle. All rights reserved.

Custom Tag Library Components


Custom Tag Libraries contain two main components: one or more tag handler classes (Java
class files) and a tag library descriptor (an XML file). The tag handler class defines the
custom tag itself. The tag library descriptor contains the metadata about the tag, the tag
name, the tag location, and the tag attributes. To use a tag in a JSP, the Web developer
invokes the tag library by using a special JSP directive, taglib. This directive points to the
location of the tag library descriptor, or .tld file. Tags contained within that library are
available for use by specifying the name of the class. Additionally, existing tags can be
added to a library by defining them in an existing .tld file. Tag libraries should be
declared in a <taglib> element in the web.xml file for a JSP application, as follows:

<taglib>
<taglib-uri>/webapp/mytaglib</taglib-uri>
<taglib-location>/WEB-INF/taglib.tld</taglib-location>
</taglib>

Oracle 10g: Build J2EE Applications 9-4


Tag Handler: Example

import javax.servlet.jsp.*;
import javax.servlet.jsp.tagext.*;
import java.io.*;
public class HelloWorldTag extends TagSupport {
public int doStartTag() {
try {
JspWriter out = pageContext.getOut();
out.print("Hello from Custom Tag!!!");
}
catch(IOException io) {
System.out.println("Error in TagMessage: " + io);
}
return(SKIP_BODY);
}
public int doEndTag() {
return (SKIP_PAGE);
}
}

Copyright © 2005, Oracle. All rights reserved.

Tag Handler: Example


The HelloWorldTag tag handler contains the doStartTag() and doEndTag()
methods. The doStartTag() method returns SKIP_BODY because the tag has no body.
The doEndTag() method returns SKIP_PAGE because you do not want to evaluate the
rest of the page. If the tag has a body, doStartTag() returns EVAL_BODY_INCLUDE. If
the rest of the page needs to be evaluated, doEndTag() returns EVAL_PAGE. More
information about the doStartTag() and doEndTag() methods is available at:
http://java.sun.com/products/jsp/taglibraries.html.
Note that the JSPWriter for this tag is obtained from the JSP pageContext. Request,
response, and session information can also be obtained from the JSP pageContext.

Oracle 10g: Build J2EE Applications 9-5


Tag Library Descriptors

A tag library descriptor (.tld) is an XML document


that describes one or more tags and their attributes. It
contains the following elements:
<tlibversion> The tag library’s version
<jspversion> The JSP specification version for the library
<shortname> A default name for the library
<uri> Identifies the tag library location
<info> Documentation regarding the library
<tagclass> Specifies the class for the individual tag
<bodycontent> Set to empty, tagdependent, or JSP

Copyright © 2005, Oracle. All rights reserved.

Tag Library Descriptors


The tag library descriptor for HelloWorldTag is listed below. Note that the
bodycontent element can have three values, empty (indicating that the tag has no
body), tagdependent (the body of the tag is handled by the tag itself), or JSP,
(indicating that the JSP container should evaluate the body of the tag). Additionally, many
tags can be defined in one .tld file.
<taglib xmlns = "http://java.sun.com/j2ee/dtds/web-
jsptaglibrary_1_1.dtd">
<tlibversion>1.0</tlibversion>
<jspversion>1.1</jspversion>
<shortname>mytags</shortname>
<tag>
<name>hellotag</name>
<tagclass>HelloWorldTag</tagclass>
<bodycontent>empty</bodycontent>
</tag>
</taglib>

Oracle 10g: Build J2EE Applications 9-6


Using a Custom Tag

<html>
<head>
<%@ taglib uri="webapp/taglib.tld"
prefix="mytags" %>
</head>
<body>
<h2>The following output is from the
HelloWorldTag:</h2>
<p>
<mytags:hellotag/>
</p>
</body>
</html>

Copyright © 2005, Oracle. All rights reserved.

Using a Custom Tag


Use the taglib directive to specify that a JSP will use a tag that is defined in a tag library
(.tld) before any custom tag is called. The uri attribute refers to the location (relative or
absolute) of the tag library descriptor. The prefix attribute specifies the tag library that is
to be used in the JSP. This typically corresponds to the value of the shortname element in
the descriptor, but can be any valid string. The example in the slide declares that the tags
described in taglib.tld will be used in this JSP. The tag is then called by using
<mytags:hellotag>. This indicates that the tag named hellotag will be called from
the taglib.tld library. Note that this tag does not contain attributes.

Oracle 10g: Build J2EE Applications 9-7


Tags with Attributes

Tags with attributes should include the get() and


set() methods for each attribute in the tag handler.
• The tag library descriptor defines each attribute.
• Supporting classes can validate attributes.
<tag> <name>hellotag</name>
<tagclass>HelloWorldTag</tagclass>
<bodycontent>empty</bodycontent>
<attribute>
<name>custName</name>
<required> true</required>
<rtexprvalue>true</rtexprvalue>
</attribute> </tag>

Copyright © 2005, Oracle. All rights reserved.

Tags with Attributes


To create a tag that contains attributes, the tag handler uses the
pageContext.setAttribute(name, value) and
pageContext.getAttribute(name) methods to create and set the value of the
expression.
The descriptor gives the attribute a name, specifies if the attribute is required, and indicates
whether the value can be determined at run time (usually via a JSP expression). The attribute
could be set in the JSP by using the following syntax:
<mytags:hellotag custName="<%=custName%>" />
To validate the value of attributes, a supporting class called a TagExtraInfo class is
created for the tag handler. The isValid() method can be used to check the attribute
values at the time of page translation. More information about the isValid() method and
the use of TagExtraInfo classes is available at:
http://java.sun.com/products/jsp/taglibraries.html.

Oracle 10g: Build J2EE Applications 9-8


Creating a Custom Tag in JDeveloper

To create a custom tag and a tag library in JDeveloper,


perform the following:
1. Create a tag library descriptor from the JavaServer
Pages category.
2. Right-click the .tld file in System Navigator and
select “Add Tag” to create a tag handler.
3. Right-click the .java file in System Navigator and
select “Add Attribute” or “Add Scripting Variable”
as necessary.
4. Add the tag library to the component palette.

Copyright © 2005, Oracle. All rights reserved.

Creating a Custom Tag in JDeveloper


To create a new custom tag and library in JDeveloper, first create the tag library descriptor.
Next, right-click the .tld file in System Navigator and select “Add Tag.” This invokes a
wizard that creates the skeleton code for a tag handler, and automatically adds it to the
.tld file. The tag handler can then be modified as necessary, and attributes and scripting
variables can be automatically added to the code (and defined in the .tld file) by right-
clicking the tag handler in System Navigator. Finally, the tag library can be added to the
JDeveloper IDE to aid in using the tag library in JSPs. Tag libraries are contained in
JDeveloper in the customizable component palette.

Oracle 10g: Build J2EE Applications 9-9


Tag Libraries in JDeveloper

• Tag libraries are viewed in JDeveloper by using


the component palette.
• Select View > Component Palette to enable the
palette in the integrated development environment
(IDE).

Copyright © 2005, Oracle. All rights reserved.

Tag Libraries in JDeveloper


To use custom tags in JSP applications, Oracle JDeveloper 10g provides a customizable
component palette. When you select View > Component Palette while working in a JSP, the
palette displays valid JSP tags. Additionally, you can add custom tag libraries to the
component palette by registering them in JDeveloper. You can then use these tags by
placing your cursor at the insertion point in the JSP and by clicking the tag that you want to
use in the palette. Note that you can add any tag libraries to the component palette, whether
custom-made by you, downloaded, or purchased, as long as they are contained in a .jar
file.

Oracle 10g: Build J2EE Applications 9-10


Registering Tag Libraries

To add a tag library to the component palette, perform


the following:
1. Select Tools > Configure Palette.
2. Add a new palette page.
3. Name the page for display.

Copyright © 2005, Oracle. All rights reserved.

Registering Tag Libraries


Custom tag libraries can be added to the component palette in the Palette Properties dialog
box. First, you must create a new page for the custom tags. This step is shown below.

Oracle 10g: Build J2EE Applications 9-11


Registering Tag Libraries

4. Select Tools > Manage Libraries.


5. Add the JAR and TLD files to the list of JSP Tag
Libraries.

Copyright © 2005, Oracle. All rights reserved.

Registering Tag Libraries (continued)


To add a tag library, create a new reference to the JAR file by selecting Manage Libraries
from the Tools menu. Specify the JAR file and the .tld file. Click Yes to add the
components, then specify the page you previously created.

Oracle 10g: Build J2EE Applications 9-12


Registering Tag Libraries

Copyright © 2005, Oracle. All rights reserved.

Registering Tag Libraries (continued)


The slide shows the component palette after the library named taglib is installed on the
“Demo Tags” page. These tags can now be used in a JSP by placing the cursor at the desired
point of insertion and by selecting the tag in the component palette. If there are any
attributes for the tag, then a dialog box for entering attribute values is displayed as shown:

Oracle 10g: Build J2EE Applications 9-13


Using Tag Insight

Copyright © 2005, Oracle. All rights reserved.

Using Tag Insight


Tag insight is a feature of JDeveloper that enables you to enter the prefix of a custom tag
and view all available tags for that library. Tag insight becomes available for a tag library
after it is registered in JDeveloper. This enables you to select the tag that you want to use
from a list. Additionally, tag attributes are displayed in a list after the tag has been selected.
The slide above displays the tag insight list when <taglib: is entered into a JSP.
Attributes for the tag are introspected from the .tld file, and available from tag insight
as well.

Oracle 10g: Build J2EE Applications 9-14


JSP Standard Tag Library (JSTL)

The JSP Standard Tag Library (JSTL) was developed


under the Java Community Process. It provides a
common and standard set of custom tags for:
• Iteration, conditional processing, and expression
language support
• Parsing and transforming XML documents
• Formatting and parsing strings, dates, and
currencies for internationalization
• Database access and data manipulation

Copyright © 2005, Oracle. All rights reserved.

JSP Standard Tag Library (JSTL)


The following four tag libraries are included in JSTL:
1. Core: Tags for iteration and conditional processing, including expression language
support
2. XML: Parsing and transforming tags for use with XML documents
3. SQL: Tags for accessing and manipulating table data
4. i18N: Provides tags for formatting and parsing data for internationalization

Oracle 10g: Build J2EE Applications 9-15


Core Tag Library

The Core library of JSTL is used for typical JSP


actions.
• Reduces the need for scriptlet tags in a JSP
• Contains four types of tags:
– Generic (sets variables and display results of
expressions)
– Conditional (makes blocks of code dependent on
some criteria)
– Iteration (repeats actions on blocks of code)
– URL-related (creates URLs for linking or redirection)
Use the prefix "c" in the taglib directive:
<%@ taglib uri="http://java.sun.com/jstl/core"
prefix="c" %>

Copyright © 2005, Oracle. All rights reserved.

Core Tag Library


The Core library of JSTL is used for typical JSP actions. Its purpose is to reduce the need for
scriptlet tags in a JSP, which make JSPs difficult to read and maintain. Each of the four
types of Core tags have several tags for use in JSPs, listed on the following page.

Oracle 10g: Build J2EE Applications 9-16


Core Tag Library (continued)

<c:out> Displays the result of an expression, string, or the


evaluation to the current JspWriter object

<c:set> Sets a variable in a page and, optionally, sets the


Generic scope of the variable
<c:remove> Removes a scoped variable
<c:catch> Catches a java.lang.Throwable exception
thrown by any nested actions
<c:if> Evaluates the body content if the expression specified
is true
<c:choose> Provides the context for conditional execution
<c:when> Is nested in <c:choose>, and evaluates the body
Conditional content if the expression specified is true
<c:otherwise> Is nested in <c:choose>, and evaluates the body
content if none of the tests in the <c:when> blocks
are true. It must be listed after all <c:when> tags.
<c:forEach> Repeats the action in the body content through a
Iteration collection’s elements
<c:forTokens> Repeats the action in the body content through tokens
<c:import> Includes the content of the URL that is specified in
the JSP
URL- <c:redirect> Redirects the client
related
<c:url> Builds a URL by using the correct rewriting
principles
<c:param> Is nested inside <c:import>, <c:redirect>, or
<c:url>, and adds request parameters to the URL

Oracle 10g: Build J2EE Applications 9-17


Utilizing Core Tags

• Use the <c:out> and <c:set> tags within your


JSP to display and create variables. The value
attribute defines what will be displayed or created
as a variable:
<c:out value="Hello World" />
<c:set var="name" value="${param.username}"
scope="session" />
Welcome <c:out value="${name}"
default="guest" />

• The value attribute of the <c:set> tag uses


Expression Language (EL).

Copyright © 2005, Oracle. All rights reserved.

Utilizing Core Tags


In this example, the <c:out> tag displays a string. The <c:set> tag is used to create a
variable by using the username request parameter. The user is welcomed by using the
name variable. If there is no value for the username request parameter, then the value of
name will be null. Therefore, the default attribute of <c:out> is used to display the
text “guest” if the username request parameter is null.
Other tags:
Use the <c:remove> tag to remove a variable from the page:
<c:remove var="name" />
The <c:catch> tag is used to declare uniform error handling in a JSP. This tag can work
in conjunction with the errorPage and isErrorPage directives. For example, not
every error needs to be handled by the defined error page. Thus, the <c:catch> tag can be
used to design user-friendly error messages

Oracle 10g: Build J2EE Applications 9-18


Expression Language

JSTL tags can contain Expression Language (EL)


within attributes. Expression Language:
• Is a simpler way of writing an expression in JSPs
• Accesses object properties and collection
elements using dot notation
• Has access to implicit objects
• Uses a dollar sign and braces to create an
expression: ${expression}
<c:set var="name" value="${param.username}"
scope="session" />
Welcome <c:out value="${name}"
default="guest" />

Copyright © 2005, Oracle. All rights reserved.

Expression Language
Expression Language (EL) is an alternative to expressions. EL uses a dollar sign and braces
to create an expression. There are several benefits of using ${expr} over <%=expr%>:
1. If the value of the expression is null, it evaluates to an empty string. This is most
beneficial for eliminating null pointer exceptions when users do not enter parameter
values correctly.
2. Object properties, collection elements, and JavaBean properties are easy to reference
by using the dot notation.
3. Several implicit objects are available for easy access to JSP objects, including:

pageContext pageScope
requestScope sessionScope
applicationScope param
paramValues header
headerValues cookie

Oracle 10g: Build J2EE Applications 9-19


Using Iteration Tags

Use iteration tags to iterate over blocks of code:

<table>
<tr>
<c:forEach var="allparams" items="${param}" >
<c:out value="${allparams.key}" />
</c:forEach><tr>
<table>

Copyright © 2005, Oracle. All rights reserved.

Using Iteration Tags


There are two tags for iterating in the JSTL Core Library: <c:forEach> and
<c:forTokens>. You can use <c:forEach> to iterate over objects in a collection, or
to iterate a fixed number of times, as shown in the slide. Use the <c:forTokens> tag to
iterate over a collection, specifying the delimiter. For example, the code below iterates over
a comma-delimited string to display the output:
<table>
<tr>
<c:forTokens items="7,14,15,26,42" delims="," var="luckyNumber">
<c:out value="${luckyNumber}" /> </c:forTokens><tr>
<table>

Oracle 10g: Build J2EE Applications 9-20


Using the URL Tags

The following three tags exist for working with URLs:


• <c:import>: Accesses resources by specifying a
URL. It is preferred over the <jsp:include>
directive, because <c:import> can:
– Access URLs that exist outside the same context as
the current page’s Web application context
– Access a relative URL with a foreign Web
application context
– Include FTP resources
• <c:url>: Handles encoding and rewriting of URLs
• <c:redirect>: Redirects the client request

Copyright © 2005, Oracle. All rights reserved.

Using the URL Tags


You can use the <c:import> tag to access the resources by specifying a URL. This
provides greater flexibility than the <jsp:include> directive. Specify the URL in the
url attribute of the <c:import> tag:
<c:import url="http://www.oracle.com" />
<c:import url="/copyright.html" />
<c:import url="/copyright.html" context="/anotherwebapp" />
Using the <c:url> tag makes it easier to handle encoding and rewriting of URLs. This tag
takes a value, variable, context, and optional scope attribute. Additionally,
parameters can be appended to the URL by using the <c:param> tag. For example:
<c:url value="http://companyname.com/login" var="loginUrl" >
<c:param name="username" value="${param.name}" />
</c:url>
<a href ='<c:out value="${loginUrl}"/>'> Log In</a>

Oracle 10g: Build J2EE Applications 9-21


Using the URL Tags (continued)
Additionally, the <c:redirect> tag can be used to redirect the client’s request, and can
include URL parameters:
<c:redirect value="/processlogin >
<c:param name="username" value="${param.name}" />
<c:param name="password" value="${param.pw}" />
</c:redirect>

Oracle 10g: Build J2EE Applications 9-22


XML Tag Library

The XML tag library is used to parse and transform


XML documents.
• XML tags in JSTL conform to XPath syntax.
• XML tags include <x:out>, <x:set>, and other
tags similar to the core tag library, in addition to:
– <x:parse> : Parses a specified XML document
– <x:transform> : Creates a formatted page from an
XML source document by using an XSLT stylesheet
– <x:param> : Sets transformation parameters
(nested in <x:transform>)
Use the prefix "x" in the taglib directive:
<%@ taglib uri="http://java.sun.com/jstl/xml"
prefix="x" %>

Copyright © 2005, Oracle. All rights reserved.

XML Tag Library


The XML tag library in JSTL is useful for working with XML documents. The library
conforms to the XPath syntax. This means that you can easily reference hierarchical
information within an XML document in the XML tags. In addition to the iterative and
conditional tag types, similar to the core tag library, the XML tag library contains the
<x:parse>, <x:transform> and <x:param> tags for parsing and transforming XML
documents. To use the xml tags in a JSP, include the taglib directive in the JSP as
follows:
<%@ taglib uri="http://java.sun.com/jstl/xml" prefix="x" %>
The following is an example of parsing an XML document that is located at
http://www.oracle.com/xmlfile.xml, retrieving data from the file, and outputting values
using an XPath expression:
<c:import url="http://www.oracle.com/xmlfile.xml" var="xml"/>
<x:parse source="${xml}" var="doc"/>
<x:out select="$doc/description"/>

Oracle 10g: Build J2EE Applications 9-23


SQL Tag Library

The SQL Tag Library contains tags for testing


database applications.
• Only used for prototyping or low-volume
applications
Use the prefix “sql” in the taglib directive:
<%@ taglib
uri=http://java.sun.com/jstl/sql
prefix="sql" %>

Copyright © 2005, Oracle. All rights reserved.

SQL Tag Library


Many JSP developers wanted an easier way to create database connections and to insert and
update records. JSTL is one of the tag libraries that has attempted to answer this
requirement. However, JSTL’s SQL tag libraries do not provide connection pooling.
Therefore, JSTL SQL tags should be used for low-volume database applications or for
prototyping, but other database access elements should be used for large-scale applications.
There are six tags in the SQL tag library:

<sql:setDataSource> Creates a connection to the specified data source


<sql:query> Queries the database by using the statement in the body of
the tag
<sql:update> Inserts, updates, or deletes by using the statement in the
body of the tag
<sql:param> and Sets the value for “?” style parameters within
<sql:dateParam> <sql:query> or <sql:update>
<sql:transaction> Allows the content of a nested <sql:query> or
<sql:update> statement to be rolled back if errors occur

Oracle 10g: Build J2EE Applications 9-24


Accessing a Database with SQL Tags

To access a database from the SQL tags, you can


either:
• Reference a defined J2EE data source by name in
the <sql:query> or <sql:update> tags
Or
• Create a data source by using a
<sql:setDataSource> tag:
<sql:setDataSource
driver="oracle.jdbc.driver.OracleDriver"
url="jdbc:oracle:thin:@localhost:1521:ORCL"
user="oe" password="oe" var="myDS" />

Copyright © 2005, Oracle. All rights reserved.

Accessing a Database with SQL Tags


If a data source is not already defined in the J2EE container, then you can create it by using
the <sql:setDataSource> tag, as shown in the slide. This example uses the driver
and url attributes to find the database, and the user and password attributes to connect
to the database. The var attribute creates a variable for this data source to be used in the
datasource attribute of the <sql:update>, <sql:query>, and
<sql:transaction> tags.
To specify isolation for a SQL transaction, use the <sql:transaction> tag. This tag
has two attributes: dataSource and isolation. The dataSource attribute value
may be either a DataSource object or a string that contains a relative path to a Java
Naming and Directory Interface (JNDI) resource. The following values are valid for the
isolation attribute: read_committed, read_uncommitted, repeatable_read, serializable.
If the <sql:transaction> tag is used, then the <sql:query> or <sql:update>
tag is nested in the body of the <sql:transaction> tag. In this way, if one or more of
the <sql:update> or <sql:query> actions fail, then the entire transaction is rolled
back.

Oracle 10g: Build J2EE Applications 9-25


Querying Using SQL Tags

<sql:query datasource="jdbc/oeCoreDS"
var="customers" maxRows="10">
SELECT * FROM customers
</sql:query>
<table>
<c:forEach var="row"
items="${customers.rowsByIndex}">
<tr><c:forEach var="column" items="${row}">
<td><c:out value="${column}"/></td>
</c:forEach>
</tr>
</c:forEach>
</table>

Copyright © 2005, Oracle. All rights reserved.

Querying Using SQL Tags


After you have created a data source, you can easily query data by using the
<sql:query> tag. The example in the slide would return a result set containing the first
10 customers from the data source named “oeCoreDS.” The <sql:query> tag outputs the
result of the query to an object that implements the
javax.servlet.jsp.jstl.sql.Result interface. This interface enables you to
navigate the result set by using the getRows(), getRowsByIndex(),
getColumnNames(), getRowCount()methods, and the Boolean method
isLimitedByMaxRows(). The Result interface methods make it possible to retrieve
<sql:query> result sets by using expression language, as shown. The <c:forEach>
tag of the core tag library is used to iterate through the rows. The <c:out> tag is used to
display each column of each row, formatted within an HTML table.

Oracle 10g: Build J2EE Applications 9-26


Inserting, Updating, and Deleting Data

Use the <sql:update> tag to insert, update, or delete


data. For example:
<sql:update var="rows">
UPDATE customers SET account_mgr_id=147
WHERE account_mgr_id=149
</sql:update>
<c:out value="${rows}"/> Rows Updated.

Copyright © 2005, Oracle. All rights reserved.

Inserting, Updating, and Deleting Data


The <sql:update> tag accepts four attributes:
• sql: The command that you want to execute (This may also be included in the body
of the tag.)
• dataSource: The javax.sql.DataSource or String JNDI location
• var: A variable to store the number of rows that are affected by the update
• scope: The scope of the var attribute
The SQL JSTL tags support parameterized queries with two additional tags:
<sql:param> and <sql:dateParam>. Nest these tags in a <sql:update> tag or a
<sql:query> tag to pass in the value of a parameter. The question marks [?] in your
statement will be replaced with the value of the value attribute in the order in which they
are specified. For example:
<sql:query> SELECT * FROM customers WHERE account_mgr_id=?
AND credit_limit=?
<sql:param value="${managerId}" />
<sql:param value="${creditLimit}" />
</sql:query>

Oracle 10g: Build J2EE Applications 9-27


Formatting Tags

Formatting Tags are used to specify how numbers,


dates, and times, should be formatted and parsed in a
locale-sensitive manner.
• It is also called "i18n" tags.
• Use either java.util.ResourceBundle
or java.util.Locale to format data.
Use the prefix “fmt” in the taglib directive:
<%@ taglib uri="http://java.sun.com/jstl/fmt"
prefix="fmt" %>

Copyright © 2005, Oracle. All rights reserved.

Formatting Tags
The “i18N tags,” or “formatting tags” as they are more informally known, are used to
specify that various data elements in a JSP page, such as numbers, dates, and times, be
formatted and parsed in a locale-sensitive manner. The format tags in JSTL use either
java.util.ResourceBundle or java.util.Locale to format data.
There are several tags in the Format library, including:
• <fmt:formatNumber>: Formats a numeric value to the specified number,
currency, or percentage, or to a specified locale
• <fmt:parseNumber>: Parses the specified number, currency, or percentage that
are formatted in a customized manner
• <fmt:formatDate>: Formats a date and time to the specified or locale-sensitive
arrangement
• <fmt:parseDate>: Parses the specified date or time that were formatted in a
customized manner
• <fmt:setTimeZone>: Creates a variable containing the specified time zone
• <fmt:parseTimeZone>: Parses the specified time zone

Oracle 10g: Build J2EE Applications 9-28


Internationalization Concepts

There are three main considerations for


internationalizing an application:
• Locale (geographical or political region)
• Resource bundle (set of paired messages and
keys)
• Basename (identifier for a resource bundle)

Copyright © 2005, Oracle. All rights reserved.

Internationalization Concepts
A locale is a geographical or a political region. It is defined by a two-letter language code
and a two-letter country code, such as “en-US.”
A resource bundle is a set of paired messages and keys. The key specifies the name of the
message, and the message is the text. A resource bundle is used by referring to a basename.
The basename identifies a set of paired messages and keys based on the type of message.
For instance a “login” basename could contain two resource bundles for the “welcome” key:
“Hello” for English and “Bonjour” for French.

Oracle 10g: Build J2EE Applications 9-29


Internationalizing Strings

• To look up a message in a resource bundle, using


the current locale, specify the key attribute in the
<fmt:message> tag:

<fmt:message key="Hello" />

• Alternatively, specify the basename to use with


the <fmt:bundle> tag:

<fmt:bundle basename="login">
<fmt:message key="Hello" />
</fmt:bundle>

Copyright © 2005, Oracle. All rights reserved.

Internationalizing Strings
To look up a message in a resource bundle, specify the key attribute in the
<fmt:message> tag. This uses the current locale to display the message from the
appropriate resource bundle. Additionally, a <fmt:param> tag is available for supplying
parameters in the body of a <fmt:message> tag.
Alternatively, specify the basename to use with the <fmt:bundle> tag, as shown in the
slide. The “login” basename will look for the “Hello” key and display the string using the
current locale set in the browser. However, a locale can be specified for an application by
using <fmt:setLocale>. For example:
<fmt:setLocale value="en_US" />
To retrieve the URL parameters from a browser that does not specify an encoding of the
standard ISO-8859-1, use the <fmt:requestEncoding> tag. This tag accepts a value
attribute to set the request’s character encoding.

Oracle 10g: Build J2EE Applications 9-30


Formatting Numbers and Dates

There are several formatting tags for working with


numbers and dates, including:
• <fmt:formatNumber>: Specify how a percentage,
currency, or number should appear using patterns
and locales
• <fmt:formatDate>: Specify how a date and/or
time should appear using patterns, locales, and
time zones

<fmt:formatNumber type="percent"
value=".547" pattern="#.###" />

Copyright © 2005, Oracle. All rights reserved.

Formatting Numbers and Dates


The <fmt:formatNumber> tag accepts several attributes to specify how a number
should appear. The value can be output as a percentage, currency, or number, depending on
the value of the type attribute. In this example, the output would be 55%:
<fmt:formatNumber type="percent" value=".547" />
By default, the type attribute is “number.” If the value attribute is missing, then the value
is taken from the body content of the tag. In this way, dynamic values can be formatted.
Additionally, the value of the formatted number is output unless the var attribute is
specified. The pattern attribute takes precedence over the type attribute. Thus, the code
example shown in the slide would output .547.
Note: The pattern attribute value should follow the syntax that is specified in the
java.text.DecimalFormat class.
When formatting currencies (type attribute set to “currency”), the default Locale is used
to format the number.

Oracle 10g: Build J2EE Applications 9-31


Formatting Numbers and Dates (continued)
Date and time can be formatted by using the formatDate tag. This tag accepts several
attributes, shown below:

Attribute Purpose
value The date or time to be formatted
Type Specifies whether the time, date, or both portions of the provided
date value are to be formatted
Datesytle The formatting style for dates, provided in the syntax defined in the
java.text.DateFormat class
Timestyle The formatting style for times, provided in the syntax defined in the
java.text.DateFormat class
Pattern A custom format for dates and times
Timezone A String or java.util.TimeZone in which to format the
provided time
Var The name of the variable where the formatted date will be stored
page The scope of the variable

The current date can be formatted by using a Java bean, as follows:


<jsp:useBean id="now" class="java.util.Date" />
<fmt:formatDate value="${now}" />
This formats the current date as a date type, using the current locale. If a locale is not
defined, then the date will be formatted using java.util.Date.toString().
When formatting time information by using the <fmt:formatDate> tag, the time zone
that is to be used is determined as follows:
1. Use the time zone from the action’s timeZone attribute.
2. If the timeZone attribute is not specified, then use the time zone from the body of
the <fmt:timeZone> action, if present.
3. Use the time zone that is given by the
javax.servlet.jsp.jstl.fmt.timeZone configuration setting.
4. Use the JSP container’s time zone.
The <fmt:timeZone> tag contains one attribute, value. Specify this attribute by using
a string that is supported by java.util.TimeZone (such as “America/Los_Angeles”),
or a time zone ID (such as “GMT-8”). Additionally, you can specify a time zone for a page,
request, application, or session by using <fmt:setTimeZone>.

Oracle 10g: Build J2EE Applications 9-32


Formatting Numbers and Dates

To reverse the formatting that is executed by the


format tags, use the following tags:
• <fmt:parseNumber>: Parses a number into a
currency, percent, or number
• <fmt:parseDate>: Parses a date in a customized
or a locale-specific manner
– Specify the way the date string should be formatted
by using the pattern or parseLocale attributes.

Copyright © 2005, Oracle. All rights reserved.

Formatting Numbers and Dates (continued)


To reverse the formatting that is executed by the <fmt:formatNumber> and
<fmt:formatDate> tags, use the <fmt:parseNumber> and <fmt:parseDate>
tags, respectively. The <fmt:parseNumber> tag accepts currency, percent, or number
for the type attribute so that the number (specified in either the body of the tag or in the
value attribute) can be parsed accordingly. For example, to parse a number that was
formatted by using:
<fmt:formatNumber value="29.999" type="currency"
pattern="#,#00.00" var="num" />
use the following:
<fmt:parseNumber value="${num}" type="number" />
Additionally, this tag can be used to parse a number in a format that is specified for the
locale by using the parseLocale attribute.
The parseDate tag parses the number that is specified in either the value attribute or in
the body of the tag in a customized or a locale-specific manner. You can specify the way the
date string should be formatted by using the pattern or parseLocale attributes.

Oracle 10g: Build J2EE Applications 9-33


Transforming XML Documents

XML uses XSLT stylesheets to transform data. You can


accomplish the same by using the <x:transform>
tag:

<c:import url="Customers.xml" var="xml"/>


<c:import url="customerDisplay.xsl"
var="MyStyleSheet" />
<x:transform xml="${xml}"
xslt="${MyStylesheet}" />

Copyright © 2005, Oracle. All rights reserved.

Transforming XML Documents


XML uses XSLT stylesheets to transform data. You can accomplish the same by using the
<x:transform> tag. Import the XML file for transformation in the same way that you
would for <x:parse>, using a <c:import> tag, as shown in the slide. In this example,
the <xml:transform> tag applies a transformation to the Customers.xml file by
using the customerDisplay stylesheet. The result of this transformation will be
displayed in the JSP. However, it is possible to capture the result in an object that is
specified in the result attribute, or save it to a variable.
To set transformation parameters, such as additional styles, use the <x:param> tag. This
tag accepts two attributes, name and value. To use this tag, nest it within the body of an
<x:transform> tag, as follows:
<c:import url="Customers.xml" var="xml" />
<c:import url="customerDisplay.xsl" var="MyStyleSheet" />
<x:transform xml="${xml}" xslt="${MyStylesheet}" >
<x:param name="match" value="${customerName}" />
</x:transform>

Oracle 10g: Build J2EE Applications 9-34


JSTL in JDeveloper

• JDeveloper includes all four


libraries of the JSP Standard Tag
Libraries in the component
palette.
• The Design editor resolves the
output of the tag, as with any
other JSP element.

Copyright © 2005, Oracle. All rights reserved.

JSTL in JDeveloper
In JDeveloper 10g, you do not need to add JSTL to the component palette. Rather, the four
JSTL libraries are included and can be accessed by selecting JSTL Core, JSTL FMT (the
internationalization tags), JSTL SQL, or JSTL XML from the Component Palette drop-down
list. Drag a tag to either the Design or the Source editor to add it to the JSP.

Oracle 10g: Build J2EE Applications 9-35


Summary

In this lesson, you should have learned how to:


• Develop custom tags for use in JSP applications
• Add custom tag libraries to the Component Palette
• Use the JSTL custom tag libraries in JSP
applications

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 9-36


Practice 9-1: Overview

This practice covers creating a JSP that uses the JSTL


custom tag library.

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 9-37


Practice 9-1
The purpose of this practice is to use the Core JSTL tags in a JSP. Open the
practice09.jws workspace in JDeveloper.
1. Create a form that asks a user to log in.
a. Select the JSTL project and create a new JSP. Name the JSP Login.jsp.
b. Select the HTML category from the Component Palette and create a form
containing a Submit button that submits to LoginSubmit.jsp.
c. Within the form, create two text input fields named username and password.
Hint: Use the Property Inspector to change the name attributes of the text fields.
d. Create labels for the username and password fields and, optionally, add a style
sheet to the page.
2. Use the Core JSTL tags to create a JSP that welcomes the user.
a. Create a new JSP named LoginSubmit.jsp in the JSTL project.
b. Select the JSTL Core category from the Component Palette. Drag the set tag to
the page and set the value property in the Property Inspector to the username
request parameter. Name the variable “un.”
c. Welcome the user by name using the <c:out> tag to return the value of the un
variable. If the name is null, welcome the default user as a guest.
d. Run Login.jsp to test.
3. Next, redirect the user to a URL depending on the username that the user has entered.
a. Create a c:choose block in LoginSubmit.jsp.
b. If the name supplied is “Larry,” redirect the user to http://www.oracle.com.
c. If the name supplied is “Scott,” redirect the user to http://java.sun.com.
d. Otherwise, advise the user that the username provided is incorrect. Create a URL
variable for Login.jsp and supply an href link to the user labeled “Try
Again.”
Hint: Create the tags by using the tag dialog that appears when you drag a tag to
the JSP from the Component Palette, then modify the generated code in the
source code editor.
e. Run Login.jsp to test.

Oracle 10g: Build J2EE Applications 9-38


Practice 9-2
The purpose of this practice is to use the SQL and Formatting JSTL tags in a JSP. You will
query the Products table and display the list price of the products according to a user-
selected format.
1. Create a JSP that converts currencies.
a. Create a new JSP in the JSTL project named Products.jsp. At the top of the
page, insert an HTML form and add the text “Convert To:”.
b. Create three option buttons with values GBP, Yen, and Dollar. The name of these
buttons should be Currency. Supply the labels of the option buttons as UK
Pounds, Yen, and US Dollars.
c. Create a Submit button and submit the form to this page.
Hint: Use the HTML tag library in the Component Palette for creating the form,
option buttons, and submit buttons. Set the value of the buttons in the Property
Inspector.
d. Beneath the form, use the JSTL SQL tags to select the PRODUCT_ID,
PRODUCT_NAME, and LIST_PRICE from the PRODUCTS table where a
LIST_PRICE exists. Select only the first 25 rows, using the defined
jdbc/oeDS data source, and name the return variable prodresult.
e. Create a 1 row by 3 column table.
f. Within the table, create a <c:forEach> tag to repeat a table row for each row
of prodresult returned. Name the returned row variable prodrow.
Hint: Create the <c:forEach> tag and then drag it between the <table> and
<tr> elements using the Structure Pane.
g. In the table, output the value of the PRODUCT_ID and PRODUCT_NAME using a
<c:out> tag.
h. Switch to the code editor and just before the third <td> element, create a JSTL
variable named “Price” for the returned LIST_PRICE.
2. Now create the functionality for converting the price to the specified currency.
a. Create conditional tags to test the Currency parameter for GBP or Yen and
create a <c:otherwise> tag for the Dollar.
b. Within the <c:when> tags, use the setLocale and formatNumber tags to
format the variable you created in step 1.h. Use en_GB as the Locale for Pounds,
and ja_JP as the Locale for Yen. Multiply the variable by the currency rate (for
example, .5437 and 106.034, respectively). Name the variable “convertedPrice”
and set the formatType attribute to “currency”.
c. Otherwise, the user must have selected dollars. Use a third formatNumber tag
to return the value of the Price variable to the convertedPrice variable.
d. Within the last table cell, output the value of the convertedPrice variable.
e. Run Products.jsp to test.

Oracle 10g: Build J2EE Applications 9-39


Communicating in J2EE

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Describe Remote Method Invocation (RMI)
• Define the role of RMI in Java 2, Enterprise Edition
(J2EE) applications
• Describe Java Naming and Directory Interface
(JNDI)
• Define the role of JNDI in J2EE applications
• Write code to look up a Java object by a JNDI
name

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson describes the architecture and the APIs that are used for some communication
techniques in J2EE environments and examines their usage from client applications.
JNDI names are influenced by the configuration of various elements in the environment,
such as variables, EJB references, and data sources. In a J2EE environment, these elements
are specified in application deployment descriptors or property files.

Oracle 10g: Build J2EE Applications 10-2


Overview of RMI

Remote Method Invocation (RMI) is a framework for


executing distributed objects in Java. RMI has the
following characteristics:
• It uses RPC-like communication mechanisms.
• It is designed for client applications to invoke
remote object methods, as easily as calling local
methods.
• It comprises the following components:
– Remote interface
– Implementation class
– Server application/class
– Client application/class
– Stub (proxy) and skeleton classes

Copyright © 2005, Oracle. All rights reserved.

Introduction to RMI
An RMI client application uses a standard remote procedure call (RPC) mechanism to
communicate with remote objects. The mechanism involves the use of stubs and skeletons.
RMI applications comprise a client that communicates with a remote server object via a
user-defined remote interface. The server object is instantiated from the implementation
class in the context of a server application.
A stub acts as the client’s representative for the remote object, often called a proxy. The
client invokes a method on the local stub that in turn executes the appropriate method call on
the remote object. An RMI stub class implements the same remote interface that is used by
the remote object. The remote object may have a skeleton class. The skeleton manages the
dispatching of a client call (via the client stub) to the actual remote implementation object.
In JDK 1.2 and later, an additional stub protocol is introduced that eliminates the need for
skeletons, and generic code carries out the tasks that are performed by skeletons in JDK1.1.
Stubs and skeletons are generated by running the rmic compiler on the compiled
implementation class. For example:
rmic RMIClassImpl
The rmic command produces two class files: RMIClassImpl_Stub.class for the
stub and RMIClassImpl_Skel.class for the skeleton.

Oracle 10g: Build J2EE Applications 10-3


Role of RMI in J2EE

• Distributed components or objects in J2EE are


implemented as Enterprise JavaBeans (EJB).
• Oracle Application Server 10g Containers for J2EE
(OC4J) uses a custom form of the RMI wire
protocol known as ORMI. The J2EE 1.3
specification requires support for the RMI-IIOP
protocol as the type of communication used
between the client and server object.
• EJBs have a remote interface and implementation
classes, which conform to RMI semantics:
– They implement a remote interface.
– Methods throw the java.rmi.RemoteException.
– Object parameters or return values must be
serializable.

Copyright © 2005, Oracle. All rights reserved.

Role of RMI in J2EE


Remote objects execute in a different Java virtual machine (JVM) from the client
application. The J2EE distributed object architecture and protocols are modeled on RMI in
such a way that a remote object appears as if it is local to the client. In RMI, the server
object is an instance of the remote interface running on a server. In a J2EE container, an EJB
instance is the equivalent of the RMI server object. Client interaction with an EJB instance
is mediated through the stub and skeleton classes that are generated for the EJB component.
The EJB component and its skeleton classes reside on the remote (middle) tier, while the
stub class resides with the client software.
RMI is a wire-level protocol that supports other protocols, such as HTTP, and defaults to a
protocol called Java Remote Messaging Protocol (JRMP). The OC4J stub and skeleton layer
uses a modified wire-level protocol called ORMI. OC4J supports the RMI over IIOP (RMI-
IIOP) protocol as required by J2EE 1.3 specifications. Common Object Request Broker
Architecture (CORBA) and Microsoft Distributed Component Object Model (DCOM) are
other distributed technology implementations that use their own wire-level protocols.
Much like an RMI server object, an EJB provides a remote interface that describes how to
invoke the EJB methods. Methods could throw java.rmi.RemoteException. Objects
must conform to Java serialization rules to be passed as parameters to, or returned from, a
remote object method.
Oracle 10g: Build J2EE Applications 10-4
Communication in a J2EE Environment

J2EE server

1 Naming
3 Creation
4 Client 2
5
Interface Marshaled data
Stub Skeleton
Marshaled data
6
Local call 7
Interface
Network protocol
(Java RMI) Server
object

Copyright © 2005, Oracle. All rights reserved.

Communicating in a J2EE Distributed Object Environment


The diagram in the slide shows how the distributed object communication occurs from the
time the client requests access to a method on the remote object until the client’s request is
served.
Distributed systems provide transparent communication between objects that reside on
different nodes.
1. The client requests an appropriate remote server object from the J2EE server.
2. A new server object (which implements the required interface) is created, or an
existing server object is allocated to the client. Usually an interface object (a skeleton)
is generated to intercept and forward the requests that come from the remote client.
3. On the client side, a special interface object (stub) is instantiated. This stub exposes the
same interface that the server object implements. The stub knows the details of how to
access the remote skeleton and the server.
4. The client makes local calls to the stub that represents the server object.

Oracle 10g: Build J2EE Applications 10-5


Communicating in a J2EE Distributed Object Environment (continued)
5. The stub marshals the methods and parameters that are requested by the client, and
transfers the marshaled data over the network to the waiting skeleton.
6. The skeleton can intercept the client calls; perform authentication, access control, and
transaction handling; and manage the persistent state of the object. The skeleton then
invokes the appropriate method in the server implementation.
7. The results of the call or run-time exceptions, if any, are passed back by the skeleton to
the caller through the stub.
The association between a client and the server object remains in effect until the client either
directly or indirectly frees the server object. During that period, the client can make several
calls.

Oracle 10g: Build J2EE Applications 10-6


How Clients Locate a Distributed
Component

In J2EE, a distributed component is bound to a name


when deployed.
• The server object run-time environment provides a
naming service to help locate an object by a name:
– In RMI, the RMI registry performs this task.
– In J2EE, the container typically provides this
service.
• Clients use the Java Naming and Directory
Interface (JNDI) API to locate a remote object by a
name.

Copyright © 2005, Oracle. All rights reserved.

How a Client Locates a Distributed Component


The RMI clients use an RMI-specific URL string that is prefixed with rmi (using JRMP
protocol, by default) to locate a remote RMI server object by a name. The URL string
specifies the location of the RMI registry and the name of the remote object. The RMI
application server class instantiates the RMI server object and binds the remote
implementation object to a name in the RMI registry. In this scenario, the RMI registry
provides the service for registering the implementation object with a name, and for the client
to look up the remote object by a name in the registry. In this case, the binding of the
implementation object to a name is done at run time, and the lookup string is RMI protocol
dependent.
The J2EE implementation was designed to overcome the run-time binding and to free the
developer from a specific naming service and protocol. This was achieved by using the
JNDI specification. A J2EE container implements the naming and directory service
conforming to JNDI specifications. The binding of a name to the server object or component
is done (when the server component is deployed) by using deployment descriptors. The
client application uses the JNDI APIs to locate (or look up) a remote object by a JNDI name.
The JNDI URL pattern depends on the type of JNDI that the service provider uses to
implement the naming and directory service.
Subsequent slides in this lesson discuss JNDI in detail.
Oracle 10g: Build J2EE Applications 10-7
Java Naming and Directory
Interface (JNDI)

What is JNDI?
• JNDI is a standard API that provides access to the
directory and naming functionality.
• The JNDI Service Provider Interface (SPI)
implementation provides the mapping between the
naming servers and the JNDI APIs.

JNDI API
Client
JNDI SPI

RMI registry COS Naming LDAP


Name and directory services

Copyright © 2005, Oracle. All rights reserved.

Java Naming and Directory Interface (JNDI)


Java Naming and Directory Interface (JNDI) is a standard interface to a naming and
directory service. J2EE applications use the following two parts of JNDI to find other
distributed objects:
• An application-level interface that is used by application programs to access a naming
and directory service.
• A service provider interface to attach a provider of a naming and directory service.
By using these parts and portable programming principles, client applications can access any
directory service.
Applications use JNDI to obtain naming contexts that enable the applications to locate and
retrieve objects such as data sources, local and remote EJBs, Java Message Services (JMS),
and so on. Objects in a JNDI namespace can be managed by different directory and naming
services. For example, a JNDI service provider can be implemented by using a file system,
or by using a Lightweight Directory Access Protocol (LDAP) service, such as Oracle
Internet Directory (OID), an RMI registry, or the CORBA Object Naming services in the
form of COS Naming, and so on. Similar to Java Database Connectivity (JDBC), JNDI
provides different drivers for various service providers.
OC4J provides a complete JNDI 1.2 implementation, with the JNDI service provider
implemented in memory in the container.

Oracle 10g: Build J2EE Applications 10-8


J2EE Container and JNDI Interface

• The container implements the J2EE environment


and makes the services and resources available
through a JNDI interface.
• The JNDI service obtains names from the
Extensible Markup Language (XML) files and holds
them in memory.
• JNDI allows developers to write application code
that is independent of vendor-specific underlying
protocols, connections, and other resources.
• The JNDI interface provides a common naming
convention to access J2EE resources.

Copyright © 2005, Oracle. All rights reserved.

J2EE Container and JNDI Interface


The J2EE container provides services, such as transaction services, naming services, and so
on, as discussed earlier in this course. These services reside in a framework in the container.
This framework exposes the interfaces that are to be used by the client application code and
enterprise beans. In the case of EJB, the interfaces enable the developer to write the code for
a bean without using vendor-specific references to underlying protocols, connections, and
other resources.
The container implements the environment and makes the services and resources available
through the JNDI interface. For example, data sources represent databases, and JMS service
names can be specified as JNDI names.
The JNDI interface provides a common naming convention to access the resources that are
provided by the container. The names in the naming convention are used in the bean class
and the deployment descriptor.

Oracle 10g: Build J2EE Applications 10-9


Naming Service

A naming service allows clients or objects to locate


each other in a network by:
• Storing objects published against their names,
known as binding a name to an object
• Maintaining a mapping of logical names to actual
names of hierarchical objects
• Using a directory service with a hierarchical
structure to maintain logical names for its data
Examples: Java Naming and Directory Interface (JNDI),
RMI registry, Lightweight Directory Access Protocol
(LDAP), CORBA naming service (COS Naming)

Copyright © 2005, Oracle. All rights reserved.

Naming Service
An Object Naming Service is the principal mechanism for objects or clients to locate other
objects on the network. Names are humanly recognizable values that identify an object. The
naming service enables the creation and mapping of these names to object references.
A name-to-object association is called name binding. In the case of EJBs, the server
performs the binding of the bean’s home interface in the JNDI namespace.
Naming services can be used for literally mapping any type of object or resource with names
such as files, database objects, remote objects, and so on. EJB specifications require that the
bean home interfaces be published and made available to the clients through JNDI.
It is the responsibility of the server and container provider that the beans deployed in the
server are made available to different clients through a JNDI service.
A directory service usually has a hierarchical structure of data, and you use the naming
service to create logical names and map them to the naming server. For example, the
directory service of a file system contains a hierarchical structure of folders, subfolders, and
the files in the folders.
Examples of naming services are RMI registry, LDAP, and CORBA Naming Service (COS
Naming).

Oracle 10g: Build J2EE Applications 10-10


JNDI Terminology

JNDI client Initial context


ormi://host/AppCtx

Context Namespace
env

Sub-context
jdbc ejb

Atomic
OracleDS oeCoreDS Employee Cart
names
Binding
Objects

java:comp/env/jdbc/OracleDS Compound name

Copyright © 2005, Oracle. All rights reserved.

JNDI Terminology
Namespace: The set of all names in the naming server. The names in the namespace must
be unique. For example, in a directory structure, each file and subdirectory in a particular
level have unique names.
Initial context: The root directory object in the namespace that refers to the starting point of
the name hierarchy from which a client can start navigation. The client obtains this root
directory by creating a new InitialContext object. Relative to the initial context, a
client can look up another object using its compound name.
Compound name: Formed by concatenating the names of each context object along the
hierarchical path to the target atomic name for an object published in the JNDI namespace.
The slide shows env, jdbc, and ejb as context objects, where jdbc and ejb are
subcontexts below env.
Atomic name: A unique indivisible part of a name, such as env, jdbc, and OracleDS
Binding: The process of associating an object with a name in the naming and directory
service
URL: A composite name spanning more than one context or namespace, which is used to
uniquely identify an object in a composite namespace

Oracle 10g: Build J2EE Applications 10-11


Main JNDI Class and Interface

• The javax.naming.InitialContext class:


– Is used to obtain the initial context for JNDI lookup
operations
– Returns a reference to the object implementing the
java.naming.Context interface
• The javax.naming.Context interface:
– Provides methods to bind names to objects
– Provides methods to create subcontexts
– Provides methods to navigate the JNDI name
hierarchy
– Looks up an object by a name that is relative to the
initial context or a subcontext

Copyright © 2005, Oracle. All rights reserved.

Main JNDI Class and Interface


Context: Context is an interface in the javax.naming package. The very first JNDI
call to code is the one that gets a Context object. The first context object that you get is
called the initial context and is bound to the root naming context of the namespace. A
context can contain a subcontext and objects. An object implementing the Context
interface contains a number of methods that the EJB application developer can use. The
client uses the lookup() method on the context to look up a home object. The names in
the namespace are bound to specific objects.
URL: URL enables you to use JNDI requests to start up services and sessions and to access
components published in the database. Just as a Web document can be located by using a
unique URL, an object published in JNDI can be located by using a unique URL.
When you use JNDI in your client or server object implementations, be sure to include the
following import statements:
import javax.naming.Context; // the JNDI Context interface
import javax.naming.InitialContext;
import java.util.Hashtable; // Hashtable for the initial
// context environment

Oracle 10g: Build J2EE Applications 10-12


Accessing an Object in JNDI Namespace

A client must perform the following steps to retrieve a


local object reference from the JNDI namespace:
1. Get the JNDI InitialContext object. Example:
Context ic = new InitialContext();
2. Form the URL for the bean home interface and call
the lookup() method to get the reference to the
local home interface object. Example:
DepartmentLocalHome home =
(DepartmentLocalHome) ic.lookup(
"java:comp/env/ejb/Dept");
• lookup() returns an Object type that should be
cast to a desired type.

Copyright © 2005, Oracle. All rights reserved.

Accessing an Object in JNDI Namespace


To access an object in the JNDI namespace, the client has to perform these steps:
1. Get the JNDI InitialContext object.
2. Form the URL for the bean home interface and call the lookup() method to get the
reference to the home interface object.
The code in the slide shows an example of this process. The first statement creates a new
initial context object, using the default environment. The second statement looks up an EJB
local home interface reference in the application’s JNDI tree. In this case, ejb/Dept might
be the name of an entity bean that is declared in the ejb-jar.xml configuration file, in an
<ejb-local-ref> tag.
For example:
<ejb-local-ref>
<ejb-ref-name>ejb/Dept</ejb-ref-name>
<ejb-ref-type>Entity</ejb-ref-type>
<local-home>DepartmentLocalHome</local-home>
<local>DepartmentLocal</local>
</ejb-local-ref>

Oracle 10g: Build J2EE Applications 10-13


Getting the JNDI InitialContext

• When OC4J starts, a JNDI context is constructed


for each application deployed in the server.
• An initial context obtained by the client is used to
access the subcontexts and objects.
• Clients accessing objects in a remote OC4J
container typically require a set of environment
properties to obtain the InitialContext:
– INITIAL_CONTEXT_FACTORY
– PROVIDER_URL
– SECURITY_PRINCIPAL
– SECURITY_CREDENTIAL
– dedicated.rmicontext

Copyright © 2005, Oracle. All rights reserved.

Getting the JNDI InitialContext


When OC4J starts, a JNDI context is constructed for each application that is deployed in the
server (in server.xml). There is always at least one application for an OC4J server, the
global application, which is the default parent for each application in a server instance. User-
written applications inherit properties from the global application. User-written applications
can override property values defined in the global application, can define new values for
properties, and can define new properties as required. In the default OC4J server, as shipped,
the global application is the default application, as defined in the server.xml file. OC4J
requires certain properties for obtaining the initial context reference.
Each JNDI lookup retrieves a connection to the server. Each subsequent JNDI lookup for
this same server uses the connection that is returned by the first JNDI lookup. That is, all
requests are forwarded over and share the same connection. The
dedicated.rmicontext JNDI property overrides this default behavior. If you set
dedicated.rmicontext to true before you retrieve an InitialContext, you
will retrieve a separate physical connection for each lookup, each with its own designated
username and password. The value of dedicated.rmicontext defaults to false.
The list of properties shown in the slide is not an exhaustive list. Refer to the Oracle
Application Server 10g Containers for J2EE Services Guide for more information.

Oracle 10g: Build J2EE Applications 10-14


Getting the JNDI InitialContext

• Set environment properties for initial context in:


– The system properties, set either by the OC4J
server or by the application container
– A jndi.properties file contained in the
application EAR file, as part of the application-
client.jar file
– An environment specified explicitly in a Hashtable
• The JNDI InitialContext has two constructors:
– A no-arg constructor used by local clients to
execute code in the same J2EE container
– A constructor with a Hashtable argument used by
remote clients to execute code in a remote J2EE
container

Copyright © 2005, Oracle. All rights reserved.

Getting the JNDI InitialContext (continued)


The environment properties can be in the form of system property values that are set by
OC4J as specified in the application.xml file, in the jndi.properties file that is
contained in the application EAR file, or as environment properties defined explicitly in the
client code and passed as a Hashtable to the JNDI initial context constructor.
The JNDI InitialContext constructor has two forms:
• A default no-arg form of the constructor that creates a Context object by using the
default context environment for that application, that is created by the OC4J when the
server is started. This is typically used by server-side clients such as JSPs, servlets, or
other EJBs. These server-side clients typically use local references to locate an object
being looked up as the clients are running in the same J2EE container. You can also
specify that the object not be initialized by passing (boolean lazy) to the
constructor.
• The second form of the constructor accepts a Hashtable parameter that consists of
the environment properties. These properties can be defined in any one of the three
forms, as described above. This form is used by remote client applications. Therefore,
it is necessary to specify the JNDI properties. In the JNDI properties, you can specify
whether the object that is being looked up is running in a JVM or in a J2EE container
remotely from the client application.
Oracle 10g: Build J2EE Applications 10-15
Initial Context Factories

• There are three JNDI initial context factories:


– ApplicationClientInitialContextFactory
– ApplicationInitialContextFactory
– RMIInitialContextFactory
• An initial context factory is used to construct an
InitialContext object.
• The initial context factory class name is the string
value for the INITIAL_CONTEXT_FACTORY JNDI
property.

Copyright © 2005, Oracle. All rights reserved.

Initial Context Factories


The three types of context factories are provided to help a client establish a connection with
the naming service in an efficient way. This depends on where the client is, relative to the
component that it is locating.
Use ApplicationClientInitialContextFactory to construct the initial context
for a local or remote resource in a J2EE application. The client is bundled with the J2EE
application. For the client to access remote objects,
ApplicationClientInitialContextFactory reads the META-
INF/application-client.xml and META-INF/orion-application-
client.xml files in the <application_name>-client.jar file.
The client code runs in a server as part of a J2EE application, and can define a default set of
properties for JNDI use. ApplicationInitialContextFactory is set as the default
initial context factory for applications that are running in the same container as the client. In
this case, the clients can only look up references to local objects (for example, a servlet or
JSP calling an EJB in the same container).
RMIInitialContextFactory is used by a client to access the JNDI namespace when
looking up objects that are part of another remote J2EE application. It is also used for
resource references that cannot be specified in the application-client.xml file.

Oracle 10g: Build J2EE Applications 10-16


lookup() Method

• The lookup() method obtains a reference to the


required resource.
• To reference a local resource, pass the URL with
the object name as parameter:
java:comp/env/subContext/resourceName
Examples:
– java:comp/env/ejb/Dept
– jdbc/oeCoreDS
• Retrieve a reference to target EJB by using:
– The actual bean name specified in the <ejb-name>
element or the <ejb-ref-name> element of ejb-
jar.xml
– The logical bean name specified in the <ejb-ref-
name> element of application-client.xml

Copyright © 2005, Oracle. All rights reserved.

lookup() Method
After the client obtains the InitialContext, it should obtain a reference to the required
resource by using the lookup() method on InitialContext. The client uses the
lookup() method by passing the URL with the object name as the parameter. This
generally depends on how the resources are mapped in the naming server. Generally, the
URL to look up a local resource (in the same container) is of the following format:
java:comp/env/subContext/resourceName.
For example, the client looks up an EJB called Dept under the subcontext ejb with the
URL java:comp/env/ejb/Dept. Here, java:comp/env is the initial context, and
ejb/Dept can be the actual name of the EJB as specified in either the <ejb-name> or
the <ejb-ref-name> element of the deployment descriptor where the bean is defined. It
can also be the logical name of the bean, which is defined in the <ejb-ref-name>
element under the <ejb-ref> section in the files ejb-jar.xml, application-
client.xml, or web.xml for an EJB, an application, or a servlet or JSP client,
respectively.
In another example, a client looking up a data source called oeCoreDS may use the URL
java:comp/env/jdbc/oeCoreDS. Here, jdbc is the subcontext name and
oeCoreDS is the resource name.
Note: The initial context for a local object always uses the URL prefix java:comp/env.

Oracle 10g: Build J2EE Applications 10-17


Obtaining a Reference to a Local Resource

Using the default InitialContext:


1. Obtain InitialContext:
Context ic = new InitialContext();
2. Obtain reference to a resource using lookup():
– An EJB client referencing another local EJB
Object obj =
ic.lookup("java:comp/env/ejb/Dept");
– An EJB client referencing a data source
Object obj = ic.lookup("jdbc/oeCoreDS");
3. Cast reference obtained from lookup():
DepartmentLocalHome dlh =
(DepartmentLocalHome) obj;
DataSource ds = (DataSource) obj;

Copyright © 2005, Oracle. All rights reserved.

Obtaining a Reference to a Local Resource


To obtain a reference to a local resource, the client first obtains the initial context. The code
in the slide shows the example by using the default no-arg constructor. The
InitialContext reference returns a Context interface type variable called ic.
The client then invokes the lookup() method of the initial context. The parameter for the
lookup() method consists of the initial context and the path to the object, as discussed in
the previous slide. The lookup() method returns a value of Object type and must be
cast to the correct class to be used as intended by the application.

Oracle 10g: Build J2EE Applications 10-18


Obtaining a Reference to a
Remote Resource

Use initial context with appropriate JNDI properties:


1. Set JNDI properties for application:
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY
, ...);
2. Obtain the InitialContext:
Context ic = new InitialContext(env);
3. Obtain a reference to a resource by using
lookup():
Object obj = ic.lookup("Dept");
4. Cast the reference to the returned Object type:
DepartmentHome dh = (DepartmentHome)
PortableRemoteObject.narrow(obj,
DepartmentHome.class);

Copyright © 2005, Oracle. All rights reserved.

Obtaining a Reference to a Remote Resource


If the client application is external to the container that runs the resource, then you must
obtain the initial context by using a set of JNDI properties set in a Hashtable, or a
jndi.properties file for the application. The slide shows a snippet of creating the
Hashtable. Here is a more complete example of setting environment properties:
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY,
"com.evermind.server.rmi.RMIInitialContextFactory");
env.put(Context.SECURITY_PRINCIPAL, "admin");
env.put(Context.SECURITY_CREDENTIALS, "oracle");
env.put(Context.PROVIDER_URL, "ormi://localhost/Dept");
After the initial context is obtained by using the appropriate JNDI properties, you can invoke
the lookup() method to return a reference to an Object data type, as seen for local
resources. You then cast the remote reference to the appropriate type such as a remote home
interface or data source by using the PortableRemoteObject.narrow() method,
which is required for obtaining a remote reference from a client accessing over the RMI-
IIOP protocol.
If appropriate, the Object reference returned can be cast to a data source type by using the
javax.sql.DataSource class.

Oracle 10g: Build J2EE Applications 10-19


Setting JNDI Environment Properties

• Do not set JNDI properties if:


– The client exists in the same application as the
target
– The target exists in the parent application of the
client
• Setting JNDI properties:
– Supply the properties through the
jndi.properties file. The path of the file must be
in the CLASSPATH, or JAVA_HOME/lib.
– Supply properties in the client code by using a
Hashtable.

Copyright © 2005, Oracle. All rights reserved.

Setting JNDI Environment Properties


The JNDI environment properties can be either set in the jndi.properties file or
explicitly defined in the client code. A client that co-resides with the target EJB does not
need to supply the environment properties. The client does not need to supply the
environment properties if the parent application of the client coresides with the target EJB.
In this case, the container sets the environment properties.
The two methods are:
• Using the jndi.properties file that must be located in the machine’s
CLASSPATH, or in the JAVA_HOME/lib directory
• Explicitly coding the environment properties in the client code

Oracle 10g: Build J2EE Applications 10-20


Setting JNDI Environment Properties

Using the jndi.properties file:


• Factory: Initial context factory to be used
java.naming.factory.initial =
com.evermind.server.
ApplicationClientInitialContextFactory
• Location: URL used to look up the objects
java.naming.provider.url =
ormi://<hostname>:23891/<application-name>
• Security: Valid credentials of the client to this
container
java.naming.security.principal=<username>
java.naming.security.credentials=<password>

Copyright © 2005, Oracle. All rights reserved.

Setting JNDI Environment Properties (continued)


If you are setting the JNDI properties in the jndi.properties file, then set the
properties as follows. Make sure that this file is accessible from the CLASSPATH.
Factory: Specifies the initial context factory to use when creating a new initial context
object. Different context factories are discussed later in this lesson.
java.naming.factory.initial=
com.evermind.server.ApplicationClientInitialContextFactory
Location: The URL that the application client code uses to look up objects on the server.
The ORMI default port number is 23891, which can be modified in the config/rmi.xml
file. Thus, set the URL in the jndi.properties in one of the following three ways:
java.naming.provider.url=ormi://<hostname>/<application-name> or
java.naming.provider.url=ormi://<hostname>:23891/<application-name>
or when running in the Oracle Application Server 10g server, hardcoding the port is not necessary
and you can use
java.naming.provider.url=opmn:ormi://<host>:<port>:<oc4jinstance>/
<application-name>

Oracle 10g: Build J2EE Applications 10-21


Setting JNDI Environment Properties (continued)
Security: When you access EJBs in a remote container, you must pass valid credentials to
this container. Stand-alone clients define their credentials in the jndi.properties file
deployed with the client’s code.
java.naming.security.principal=<username>
java.naming.security.credentials=<password>

Oracle 10g: Build J2EE Applications 10-22


Setting JNDI Environment Properties

Specify the JNDI properties in the client code by:


• Using jndi.properties
• Declaring properties in a Hashtable and passing
them to the InitialContext constructor
Hashtable env = new Hashtable();
env.put(Context.PROVIDER_URL,
"ormi://myhost/J2EECourse");
env.put(Context.INITIAL_CONTEXT_FACTORY,
"com.evermind.server.
ApplicationClientInitialContextFactory");
env.put(Context.SECURITY_PRINCIPAL, "guest");
env.put(Context.SECURITY_CREDENTIALS, "welcome");
Context ic = new InitialContext (env);

Copyright © 2005, Oracle. All rights reserved.

Setting JNDI Environment Properties (continued)


If you use the jndi.properties file approach, then the properties names are specified
as the textual representation of the first parameter for each env.put() method, shown in
the slide. The property values are the same as the second parameter values that are used in
each env.put() call listed in the slide. For example:
java.naming.security.principal=guest //Context.SECURITY_PRINCIPLE
The slide shows how to use a Hashtable variable env. The property name and value
pairs are added to the Hashtable by calling the put() method. Property names are
specified by using constants defined in the javax.naming.Context class in the first
parameter of the put() method with its corresponding value specified in the second
argument.
PROVIDER_URL shows a typical example of a URL for a JNDI resource name. The
absence of the port number implies that the default ORMI port number of 23891 is assumed.
INITIAL_CONTEXT_FACTORY, as used by most client applications, is specified as
ApplicationClientInitialContextFactory.
SECURITY_PRINCIPAL and SECURITY_CREDENTIALS indicate the username and
password of the client requesting the initial context. The Hashtable variable env is then
passed as a parameter to the InitialContext constructor.

Oracle 10g: Build J2EE Applications 10-23


Using RMI over HTTP Tunneling

OC4J supports tunneling of RMI over HTTP or HTTP-S.


• Allows clients to communicate with remote
objects through a firewall
• Makes the connection appear as if it is stateful
• Clients use RMI over HTTP in JNDI requests by
prefixing PROVIDER_URL with http: as in the
following example:
Hashtable env = new Hashtable();
env.put(Context.PROVIDER_URL,
"http:ormi://<host>:<port>/Application");

• Port used is the HTTP server port (by default 80)

Copyright © 2005, Oracle. All rights reserved.

Using RMI over HTTP Tunneling


OC4J supports the ability to tunnel RMI over HTTP and HTTP-S protocols. You can use
RMI over HTTP/HTTP-S tunneling for Java-based clients when they must communicate
with OC4J over the HTTP protocol.
Typically, HTTP tunneling simulates a stateful socket connection between a Java client and
OC4J and “tunnels” this socket connection through an HTTP port in a security firewall.
HTTP is a stateless protocol, but OC4J provides the tunneling functionality to make the
connection appear to be a stateful RMI connection.
If you are using RMI over HTTP tunneling, a client can make requests and accept replies
from a server, but the server cannot initiate a communication with the client. This means
that a continuous two-way connection is not possible.
The OC4J HTTP tunneling simulates an RMI connection over the HTTP protocol,
overcoming these limitations.
An advantage of HTTP tunneling is that different J2EE components can be deployed on a
single physical tier to optimize performance, or on separate physical tiers for better
accessibility. Deploying components on separate tiers can make use of architectural
redundancy designed for managing connection rerouting and high availability, in the event
of failure.

Oracle 10g: Build J2EE Applications 10-24


Using Environment References with JNDI

An environment reference is:


• A static element accessible to applications at run
time
• Defined as:
– An environment variable
– A resource manager (JDBC data source, JMS
services, or a URL)
– An EJB reference (logical name for the EJB)
• Bound in JNDI namespace at deployment time
– Defined in the J2EE deployment descriptors
– Mapped through OC4J-specific descriptor
• Referenced by using the JNDI lookup() method
of an InitialContext

Copyright © 2005, Oracle. All rights reserved.

Configuring Environment References


Independent software vendors (ISVs) typically develop EJBs that are independent of the
EJB container. To distance the bean implementation from the container specifics, you can
create environment elements that map to one of the following:
• Environment variables that can be used by more than one application
• EJB references
• Resource managers
These environment elements are static and cannot be changed by the bean. The elements are
given logical names when defined in the J2EE deployment descriptor. Using a logical name
enables the bean developer to refer to existing variables, EJBs, and a JDBC data source
without specifying the actual name. The logical names are then associated to the actual
names within the OC4J-specific deployment descriptor. When the bean is deployed, these
elements are bound in the JNDI registry and are accessible by the client during run time.
One advantage of this is that the deployer can set different values to the same element
through the container-specific tool and deploy the bean with these different values.
The client accesses these environment elements by using the lookup() method of the
InitialContext, as discussed in the next slide.

Oracle 10g: Build J2EE Applications 10-25


Configuring Environment Variables

• Environment variables are defined in the <env-


entry> section of the deployment descriptor (DD).
– One entry for each variable; case-sensitive
– Types can be the following classes: String, Integer,
Boolean, Double, Byte, Short, Long, or Float
<env-entry> Deployment Descriptor
<env-entry-name>minBalance</env-entry-name>
<env-entry-type>java.lang.Integer</env-entry-type>
<env-entry-value>500</env-entry-value>
</env-entry>
InitialContext ic = new InitialContext(); Client
Integer minBal = (Integer)
ic.lookup("java:comp/env/minBalance");

Copyright © 2005, Oracle. All rights reserved.

Configuring Environment Variables


Environment variables are defined in an <env-entry> element of the J2EE deployment
descriptor (DD) files, that is, web.xml or ejb-jar.xml. There is one environment entry
for each variable accessed in the client code. The name of the environment variable is
defined in <env-entry-name>, the type is defined in <env-entry-type>, and its
initial value is defined in <env-entry-value>. The example in the slide declares one
environment variable for minBalance.
<env-entry>
<env-entry-name>minBalance</env-entry-name>
<env-entry-type>java.lang.Integer</env-entry-type>
<env-entry-value>500</env-entry-value>
</env-entry>
The data types specified in the <env-entry-type> element can be one of the following
Java classes: String, Integer, Boolean, Double, Byte, Short, Long, or Float.
The client accesses the environment variables through the InitialContext, as follows:
InitialContext ic = new InitialContext();
Integer min = (Integer)ic.lookup("java:comp/env/minBalance");
To retrieve the environment variable values, prefix each environment element with the base
location of java:comp/env/, at which the container stores the environment variable.
Oracle 10g: Build J2EE Applications 10-26
Configuring Environment Variables

• The J2EE name can be mapped to a different value


in the OC4J-specific deployment descriptor (DD).
• The OC4J-specific DD overrides the value in the
J2EE deployment descriptor.
<env-entry> J2EE DD
<env-entry-name>minBalance</env-entry-name>
<env-entry-type>java.lang.Integer</env-entry-type>
<env-entry-value>500</env-entry-value>
</env-entry>

<env-entry-mapping OC4J DD
name="minBalance">300
</env-entry-mapping>

Copyright © 2005, Oracle. All rights reserved.

Configuring Environment Variables (continued)


If you want the value of the environment variable to be defined in the OC4J-specific
deployment descriptor, you can map <env-entry-name> to the <env-entry-
mapping> element in the OC4J-specific deployment descriptor.
Note: The value specified in the orion-ejb-jar.xml file overrides any value that may
be specified in the ejb-jar.xml file. The type specified in the EJB deployment
descriptor stays the same.
The minBalance environment variable is defined as 300 in the OC4J-specific
deployment descriptor, as shown in the code in the slide.

Oracle 10g: Build J2EE Applications 10-27


Specifying an EJB Reference

• Specify an EJB reference by using an <ejb-ref>


element in a J2EE client application deployment
descriptor:
<ejb-ref>
<ejb-ref-name>Employee</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>businesstier.EmployeeHome</home>
<remote> businesstier.Employee</remote>
</ejb-ref>

• A logical name in an <ejb-ref-name> element must


be mapped to a JNDI name in an <ejb-name>
element of an EJB deployment descriptor.
• The server side receives the JNDI name and resolves
it in its JNDI tree.

Copyright © 2005, Oracle. All rights reserved.

Specifying an EJB Reference


You can specify a reference to a local or remote EJB in the <ejb-ref> element of a J2EE
client application’s deployment descriptor (for example, in application-
client.xml, ejb-jar.xml, or web.xml). Choose the XML file based on the
location of the client with respect to the target EJB.
Note: The slide shows an example of a reference to a remote EJB because you defined the
<home> and <remote> elements of the bean in the <ejb-ref> element. If the EJB
reference is for a local component (that is, in the same container), then you specify the
names of the local interfaces in the <local-home> and <local> elements inside the
<ejb-ref> section.
The value specified for <ejb-ref-name> can be:
• The actual JNDI name of the target EJB, as found in the <ejb-name> element of the
EJB deployment descriptor (ejb-jar.xml)
• A logical name used by the application client in the JNDI lookup request
If <ejb-ref-name> used is a logical name, then it must be mapped to an actual JNDI
name found in the <ejb-name> element of the target EJB.

Oracle 10g: Build J2EE Applications 10-28


Configuring EJB References

• The <ejb-ref> element of a client J2EE


deployment descriptor can provide:
– The actual name of the bean in <ejb-ref-name>
– A logical name of the bean in <ejb-ref-name> and
the actual name in <ejb-link>
– The logical name of the bean in <ejb-ref-name>,
to be mapped to the actual name of the bean in the
<ejb-ref-mapping> element in the OC4J-specific
deployment descriptor
• Other elements of the EJB reference are:
– Type: Session or entity bean
– Home/LocalHome: Qualified home interface name
– Remote/Local: Qualified remote/local interface
name

Copyright © 2005, Oracle. All rights reserved.

Configuring EJB References


If an EJB client invokes another EJB, the deployment descriptor for the client uses a
reference to locate the other bean. The following examples show how a client specifies an
EJB reference by using the actual JNDI name or logical name of the referenced bean.
The examples assume that the referenced EJB is a session bean defined in the EJB
deployment descriptor (ejb-jar.xml) as follows:
<session> ...
<ejb-name>Employee</ejb-name>
<home>businesstiersoln.EmployeeHome</home>
<remote>businesstiersoln.Employee</remote>
<ejb-class>businesstiersoln.impl.EmployeeBean</ejb-class>
...
</session>
Specify the actual JNDI name of the bean in the <ejb-ref-name> element:
<ejb-ref>
<ejb-ref-name>Employee</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>businesstier.EmployeeHome</home>
<remote>businesstier.Employee/remote>
</ejb-ref>

Oracle 10g: Build J2EE Applications 10-29


Configuring EJB References (continued)
Specify a logical name in the <ejb-ref-name> element, and the actual name in the
<ejb-link> element:
<ejb-ref>
<ejb-ref-name>ejb/MyEmployee</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>businesstier.EmployeeHome</home>
<remote>businesstier.Employee/remote>
<ejb-link>Employee</ejb-link>
</ejb-ref>
The <ejb-link> element provides the mapping of the logical name used in a JNDI
lookup request to the target bean.
Provide a logical name in the <ejb-ref-name> element, which is mapped to the actual
name with a <ejb-ref-mapping> element:
<ejb-ref>
<ejb-ref-name>ejb/MyEmployee</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<home>businesstier.EmployeeHome</home>
<remote>businesstier.Employee/remote>
</ejb-ref>
This reference alone is incomplete without mapping the logical name to the actual bean
name. The mapping can be achieved by using either the <ejb-link> element in the same
deployment descriptor, as shown in the example before this, or by specifying the mapping of
the logical name to the actual name in the applications OC4J-specific deployment descriptor
as follows:
<ejb-ref-mapping
name="ejb/MyEmployee"
location="Employee"/>
In the <ejb-ref-mapping> element of the client application’s OC4J-specific
deployment descriptor:
• The name attribute identifies the logical name used in the client application lookup
request and specifies the <ejb-ref-name> element of the J2EE deployment
descriptor.
• The location attribute identifies the actual JNDI name of the target bean specified
in the <ejb-name> element of the EJB deployment descriptor (ejb-jar.xml).

Oracle 10g: Build J2EE Applications 10-30


Configuring Data Source References

• Create an environment reference to each data


source that is used by a client through a JNDI
reference.
• These references can be used only by the J2EE
application that defines these data sources.
• The JNDI name is defined in the ejb-location
attribute of a <data-source> element in the
data-sources.xml file.
• The J2EE deployment descriptor can use either
the JNDI name or a logical name.
• A logical name must be mapped to the JNDI name
in the OC4J-specific deployment descriptor.

Copyright © 2005, Oracle. All rights reserved.

Configuring Data Source References


You can access a database through JDBC either by using the traditional method or by
creating an environment reference element for a JDBC data source. To create an
environment reference element for your JDBC data source, the following steps are
necessary:
1. Define the JNDI name for each data source in the OC4J or the application-specific
data-sources.xml file.
2. Write the client code to use the JNDI name specified in the data sources file, or use a
logical name that must be specified in the <res-ref-name> element in the J2EE
deployment descriptor (either the web.xml file for a servlet or JSP, or the ejb-
jar.xml file for an EJB).
3. If the client application uses a logical JNDI name, as specified in the <res-ref-
name> element of the J2EE applications deployment descriptor, then this logical
name should be mapped to the actual JNDI name specified in the ejb-location
attribute for the data source found in a data-sources.xml file. The mapping of
the logical name to the actual JNDI name is done in the OC4J-specific deployment
descriptor (that is, the orion-web.xml file for a servlet or JSP, and the orion-
ejb-jar.xml file for an EJB).

Oracle 10g: Build J2EE Applications 10-31


Configuring Data Source References
1. Define in data-sources.xml.
<data-sources>
<data-source
class="com.evermind.sql.DriverManagerDataSource"
name="OracleDS"
location="jdbc/OracleCoreDS" ...
ejb-location="jdbc/OracleDS" ... />
</data-sources>
JNDI Name
2. Reference in J2EE Deployment Descriptor.
<resource-ref>
<res-ref-name>jdbc/oeCoreDB</res-ref-name>
<res-type>javax.sql.DataSource</res-type>
<res-auth>Application</res-auth>
<resource-ref>
3. Map in OC4J-specific deployment descriptor.
<resource-ref-mapping
Logical Name
name="jdbc/oeCoreDB"
location= "jdbc/OracleDS" />

Copyright © 2005, Oracle. All rights reserved.

Configuring Data Source References (continued)


The code examples in the slide indicate how the target JNDI name and the logical names for
a data source are defined.
1. The data-sources.xml file defines the JNDI name value jdbc/OracleDS in
the ejb-location attribute of the <data-source> element.
2. In the J2EE deployment descriptor (web.xml/ejb-jar-xml), the reference
indicates that the value jdbc/oeCoreDB in the <res-ref-name> element is the
logical JNDI name that the client application uses to look up the data source.
3. The OC4J-specific deployment descriptor (orion-web.xml/orion-ejb-
jar.xml) is used to map the logical name used in J2EE deployment descriptor to the
actual JNDI name for the data source defined in the data-sources.xml file.
Note: Although JNDI names are specified in the location, xa-location, and ejb-
location attributes of the <data-source> element, it is recommended that you use or
map to the name specified in the ejb-location attribute. The configuration in the slide
supports a client application that uses the logical JNDI name defined in the <res-ref-
name> element of the J2EE deployment descriptor. For example:
InitialContext ic = new InitialContext();
javax.sql.DataSource ds =
(javax.sql.DataSource)ic.lookup("java:comp/env/jdbc/oeCoreDB");

Oracle 10g: Build J2EE Applications 10-32


Summary

In this lesson, you should have learned how to:


• Describe Remote Method Invocation (RMI)
• Recognize the role of RMI in a J2EE environment
• Explain the concepts of JNDI
• Access an EJB or a data source object by using
JNDI techniques
• Configure the JNDI names and environment
properties, such as environment variables, EJB
references, and data sources

Copyright © 2005, Oracle. All rights reserved.

Summary
The slide summarizes the key points covered in this lesson. RMI is not specified as a part of
the J2EE specification. However, RMI mechanisms and java.rmi interfaces and classes
are used by J2EE components. The RMI communications architecture is used as the basis
for communication between J2EE client and server components such as Enterprise
JavaBeans. The JNDI services provided by J2EE-compliant implementations provide a
standard way for clients to locate, look up, and communicate with distributed objects in a
J2EE environment.

Oracle 10g: Build J2EE Applications 10-33


Practice 10-1: Overview

This practice covers the following topics:


• Creating a JSP Java client to connect to and
invoke a remote Hello World EJB (the EJB is
provided) by using the ORMI protocol
• Creating a stand-alone client to obtain a reference
to an EJB and JDBC data source

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 10-34


Practice 10-1
The aim of this practice is to write the code to perform JNDI lookup of an EJB and data
source object. To formulate an appropriate JNDI lookup request, you need to know only the
name of the EJB and how to call a method, which is similar to calling a method by using an
object reference in any Java application.
In JDeveloper, open the workspace practice10ske.jws in the practice10ske
directory and expand the usingjndi.jpr project. The project contains a HelloWorld
stateless session EJB and its deployment descriptor.
1. Enable the HelloWorldLocal.jsp application to invoke the greeting()
method of the HelloWorld session bean. The JSP and the session bean execute in
the same embedded OC4J container.
a. Open the HelloWorldLocal.jsp file and in the first scriptlet create an
initial context object and assign it to a Context variable called context.
b. Which package name is required in the import statement to compile this line of
code?
c. Now modify the string parameter value in the context.lookup() method to
be the name of the EJB.
Hint: Open the ejb-jar.xml file for the EJB and find the <ejb-name>
element.
d. Save your changes, compile the JSP, and correct any syntax errors.
e. Expand the usingjndi.impl package, and right-click the HelloWorld
node to run the HelloWorld EJB component in the embedded OC4J container.
f. Run HelloWorldLocal.jsp and observe the results in the generated HTML
page. The HTML page should contain the following text: “Result from the
HelloWorld greeting() method is: Hello World (from Stateless Session
EJB)”.
2. Create a stand-alone Java class, with a main() method to invoke the
HelloWorldEJB in the embedded OC4J container.
a. Right-click the usingjndi project, select New, and then click Simple Files and
create a new Java class called HelloWorldClient, making sure that the
Generate Main Method check box is selected.
b. In the default constructor, copy the code from the scriptlet of the
HelloWorldLocal.jsp into the body of a try block, with Exception
class being caught in the catch block.
Hint: Make sure that you import the javax.naming package and any others
that may be required in your class, and call the exception object
printStackTrace() method in the catch block.
c. In the last line of the try block, enter the following code to print the return
value of the greetings() method of the EJB:
System.out.println(helloWorld.greetings());
d. Right-click HelloWorldClient.java, and select Run from the menu.
e. You are expected to get an error. Can you explain the error?
Hint: Check the first line of the error message displayed.

Oracle 10g: Build J2EE Applications 10-35


Practice 10-1 (continued)
f. Modify the HelloWorldClient application to create a
java.util.Hashtable with JNDI properties set to the following values:
Context.INITIAL_CONTEXT_FACTORY set to the string
"com.evermind.server.rmi.RMIInitialContextFactory"
Context.SECURITY_PRINCIPAL set to "admin"
Context.SECURITY_CREDENTIALS set to "welcome"
Context.PROVIDER_URL set to
"ormi://localhost:23891/current-workspace-app"
Hint: Remember to add an import statement for the java.util.Hashtable.
Make sure that the port number in PROVIDER_URL is the same as the RMI port
number printed in the Embedded OC4J Container tab window in the Log
Message window.
g. Modify the HelloWorldClient application to provide the Hashtable
object as a parameter to the constructor when creating the InitialContext.
h. Right-click HelloWorldClient.java and select Run. The Log window
should show the bean message.
3. Open the UseDataSource.java file and write the JNDI code to obtain a data
source object from an OC4J server. You must run the HelloWorld EJB application
to start the embedded OC4J container.
a. In the try block of the UseDataSource() constructor, create a new
InitialContext with the same JNDI properties used in the
HelloWorldLocal.jsp application.
Hint: Use a Hashtable parameter with the InitialContext constructor,
or copy the jndi.properties file located in your
E:\JDeveloper\jdev\mywork\practice10ske directory to your
E:\JDeveloper\jdev\mywork\practice10ske\usingjdni\clas
ses directory, and use the no-arg constructor of the InitialContext.
You may need to edit the port number in the java.naming.provider.url
property of the jndi.property file.
b. Use the context object to create a javax.sql.DataSource object by
looking up the JNDI name of jdbc/oeDS.
c. Create a java.sql.Connection using the data source object by calling the
getConnection(), or the getConnection(user, pass) with your
database username and password.
d. Call the listDepartments() method using the JDBC connection object that
you opened from the data source to verify that your JNDI lookup works.
e. Compile the code and eliminate any syntax errors.
f. Run the HelloWorld EJB to launch the OC4J container.
g. Run the UseDataSource application. The application should display a list of
department ID and names in the JDeveloper Log window.

Oracle 10g: Build J2EE Applications 10-36


Practice 10-1 (continued)
Optionally, if you have time, then you can perform the following:
4. Alter the client applications to work with the HelloWorld EJB deployed to Oracle
Application Server 10g.
a. Right-click HelloWorldEJB.deploy and select Deploy to
OracleAS10g, or select Deploy to EAR file and deploy the resulting
EAR file by using the Oracle Enterprise Manager Web interface.
b. Modify HelloWorldClient.java and UseDataSource.java to work
with Oracle Application Server 10g.
c. Run HelloWorldClient.java. You should see the EJB message Hello
World (from Stateless Session EJB) displayed in the Log Message
window.
d. In HelloWorldClient.java, alter the code that executes the lookup()
method by passing the return value of the context.lookup() method to the
first parameter of the javax.rmi.PortableRemoteObject.narrow()
method.
Hint: PortableRemoteObject.narrow() requires
HelloWorldHome.class as a second parameter and an import
javax.rmi.PortableRemoteObject statement.
e. Run the HelloWorldClient.java application again, and it should yield the
same result as before. In the client code, you use
PortableRemoteObject.narrow()to resolve the remote object reference
obtained from the a JNDI lookup request into its target object type.
5. Modify HelloWorldClient.java or UseDataSource.java to use RMI over
HTTP tunneling.
Hint: Prefix PROVIDER_URL with http:.

Oracle 10g: Build J2EE Applications 10-37


Creating the Business Tier:
Enterprise JavaBeans

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Define an Enterprise JavaBean
• Describe the Enterprise JavaBeans (EJB)
architecture
• Describe the types of EJBs and when they
are used
• Explain EJB interfaces
• Define the steps to deploy an EJB to Oracle
Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson introduces Enterprise JavaBeans and how to create them in Oracle JDeveloper
10g.

Oracle 10g: Build J2EE Applications 11-2


Enterprise JavaBeans (EJB)

Enterprise JavaBeans are portable components,


which:
• Enable faster application development
• Allow reuse of business components
• Encapsulate business logic that can be invoked
by clients
• Execute in a container that provides services such
as support for transactions, persistence, and
access control for the beans

Copyright © 2005, Oracle. All rights reserved.

Enterprise JavaBeans
EJBs have the following features:
• EJBs reduce the burden on the developer, because the details of transaction support,
security, remote object access, and many other complicated and error-prone issues are
provided transparently to the developer by the EJB server and container.
• EJBs support a standard set of interfaces.
• EJBs consist of methods that encapsulate business logic. For example, an EJB may
have business logic that contains a method to update the customer data in a database. A
variety of remote and local clients can invoke this method.
• The container vendor provides the services that are required to make EJBs work.
Because all vendors support the same standard set of EJB interfaces, any EJB should
be able to execute in any EJB container. This complies with the “write once, run
anywhere” concept of Java. Oracle provides an EJB container in Oracle Application
Server 10g Containers for J2EE (OC4J).

Oracle 10g: Build J2EE Applications 11-3


When to Use EJBs

When developing a J2EE application, decide whether


to use EJBs based on the following requirements:
• The applications are complex and would benefit
from the system-level services that are provided
by an EJB container.
• The applications must be portable and scalable.
• The applications must be accessed by different
types of clients.

Copyright © 2005, Oracle. All rights reserved.

When to Use EJBs


When you develop a J2EE application, use the following requirements to decide whether to
use EJB APIs or another technology:
• The applications are complex and would benefit from the system-level services that are
provided by an EJB container. You might not be able to determine which API to use
for the application, based only on complexity. However, if data integrity is maintained
by using transactions, you can use an EJB container to manage these transactions.
• The applications must be portable and scalable. You might need to distribute your
applications across various platforms and make them available to multiple clients. EJB
applications provide location transparency.
• The applications may be accessed by different types of clients. One of the benefits of
EJB applications is that the clients requiring access to these applications need only a
few lines of code to locate and access them. Clients can be servlets, JSPs, applets,
stand-alone applications, or other local or remote server-side Java applications.

Oracle 10g: Build J2EE Applications 11-4


Types of EJBs

EJB Type Purpose

Session Beans Performs a task for a client

Entity Beans Represents a business object


that exists in a database

Message-Driven Beans Receives asynchronous Java


Message Service (JMS)
messages

Copyright © 2005, Oracle. All rights reserved.

Types of EJBs
Session Bean
A session bean implements one or more business tasks. A session bean can contain methods
that query and update data in a relational table. Session beans are often used to implement
services. For example, an application developer can implement one or several session beans
that retrieve and update inventory data in a database.
Entity Bean
An entity bean is a complex business entity. An entity bean models a business entity or
multiple actions within a business process. Entity beans are often used to facilitate the
business services that involve data and computations on that data. For example, an
application developer might implement an entity bean to retrieve and perform computation
on items in a purchase order. Your entity bean can manage multiple, dependent, and
persistent objects while performing its necessary tasks. An entity bean is an object that
manages persistent data, performs complex business logic, potentially uses several
dependent Java objects, and can be uniquely identified by a primary key.

Oracle 10g: Build J2EE Applications 11-5


Types of EJBs (continued)
Message-Driven Bean
Message-driven beans (MDBs) provide an easier method to implement asynchronous
communication than by using straight Java Message Services (JMS). MDBs were created to
receive asynchronous JMS messages. The container handles most of the setup processes that
are required for JMS queues and topics. It sends all the messages to the interested MDB. An
MDB allows J2EE applications to send asynchronous messages that can then be processed
by the application.

Oracle 10g: Build J2EE Applications 11-6


Session Beans
Session beans invoke methods for a single client.
There are two types of session beans:
• Stateless Session Beans (SLSBs)
– Conversation that spans a single method call
– Single request business processes that do not
maintain client-specific state
• Stateful Session Beans (SFSBs)
– Conversation with one client that may invoke many
methods
– Business processes that span multiple method
requests, thus maintaining state
EJB container EJB container
Pool of SLSBs SFSBs
Client 1 Client 1

Client 2 Client 2

Copyright © 2005, Oracle. All rights reserved.

Session Beans
Session beans represent verbs in the business process such as “process order.” Session beans
are classified based on the maintenance of the conversation state:
• Stateless session beans: Stateless session beans do not have an internal state. They do
not keep track of the information that is passed from one method call to another. Thus,
each invocation of a stateless business method is independent of its previous
invocation; for example, calculating taxes or shipping charges. When a method to
calculate taxes is invoked with a certain taxable value, the tax value is calculated and
returned to the calling method, without the necessity to store the caller’s internal state
for future invocation. Because they do not maintain state, these beans are simple to
manage for the container. When the client requests a stateless bean instance, it may
receive an instance from the pool of stateless session bean instances that are
maintained by the container. Because stateless session beans can be shared, the
container can maintain a lesser number of instances to serve a large number of clients.

Oracle 10g: Build J2EE Applications 11-7


Session Beans (continued)
• Stateful session beans: A stateful session bean maintains a conversational state across
method invocations; for example, an online shopping cart of a customer. When the
customer starts online shopping, the customer’s details are retrieved from the database.
The same details are available for the other methods that are invoked when the
customer adds or removes items from the cart, places the order, and so on. Yet, stateful
session beans are transient because the state does not survive session termination,
system crash, or network failure. When a client requests a stateful session bean
instance, that client is assigned one stateful instance, and the state of the bean is
maintained for that client.

Oracle 10g: Build J2EE Applications 11-8


Entity Beans
Entity beans represent a business object in the
database. They are:
• Sharable across multiple clients
• Uniquely identifiable through a primary key
• Persistent—the state survives an EJB server crash
There are two types of persistence in entity EJBs:
• Container-managed persistence (CMP) beans:
– The state of the bean is maintained by the
container.
– The bean developer specifies the persistent fields.
• Bean-managed persistence (BMP) beans:
– The state of the bean is maintained by the bean
itself.
– The bean developer writes the logic to manage
persistence by using Java Database Connectivity
(JDBC).

Copyright © 2005, Oracle. All rights reserved.

Entity Beans
An entity bean represents persistent data from the database. For example, an entity bean can
represent a row in a customer table, or an employee record in an employee table.
Entity beans are sharable across multiple clients. For example, an employee entity bean can
be used by various clients to calculate the annual salary of an employee or to update the
employee address.
Each entity bean instance is uniquely identified through its primary key.
An EJB server crash can result in the rollback of a transaction but does not destroy the entity
bean because the entity bean is a representation of permanent data from the database. The
same entity bean can be restored by reading from the persistent storage.
Specific fields of the entity bean object can be made persistent. Thus, based on their
persistence mechanisms, entity beans can be classified as follows:
• Container-managed persistence (CMP) beans: The container reads the information
of the persistent fields from the deployment descriptor and automatically manages the
persistence. The bean developer does not need to code the persistent logic because the
container performs all the functions that are necessary to save, load, and locate the
persistent data.
• Bean-managed persistence (BMP) beans: The bean developer must write the logic to
save, load, and locate the persistent data of the entity bean by using a persistence API
such as JDBC.
Oracle 10g: Build J2EE Applications 11-9
Message-Driven Beans

• Provide a facility for asynchronous


communication
• Exist within a pool, and receive and process
incoming messages from a JMS queue or topic
• Are invoked by the container to handle each
incoming message from the queue or topic
• Are similar to stateless session beans
JMS queue EJB container
Clients

Pool of MDBs

Copyright © 2005, Oracle. All rights reserved.

Message-Driven Beans
Message-driven beans provide an easier method to implement asynchronous communication
than by using straight Java Message Service (JMS). MDBs were created to receive
asynchronous JMS messages from JMS queues or topics. The container handles most of the
setup processes required for JMS queues and topics. It sends all messages to the interested
MDB. The container invokes a bean from the queue or topic to handle each incoming
message from the queue or topic. No object invokes an MDB directly: all invocation for an
MDB comes from the container. After the container invokes the MDB, it can invoke other
EJBs or Java objects to continue the request. MDBs are responsible for coordinating tasks
that involve other session or entity beans.
An MDB is similar to a stateless session bean because it does not save conversational state
and is used for handling multiple incoming requests. However, instead of handling direct
requests from a client, MDBs handle requests that are placed in a queue. The diagram in the
slide demonstrates this by showing how clients place requests on a queue. The container
takes the requests from the queue and gives the request to an MDB in its pool.

Oracle 10g: Build J2EE Applications 11-10


EJB Architecture

EJB server
EJB container
Home/local Home/
home local home
interface object
EJB
EJB client Class
Remote/ Remote/
local local
interface object Database

Enterprise Services
Deployment
Naming, Transaction, Security,
descriptor
Messaging

Copyright © 2005, Oracle. All rights reserved.

EJB Architecture
The diagram in the slide shows the major components (classes, interfaces, and services) in
the EJB architecture. A basic EJB architecture consists of the following major components:
• The EJB server provides the server-side framework and services to the components.
• An EJB container isolates the beans from the specifics of the server, hosts the beans,
and maintains their life cycles. They also provide services such as naming (Java
Naming and Directory Interface [JNDI]), security, and transaction (Java Transaction
Service [JTS]) control.
• The EJB classes are beans themselves. They are the business components of the
application, and contain the implementation of the business and life-cycle methods.
• Home/local home interfaces and home/local home objects are object factories. Using
them, the client can create, get a reference to, or destroy instances of beans.
• Remote/local interface and remote/local objects mediate a client’s request to access
business methods on the EJBs. The remote/local interface is generally referred to as
the component interface. The component interface defines the services that the bean
provides to the client program.
• EJB clients are the applications that access the business methods of the EJB through
the EJB container.
• The deployment descriptor is an XML file that describes how the EJB should be
installed (deployed) into the server/container.

Oracle 10g: Build J2EE Applications 11-11


EJB Server

• Manages the EJB container


• Provides a deployment and execution platform for
EJB components
• Provides system services to containers that in
turn provide services to beans:
– Transaction services
– JNDI naming services
• Can provide vendor-specific features such as
connection pooling

Copyright © 2005, Oracle. All rights reserved.

EJB Server
The EJB server provides a deployment platform and an organized environment to support
the execution of applications that are developed by using EJBs and other related
components. It provides services to the containers, which in turn provide services to the
bean. The EJB server manages and coordinates the allocation of resources to the
applications.
The EJB server makes EJB containers that are running within the server visible to the
outside world. The server provides JNDI-accessible naming services, secure socket layer
(SSL) support, transaction management services, and so on. All the bean home objects that
are hosted by the containers in the server are published in this server-provided naming
service. The clients look for the home interface by using the JNDI service.
The EJB server is responsible for communicating with the network, handling protocol
issues, and providing a place for the EJBs to execute.
EJBs are based conceptually on the Java Remote Method Invocation (RMI) model. For
example, remote object access and parameter passing for EJBs follow the RMI specification.
The EJB specification does not prescribe the transport protocol. The Oracle Application
Server 10g EJB server uses ORMI for its transport protocol.

Oracle 10g: Build J2EE Applications 11-12


EJB Container

• Manages the life cycle of the enterprise beans


• Isolates the enterprise beans from direct access
by client applications
• Makes required services available to the EJB
classes through well-defined interfaces
EJB container
Home/local home/local
home home
interface object
EJB Container
Client class generated
Remote/ remote/
local local
interface object

Copyright © 2005, Oracle. All rights reserved.

EJB Container
The EJB container supplies the run-time environment for a deployed EJB. Containers ensure
that the EJBs are deployed properly and present an interface between the bean and the
server. All the service requests that the bean makes from its infrastructure are directed to the
container, which in turn delegates them to the server. A container manages the entire life
cycle of the bean—that is, its creation, destruction, passivation, and activation. The
container also manages remote access to the bean, security, transaction, distribution, and
other infrastructure issues. It performs all these functions with the help of the server. The
container generates the home object and remote object.
The EJB container also provides a naming context for the object. A particular class of an
enterprise bean is assigned to one EJB container. When a client application invokes a remote
method on an enterprise bean, the container verifies the invocation to ensure that the
persistence, transactions, and security are applied properly to every operation that a client
performs on the bean.

Oracle 10g: Build J2EE Applications 11-13


Services Provided by the EJB Container

• Life-cycle management
• Bean instance pooling
• Client state management
• Database connection pooling
• Declarative transaction management
• Security
• Persistence

Copyright © 2005, Oracle. All rights reserved.

Services Provided by the EJB Container


The container manages the life cycle of the deployed EJB by creating, instantiating,
activating, passivating, and removing the bean instances as appropriate.
When a client requests a bean that is not already in the pool, the container creates a new
instance of the bean. If an instance is already there in the pool, the container retrieves an
instance of the bean from the pool (activates the bean) and assigns it to the client. Similarly,
when a client releases the bean, the container returns the bean to the pool (passivates the
bean). The container also removes the unused bean instances from the pool.
When a client requests an instance of a bean, the container may record the state of the client.
When the client requests the same bean after some time, the recorded state is copied into an
available instance from the pool and then allocated to the client. When the state is
maintained in this manner, the client cannot see any difference in the instances that are being
allocated.
When the server starts up, it pools a set of database connections. These connections can be
shared by many clients, and this increases the scalability of the applications.

Oracle 10g: Build J2EE Applications 11-14


Services Provided by the EJB Container (continued)
The application developer can leave the transaction management to the container by
declaring the methods or specific operations that need to be transaction-managed in the
deployment descriptor. The container then manages the operations such as rolling back or
committing a transaction.
Similar to transaction management, the application developer can declare the users, roles,
and access privileges in the deployment descriptor. The container then provides security to
the application by verifying the client’s privileges to various components of the application.
The application developer may request that the persistence of the data be managed by the
container. This is known as container-managed persistence (CMP).

Oracle 10g: Build J2EE Applications 11-15


EJB Client

An EJB client is a stand-alone application, servlet,


JSP, or another EJB that accesses the bean.
It can be a:
• Local client:
– Resides within the same Java virtual machine (JVM)
as the bean
– Passes arguments by reference to the bean
– Interacts with the EJB through methods defined in
the local interface
• Remote client:
– Is location independent
– Passes arguments by value to the bean
– Interacts with the EJB through methods defined in
the remote interface

Copyright © 2005, Oracle. All rights reserved.

EJB Client
An EJB client is the application that accesses the bean. Although it does not necessarily
reside on the client tier, a client can be a stand-alone application, JSP, servlet, or another
EJB.
The client accesses the methods on the bean class through the EJB container. The container
generates a proxy for the bean, called the remote or local object. The client obtains reference
to this object through the home interface. When the client invokes a business method on the
bean, the remote or local object receives the request, delegates it to the corresponding bean
instance, and returns the results to the client.
Because a local client must run in the same JVM as the EJB, there is less overhead in
looking up the bean instance. The client accesses the methods of an EJB through the local
home and local interfaces of the bean. The client passes arguments to the bean by passing
the location of the argument to the bean.
A remote client accesses the methods of an EJB through the home and remote interfaces of
the bean. The client may reside in a different JVM or on a different machine than the EJB.
However, there is overhead involved in looking up the bean instance to access the bean
methods. Additionally, the client passes arguments to the bean methods by value. That is, an
argument in a remote call is a copy of an object. The bean processes the argument at the
copied location. The disadvantage in this method is that if the size of the argument is large,
there can be considerable overhead in copying the argument to a different location.

Oracle 10g: Build J2EE Applications 11-16


EJB Interfaces and Classes

• Interfaces:
– Remote interface/Local interface
– Home interface/Local home interface
• Classes:
– Bean class
– Primary key class (entity beans)

Copyright © 2005, Oracle. All rights reserved.

EJB Interfaces and Classes


The EJB interfaces are classified as the following types:
• A remote interface that defines a bean’s business methods that are accessible by
remote clients
• A local interface that defines business methods that are accessible by local clients
residing in the same JVM as the bean
• A home interface that defines life cycles of a bean that are accessible by remote clients
• A local home interface that defines life-cycle methods for local clients
These interfaces are used only by session and entity beans. The message-driven beans do not
use these interfaces because the message-driven beans are not accessible by clients through
any method calls. Because an EJB can have both remote and local clients, it may have all
the four interfaces (mentioned above) defined on it.
An EJB class is:
• A bean class that actually implements the bean’s business methods
• A primary key class that uniquely identifies each entity bean. A primary key class is
not mandatory if a Java primitive type is used to identify an entity bean. In this case,
the deployment descriptor of the bean declares a unique field of the bean as its primary
key.
Note: Remote and local interfaces are generally referred to as the component interfaces.

Oracle 10g: Build J2EE Applications 11-17


Remote Interface and Remote Object

• Remote interface:
– Extends the javax.ejb.EJBObject interface that
extends the java.rmi.Remote interface
– Describes the client view of an EJB
– Declares the business methods that are accessible
to remote clients
• EJB object:
– Is a container-generated implementation of a
remote interface
– Is a reference object that a client receives
– Delegates the method calls to a bean class after
doing some infrastructure work
• The remote interface and remote object are used
by session and entity beans.
Copyright © 2005, Oracle. All rights reserved.

EJB Remote Interface and Remote Object


The bean developer writes a remote interface for each EJB in the application. The remote
interface declares the business methods that the bean contains. Each method in the bean to
which a remote client has access must be specified in the remote interface. Private methods
in the bean are not specified in the remote interface. The signature for each method in the
remote interface must match the signature in the bean implementation. (PL/SQL developers
recognize that the remote interface is much like a package specification, and the remote
interface implementation is similar to the package body. However, the remote interface does
not declare public variables. It declares only the methods that are implemented by the bean.)
The remote interface must be public, and it must extend javax.ejb.EJBObject.
All the methods in the remote interface are declared as throwing the
java.rmi.RemoteException exception. This is the usual mechanism for notifying
the client of run-time errors in the bean. However, the bean container can throw other
exceptions, such as SQLException. Any exception can be thrown to the client as long as
it is serializable. Run-time exceptions are transferred back to the client as remote run-time
exceptions. The remote object is generated by the container.

Oracle 10g: Build J2EE Applications 11-18


Home Interface and Home Object

• Home interface:
– Extends the javax.ejb.EJBHome interface that
extends the java.rmi.Remote interface
– Contains the life-cycle methods for creating,
removing, and locating the instances of a bean
class
– Contains home methods
– Are accessed by remote clients
• Home object:
– Is a container-generated implementation of the
home interface
– Uses callback methods on a bean class to perform
its functions

Copyright © 2005, Oracle. All rights reserved.

Home Interface and Home Object


The home interface defines the life-cycle methods to create, destroy, and find a bean
instance. When a client needs to create a bean instance, it does so through the home
interface. The client uses one of the create() methods specified by the home interface.
The client uses this home interface to obtain a reference to the bean’s remote interface. A
create() method can take parameters that are passed in from the client when the bean is
created.
For each create() method in the home interface, there must be a corresponding
ejbCreate() method specified in the bean class with the same signature. For the
remove() method in the home interface, there must be an ejbRemove() method in the
bean class. The home interface contains find methods for entity beans. A find method is a
method that starts with the findBy keyword. When a client invokes the create()
method on the home interface, the container interposes whatever services are required at that
point, and then calls the corresponding ejbCreate() method in the bean itself. The home
object is generated by the container. The client looks up the reference of the published home
object to create instances of the bean. The home interface uses the callback methods that
allow the container to notify the bean of events in its life cycle.

Oracle 10g: Build J2EE Applications 11-19


Local Interface and Local Home Interface

• Local interface:
– Extends the javax.ejb.EJBLocalObject interface
– Declares the business methods of the bean that are
accessible by a local client
– Improves performance because the bean resides in
the same JVM, and parameters are passed by
reference
• Local home interface:
– Extends the javax.ejb.EJBLocalHome interface
– Defines the life-cycle methods that are accessible
by local clients
• These interfaces are used by session and entity
beans.
• They enable relationships between entity beans.
Copyright © 2005, Oracle. All rights reserved.

EJB Local Interface and Local Home Interface


The local interface defines business methods that are accessible by local clients. The local
interface extends the javax.ejb.EJBLocalObject interface. Local interface methods
never throw the RemoteException exception.
The local home interface defines life-cycle methods that are accessible by local clients. The
local home interface extends the EJBLocalHome interface.
In addition to the fact that the business methods never throw the RemoteException
exception, the business methods of beans that implement the local interface receive
arguments by reference instead of by value.
Because the client and the bean are in the same JVM, and because the values are passed by
reference, there is less overhead in locating and accessing the bean from the client. This
improves performance.
Relationship between entity beans is possible only through local interfaces that are defined
on the beans. Relationship between the entity beans is discussed later in this course.

Oracle 10g: Build J2EE Applications 11-20


EJB Bean Class

• A bean class extends


javax.ejb.EnterpriseBean.
• A session/entity bean class:
– Implements javax.ejb.SessionBean /
javax.ejb.EntityBean
– Implements business/life-cycle methods
– Contains methods to support container callbacks
– Contains methods to set and unset the context of
the bean
• A message-driven bean class:
– Implements javax.ejb.MessageDrivenBean
– Must implement the MessageListener interface
– Contains business logic in the onMessage()
method
Copyright © 2005, Oracle. All rights reserved.

EJB Bean Class


Enterprise JavaBean is a Java class that defines the business methods and implements some
interfaces and methods to conform to the requirements of the specification. Business
methods are methods that represent the business tasks that a bean has to perform. These
methods are:
• Methods to support home interface functions: For each create() method specified
by the home interface, the bean class must specify an ejbCreate() and an
ejbPostCreate() method with the same signature.
• Methods to support container callbacks: Callback methods allow the container to
notify the bean of the events in its life cycle. The container informs the bean class
when it is about to activate the bean, persist its state to the database, end a transaction,
remove the bean from memory, and so on. This allows the bean class to restore or
close any resources as required.
• Methods that perform business tasks: A bean class must implement each of the
business methods that is described in the remote/local interface of the bean.
• Methods that set and unset the session and entity context: After it is set, the context
can be used later to access the methods of the bean.
For an MDB, as discussed earlier, there are no component interfaces. An MDB has a bean
class only and it contains the business logic in its onMessage() method.
The bean class is discussed in detail when each bean type is discussed later in this course.

Oracle 10g: Build J2EE Applications 11-21


The EJB Deployment Process
Developer’s
Home interface responsibility
Remote interface
Bean class
Other classes Component deployer’s
responsibility

Jar Deployment
Deployment EJB
command/ tools/
descriptor JAR
tool commands

Deployed EJB in the


Server

JNDI

Copyright © 2005, Oracle. All rights reserved.

The EJB Deployment Process


The EJB deployment process consists of the following steps:
• The EJB developer creates a JAR file containing the beans and their accompanying
classes, including the home and remote interfaces and any classes that are dependent
on the bean. This is known as the EJB JAR file.
• Each EJB JAR file has an EJB deployment descriptor, named ejb-jar.xml.
• If you are deploying your EJB to Oracle Application Server 10g, then create an Oracle-
specific deployment descriptor, named orion-ejb-jar.xml.
• Deploy the EJB by using a command-line tool such as Oracle Enterprise Manager, or
Oracle JDeveloper 10g. These tools:
- Read the deployment descriptor and the bean JAR file
- Map the logical names that are defined in the EJB deployment descriptor to
existing JNDI names and database tables
- Load the bean classes into the EJB server
- Publish the home interface of the bean
• The client application developer can then access the methods of the bean that are
provided with the remote interface name of the bean and the name of the published
beans.

Oracle 10g: Build J2EE Applications 11-22


ejb-jar.xml File
<ejb-jar>
<enterprise-beans>
<session>|<entity>|<message-driven>
<description>Say Hello</description>
<display-name>HelloWorld</display-name>
<ejb-name>HelloWorld</ejb-name>
<home>lesson11.HelloWorldHome</home>
<remote>lesson11.HelloWorld</remote>
<ejb-class>lesson11.impl.HelloWorldBean</ejb-class>
</session>|</entity>|</message-driven>
</enterprise-beans>
<assembly-descriptor>
<security-role> </security-role>
<method-permission> </method-permission>
<container-transaction> </container-transaction>
</assembly-descriptor>
</ejb-jar>

Copyright © 2005, Oracle. All rights reserved.

ejb-jar.xml File
The code in the slide shows major elements of an EJB deployment descriptor.
The tag <ejb-jar> indicates the beginning of the document. (The version and Document
Type Definition (DTD) for this XML file should be included before the beginning tag.) The
body of the deployment descriptor is enclosed within the <ejb-jar> and </ejb-jar>
tags.
Between the <enterprise-beans> and </enterprise-beans> tags, you declare
the details for the beans that are contained in this JAR file. The information described within
these tags contains the type of the bean, the names of the home and remote interfaces, and
the bean class. The details of the session beans are described with a <session> element,
those of entity beans with an <entity> element, and those of MDBs with a <message-
driven> element. Additionally, elements that are specific to individual EJB types are
contained within the bean descriptor. For example, a session bean should have a
<session-type> element, and an entity bean should have a <primary-key> element.
In the <assembly-descriptor> section, the security roles that are used to access the
beans and transaction attributes for the application are defined. Note that all the beans within
this JAR file share security and transactional declarations.
The details of the above elements are discussed in detail later in the course.

Oracle 10g: Build J2EE Applications 11-23


orion-ejb-jar.xml File

Oracle Application Server 10g uses the


orion-ejb-jar.xml file for deployment. This file:
• Specifies run-time attributes of the bean for
deployment to the container
• Enables customization of the run-time behavior of
enterprise beans

Copyright © 2005, Oracle. All rights reserved.

orion-ejb-jar.xml File
The orion-ejb-jar.xml file is the deployment descriptor for EJBs that are deployed to
Oracle Application Server 10g. It is used for customizing and specifying the dependencies of
the beans on the environment, such as resources and security, relationships between beans,
lists of parameters for controlling pooling, session timeout, interoperability, and concurrency
modes. The orion-ejb-jar.xml file is processed by OC4J at deployment. Note that
the ejb-jar.xml file is used for all J2EE containers. The orion-ejb-jar.xml is
specifically used by the OC4J server for EJB configuration within the OC4J container. Other
vendors have their own deployment descriptors, many of which can be created in
JDeveloper, although orion-ejb-jar.xml is created by default.

Oracle 10g: Build J2EE Applications 11-24


Creating an EJB in JDeveloper

Copyright © 2005, Oracle. All rights reserved.

Creating an EJB in JDeveloper


To create a new EJB in JDeveloper, select File > New > Business Tier > Enterprise
JavaBeans. You can choose the type of bean to create from the list of items.

Oracle 10g: Build J2EE Applications 11-25


Using the EJB Wizard

Copyright © 2005, Oracle. All rights reserved.

Using the EJB Wizard


After selecting the type of bean to create, enter the name of the EJB and the details of the
bean, depending on the type of bean that you selected.

Oracle 10g: Build J2EE Applications 11-26


Using the EJB Wizard

Copyright © 2005, Oracle. All rights reserved.

Using the EJB Wizard (continued)


You can easily create home and remote/local interfaces by using the wizard. After you click
Finish to generate the bean, JDeveloper creates the following files for you:
• ejb-jar.xml: The deployment descriptor for this EJB module, based on the
parameters you gave when using the wizard
• MySessionEJB: The EJB module containing all the components of the bean
- MySessionEJB.java: Contains the skeleton code for the remote interface
- MySessionEJBBean.java: Contains the skeleton code for the class,
including ejbCreate(), ejbRemove(), and so on
- MySessionEJBHome.java: Contains the skeleton code for the home
interface
• orion-ejb-jar.xml: The deployment descriptor for Oracle Application Server
10g

Oracle 10g: Build J2EE Applications 11-27


Adding Methods to the Bean

To add methods to the bean, right-click and select Go


To Bean Class:

Copyright © 2005, Oracle. All rights reserved.

Adding Methods to the Bean


When you select the Class Editor as shown in the slide above, you can add methods to the
bean by using the Add button, as shown in the following screenshot:

Oracle 10g: Build J2EE Applications 11-28


Deploying to Oracle Application Server
10g from JDeveloper

Copyright © 2005, Oracle. All rights reserved.

Deploying to Oracle Application Server 10g from JDeveloper


As stated previously, you can use a command-line tool, such as Oracle Enterprise Manager,
or JDeveloper, to deploy EJBs. To deploy from JDeveloper, right-click the ejb-jar.xml
file and select Create EJB JAR Deployment Profile. This creates a .deploy file, which
contains the details of the deployment. After creating the .deploy file, you can right-click
the file and select Deploy to OracleAS10g, where OracleAS10g is the name of your
application server connection.

Oracle 10g: Build J2EE Applications 11-29


Summary

In this lesson, you should have learned how to:


• Define an EJB
• Describe the EJB architecture
• Describe the types of EJBs and when they are
used
• Explain EJB interfaces
• Define the steps to deploy an EJB to Oracle
Application Server 10g

Copyright © 2005, Oracle. All rights reserved.

Summary
There are three types of EJBs:
• Session beans: Process business logic. They can access data from the database by
using direct JDBC calls, or by using an entity bean.
• Entity beans: Represent data in the database and also the methods to manipulate that
data. Each row of the data in a data object is represented by one entity bean.
• Message-driven beans: Are developed to enable asynchronous messaging with JMS
The EJB architecture contains:
• A server and container that are responsible for managing the life cycle of the EJBs and
for providing the system services. Deployment tools such as JDeveloper are used to
publish the beans on the EJB server.
• A client application that invokes methods on the bean
• A home interface that contains methods to create, find, and get metadata from the EJB
• A remote interface that describes the methods that a client application can invoke on
the EJB
• The bean class itself that contains the methods to process business logic
• Deployment descriptors that contain the properties of the bean that are used by the
container during the deployment process

Oracle 10g: Build J2EE Applications 11-30


Practice 11-1: Overview

This practice covers the following topics:


• Creating an EJB in JDeveloper
• Testing an EJB

Copyright © 2005, Oracle. All rights reserved.

Practice 11-1: Overview


In this practice, you observe the classes, interfaces, and deployment descriptor for a given
EJB.

Oracle 10g: Build J2EE Applications 11-31


Practice 11-1
The purpose of this practice is to reinforce the concepts of EJBs by creating a simple session
bean in JDeveloper, testing it, and deploying it.
1. Create a new EJB.
a. Navigate to the EJB project in the practice11ske.jws workspace. Right-
click the EJB project and select New.
b. From the Business Tier category, select Enterprise JavaBeans and select Session
Bean from the items list.
c. Select EJB 2.0 to create a session bean that complies with the 2.0 specification.
d. Accept the defaults for the name, session, and transaction types, and click Next.
e. Accept the defaults for the bean class and source directory, and click Next.
f. Accept the default to include the remote interfaces for the bean.
g. Click Finish to generate the EJB.
2. Add a field to the EJB that you have created.
a. Right-click the bean class that is generated for you and select "Go to Bean
Class."
b. Click the Class tab to open the class editor.
c. Click the Fields tab and add a String field named “hello” to the EJB.
d. Accept all the other field defaults and click OK.
e. Click the Source tab to view the code that is generated for you.
f. Select the bean in the System Navigator and double click the remote interface in
the Structure Pane.
g. Create a declaration in the remote interface for the setHello() and
getHello() methods. These methods should throw a
java.rmi.RemoteException exception.
3. Test the EJB.
a. Right-click the session bean that you created and choose Run. This starts the
embedded OC4J server and deploys the EJB. After the message “Oracle
Application Server Containers for J2EE 10g initialized ” appears, the bean is
running and you can access it with a client.
b. Right-click your session bean and select New Sample Java Client.
c. In the Sample EJB Java Client Details dialog box, select the option to connect to
the embedded OC4J server and click OK.
d. A new client file is created for you. View the code in the editor to see how the
client accesses the EJB that you created in step 1.
e. Uncomment the setHello() method and set the value to any String value.
f. Call getHello() and print it to the console.

Oracle 10g: Build J2EE Applications 11-32


Practice 11-1 (continued)
g. If the code was not added for you, obtain access to the InitialContext
object by copying and pasting the following code into the
getInitialContext() method:
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY,
"com.evermind.server.rmi.RMIInitialContextFactory");
env.put(Context.SECURITY_PRINCIPAL, "admin");
env.put(Context.SECURITY_CREDENTIALS, "welcome");
env.put(Context.PROVIDER_URL,
"ormi://localhost:23891/current-workspace-app");
return new InitialContext(env);
h. Finally, run the client by right-clicking the client and selecting Run
<yourclientname>. You should see the output in the EJB.jpr message
window containing your String value.

Oracle 10g: Build J2EE Applications 11-33


Implementing Business Tasks with
Session EJBs

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Describe session beans
• Differentiate stateless session beans from stateful
session beans
• Develop a home interface, a remote interface, and
a bean class for session beans
• Develop a client application to invoke the
business methods

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson introduces session beans and different types of session beans. You learn the
difference between stateless session beans and stateful session beans. You develop a
stateless session bean and a client application to invoke the stateless session bean.

Oracle 10g: Build J2EE Applications 12-2


Session Beans

A session bean:
• Implements business processes
• Is short-lived and has the lifetime of a client’s
session
• Does not survive server, machine, or network
crashes
• Is not saved in permanent storage
• Implements the javax.ejb.SessionBean
interface

Copyright © 2005, Oracle. All rights reserved.

Session Beans
You have learned about the different interfaces and the bean class that constitute Enterprise
JavaBeans (EJB). You have also learned that there are three types of enterprise beans:
session beans, entity beans, and message-driven beans (MDB). You now learn about session
beans.
A session bean implements one or more business processes. A session bean can perform any
business process. For example, it can retrieve and update inventory data in a database. Note
that the session bean can retrieve or update the data but it does not represent the persistent
data. That is, a session bean is not directly associated with a row of a table.
Session beans are short-lived. Their life cycles are dependent on the client’s session. When
there is a request for a session bean, the container instantiates the session bean and
associates one instance of this bean to the client. The EJB container uses management
methods for creating and destroying session beans.
Session beans are transient because they do not survive a server crash or a network failure.
If, after a crash, you instantiate a bean that had previously existed, then the state of the
previous instance is not restored. However, stateful session beans can survive crashes if they
are clustered.

Oracle 10g: Build J2EE Applications 12-3


Session Beans (continued)
Session beans are nonpersistent. They are in-memory objects that live and die with their
environments. Session beans are not saved to permanent storage.
All session beans must implement the javax.ejb.SessionBean interface, which in
turn extends the generic javax.ejb.EnterpriseBean interface. This interface must
be implemented because it provides the management methods that are used by the EJB
container to manage the life cycle of the session beans.

Oracle 10g: Build J2EE Applications 12-4


javax.ejb.SessionBean Interface

The SessionBean interface contains the following


callback methods:
• setSessionContext(SessionContext ctx)
• ejbActivate()
• ejbPassivate()
• ejbRemove()

Copyright © 2005, Oracle. All rights reserved.

javax.ejb.SessionBean Interface
Callback methods: A session enterprise bean class must implement the SessionBean
interface. This interface defines the methods that the container calls on the bean at various
stages to manage the bean life cycle and state. These methods are called callback methods.
The bean class must implement all the methods that are defined in the SessionBean
interface, or at least provide empty implementations. The client never directly accesses these
methods.
setSessionContext(SessionContext ctx): Enterprise beans are assigned a
context object when they are first created. Session beans are assigned a SessionContext
object. The beans save this context object for later processing. A bean uses its session
context to interact with the container regarding the security and transaction management.
The setSessionContext(SessionContext ctx)method takes this session
context as its parameter and is invoked in the beginning of the life cycle of a bean. This
method is invoked each time a session bean is created. The container calls
setSessionContext()on the bean instance when the client calls create()on the
home interface. Beans that manage their own transactions can use the session context to get
the transaction context. Session beans have session contexts that the container maintains and
makes available to the beans. The bean can use the methods in the session context to make
callback requests to the container.

Oracle 10g: Build J2EE Applications 12-5


javax.ejb.SessionBean Interface (continued)
ejbActivate(): The container invokes this method immediately after it returns a bean
instance from secondary storage (passivated state) to the main memory. The container
notifies the bean about activation before calling this method. The bean class can open any
closed resources at this stage.
ejbPassivate(): Instances of the beans that are no longer required can be moved to
temporary storage, such as a file system or database, by the container, thus releasing some of
the resources that the beans were using. This process is known as passivation. Passivating
the beans allows the container to efficiently manage the pool of beans in a cache. Just before
passivating the bean, the container uses this callback method to inform the bean that it is
going to be passivated. The implementation of this method in the bean class must have the
logic to release the resources that it might be holding. For example, the bean may close its
open files, database or network connections, open cursor objects, and so on.
ejbRemove(): A container invokes this method before it is about to remove the session
bean instance. This happens when the client invokes the home object’s remove() method
or when a container decides to terminate the session object after timeout. The container calls
this method on the bean before destroying the bean reference. This gives the bean instance a
chance to release some resources that it may be holding or to make some database updates
before it is destroyed. Note that the container may never call this method even if this method
is implemented. This can happen under circumstances such as container crashes, exceptions,
and so on.
The ejbRemove() method is a no-argument method that must be implemented by all the
beans. There is only one ejbRemove() method per bean.

Oracle 10g: Build J2EE Applications 12-6


Types of Session Beans

There are two types of session beans:


• Stateless session bean: A stateless session bean
does not maintain the state for a client.
• Stateful session bean: A stateful session bean
maintains the state for a client, and the instance
variable represents the state of a unique client.

Copyright © 2005, Oracle. All rights reserved.

Types of Session Beans


What is a conversation in terms of enterprise beans?
A conversation is an interaction between a client and a bean. This interaction is nothing but
the method calls between the client and the bean. Session beans are classified into stateless
session beans and stateful session beans depending upon their conversational state.
Stateless session bean: A stateless session bean does not maintain the conversational state
for a particular client. When a client invokes a method of stateless bean, the variables that
hold the state have some value. But these values persist only until the called method is
executed. When the client invokes another method of the stateless bean within the same
instance, the previous state of the instance is not maintained. After each method invocation,
a stateless session bean clears itself of all information pertaining to past invocation. Stateless
session beans are employed for business services that are not connected to any specific
client, such as generic currency calculations, mortgage rate calculations, and so on.

Oracle 10g: Build J2EE Applications 12-7


Types of Session Beans (continued)
Stateful session bean: A stateful session bean maintains the conversational state for a
particular client. It maintains the state of the client across method invocations and
transactions. Thus, there is one instance of a stateful session bean created for each client.
The container guarantees that no other client request is ever handled by the same stateful
session bean instance. The stateful session bean can also span across client sessions, because
the life of a stateful session bean’s handle is not bound to client sessions. Although stateful
session beans maintain the state of a client, the information does not survive system crashes.
However, clustered stateful session beans in OC4J can survive crashes.

Oracle 10g: Build J2EE Applications 12-8


When to Use Session Beans

• The state of the bean need not be persistent.


• Use stateless session beans when:
– The state need not be maintained for a client
– A general task must be performed
– Data is fetched only from a database, and data
manipulation is not necessary
• Use stateful session beans when:
– Interaction between bean and client must be
maintained across method calls and transactions
– A bean works on logic based on entity beans that
represent persistent data

Copyright © 2005, Oracle. All rights reserved.

When to Use Session Beans


Session beans model business processes or tasks and interactions; for example, a session
bean can be used to process an order by calculating discounted prices. Session beans are
generally represented by verbs.
A stateful session bean can work on logic based on the data represented by the entity bean. If
a bean is used to calculate discounted prices, then an entity bean can represent the prices of
products. The session bean can get the data by invoking methods of an entity bean and
applying the necessary business logic.
Session beans do not store persistent states. When the state of the bean need not be persistent
or when the state must be available for only a short period of time, you can use session
beans.
You can use a stateless session bean in the following situations:
• When the bean state need not be associated with a specific client
• When a general task must be performed, such as sending an e-mail when the order has
been processed
• When you need to fetch read-only data from a database, such as to display the video
rentals that are available in a week

Oracle 10g: Build J2EE Applications 12-9


When to Use Session Beans (continued)
You can use a stateful session bean in the following situations:
• When the bean state must be associated with interaction from a specific client between
method invocations, such as in an online shopping cart
• When the bean must manage the logic by using data retrieved from the database, using
the entity beans. For example, an online shopping cart might need to retrieve product
information, customer information, and so on, to complete the processing for a
particular customer. The information about products and customers may be obtained
through entity beans representing the persistent data.

Oracle 10g: Build J2EE Applications 12-10


Life Cycle of a Stateless Session Bean

Does not
exist

Container invokes Container invokes


class.newInstance, ejbRemove() .
setSessionContext(sessCtx),
and ejbCreate().

Ready

Copyright © 2005, Oracle. All rights reserved.

Life Cycle of a Stateless Session Bean


You have learned that stateless session beans do not hold any state for a client. Therefore, all
instances of the same stateless session bean class are equivalent and indistinguishable to a
client. Any stateless session bean instance can service any client request. These beans are
easily reused by multiple clients.
Taking advantage of the fact that stateless session beans do not maintain conversational
state, EJB containers pool stateless session bean instances before the clients connect. When
a client calls a method, the container retrieves one instance from the pool to service the
client. This instance is returned to the pool when the client’s request is served. This enables
the container to dynamically assign bean instances to different clients. The slide shows the
life cycle of a stateless session bean.
The container verifies whether there are instances of a stateless session bean. If there are no
instances or fewer instances than needed, it invokes the newInstance()method on the
bean class to create an instance. Then the container invokes the
setSessionContext(SessionContext)and ejbCreate()methods on the bean
instance. Now a client can invoke methods on this instance. The container can invoke the
ejbRemove() method to remove the instance from the pool and free the resources.

Oracle 10g: Build J2EE Applications 12-11


Home Interface for Stateless
Session Beans

import javax.ejb.EJBHome;
import java.rmi.RemoteException;
import javax.ejb.CreateException;
public interface StatelessejbHome extends
EJBHome
{
Statelessejb create() throws RemoteException,
CreateException;
}

Copyright © 2005, Oracle. All rights reserved.

Home Interface for Stateless Session Beans


You have already learned that home interfaces define methods for creating, destroying, and
finding EJB objects. The home interface acts as the factory for EJB. Note that the home
interface StatelessejbHome contains a single create()method that does not take
any argument. Stateless session beans do not hold any state for a client between method
invocations. Therefore, it does not make sense to provide overloaded forms—create()
methods with different argument list—of the create() method. The create() method
throws a javax.rmi.RemoteException exception, because the home object is a
Remote Method Invocation (RMI) remote object. The EJBHome interface extends the
javax.rmi.Remote interface. All methods of objects extending the
javax.rmi.Remote interface must throw the RemoteException exception.
You can have remote home interfaces or local home interfaces. A remote client accesses a
bean through the bean’s remote home interface. When you define a local component
interface, you define a local home interface. A local home interface extends the
javax.ejb.EJBLocalHome interface. Although a bean can have both the remote and
the local interfaces, it is common to provide either of the interfaces, but not both.

Oracle 10g: Build J2EE Applications 12-12


Home Interface for Stateless Session Beans (continued)
A local client accesses a bean through the bean’s local home interface. A local client is
collocated in the same Java virtual machine (JVM) with the bean that it is accessing.
If you define local interfaces, then they can be used only in the same application. You have
faster access to the beans because RMI calls are avoided. If you define remote interfaces,
then they can be used with both local and remote applications. The access is slower
compared with beans with local interfaces, because RMI calls are required.

Oracle 10g: Build J2EE Applications 12-13


Remote Interface for Stateless
Session Beans

import javax.ejb.EJBObject;
import java.rmi.*;

public interface Statelessejb extends


EJBObject
{
public String incrementValue() throws
RemoteException;
public int getValue()throws RemoteException;
}

Copyright © 2005, Oracle. All rights reserved.

Remote Interface for Stateless Session Beans


Clients access the entity object through component interface reference. Component
interfaces can be remote or local interfaces. Component interfaces define business methods
that are accessible by the client. They may also define the get() and set()methods to
get and set bean attributes.
A remote interface is the component interface that is accessed by remote clients. A remote
interface extends the javax.ejb.EJBObject interface. Methods that are declared in
the remote interface should throw the RemoteException exception.
The local interface is the component interface that is accessed by local clients. A local
interface extends the javax.ejb.EJBLocalObject interface. Methods in the local
interface must not throw the RemoteException exception.
The slide shows a remote interface, which contains the business methods that are
implemented in the bean. Though the bean class implements these methods, the bean class
does not implement the remote interface. The container implements the remote interface and
this implementation is the EJB object that is responsible for delegating the client’s request to
the beans. The remote interface shown in the slide has two business methods:
incrementValue() and getValue(). These methods are implemented in the bean
class.

Oracle 10g: Build J2EE Applications 12-14


The Session Bean Class

• The class must be defined as public, must not be


final, and must not be abstract.
• The class must implement ejbCreate() methods:
– There must be an ejbCreate() method for each
create() method of the home interface.
– The signatures of the two methods mentioned
above should match.
– The return type of the ejbCreate() method
should be void.
– Remote or create exceptions need not be thrown.
• The class can optionally implement the
SessionSynchronization interface.

Copyright © 2005, Oracle. All rights reserved.

The Session Bean Class


The bean class must be public and must not be final or abstract.
ejbCreate(): The container invokes this method immediately before it creates the bean.
Stateless session beans must not do anything in this method. Stateful session beans can
initiate state in this method. The create() method is used to initialize the state of a bean.
Because there is no state maintained, stateless session beans implement a no-argument
create()method.
Session beans are initialized through the ejbCreate() method. Because the
ejbCreate() method is not part of the SessionBean interface, it must be provided by
the bean developer.
• There must be one ejbCreate() method corresponding to each create() method
of the home interface. Signatures of these two methods must match. Stateless session
beans contain only one ejbCreate() method, which cannot contain any parameters,
because stateless session beans do not store their states.
• When the client calls a create() method of the home interface, the parameters, if
any, are passed by the container to the corresponding ejbCreate() method of the
bean class. This ejbCreate() method of the bean class performs any initialization
that is required for the bean.

Oracle 10g: Build J2EE Applications 12-15


The Session Bean Class (continued)
• The return type of the ejbCreate() method must be void. Even though the
create() method of the home interface returns an object that implements the remote
interface, the actual creation of this object is the responsibility of the container.
• The ejbCreate() method need not throw the remote and create exceptions because
the container may throw these exceptions. If any application-specific exceptions are to
be thrown for this method, then those exceptions must also be thrown in the
corresponding create() method.
A session bean should implement the SessionSynchronization interface if it needs
to synchronize its state before and after the start and completion of a transaction. The
SessionSynchronization interface allows a session bean instance to be notified by
its container of transaction boundaries.
The methods of this interface notify the bean instance when a new transaction has started,
when a transaction is about to be committed, and when a transaction is complete. These
methods help the bean instance to read data from a database and cache the data in its
instance fields or write cached data to the database. After the transaction is complete, the
bean instance can discern whether the transaction has been committed or rolled back.

Oracle 10g: Build J2EE Applications 12-16


The Session Bean Class:
Business Methods

• The bean class may define zero or more methods


to process the business logic.
• The business methods that are to be accessed by
the client applications must be public.
• The business methods must not be declared as
final or static.
• The business methods that are to be accessed by
clients must be exposed through the component
interface.
• The method arguments and return types must be
legal types for RMI.
• Application-specific exceptions can be thrown.

Copyright © 2005, Oracle. All rights reserved.

The Session Bean Class: Business Methods


The bean class may provide zero or more business methods that contain the business logic.
All the business methods of the bean class that need to be accessed by the client applications
must be exposed through the component interface with the same signature. These methods
must be public.
The container delegates all the business method calls to the bean instance, after performing
some preliminary tasks such as security checks and transaction demarcation. The business
methods can throw any application-specific exception. These exceptions are passed as such
to the client, invoking the method.

Oracle 10g: Build J2EE Applications 12-17


Bean Class for the Stateless
Session Bean
...
public class StatelessejbBean implements SessionBean
{
int value =0;
public void ejbCreate() { }
public void ejbActivate() { }
public void ejbPassivate(){ }
public void ejbRemove() { }
public void setSessionContext(SessionContext ctx) { }
public String incrementValue() {
value++;
return " value incremented by 1"; }
public int getValue()
{
return value;
}
}

Copyright © 2005, Oracle. All rights reserved.

Bean Class for the Stateless Session Bean


The bean class contains all the container callback methods. These methods are invoked by
the container to manage the life cycle of the beans. You can include several ejbCreate()
methods corresponding to the create() method in the home interface. The bean class
must have at least one ejbCreate() method. The slide shows the bean class for a
stateless session bean. It contains a single instance variable called value, which is
initialized to 0. It also contains the ejbCreate() method and the implementation of the
business methods.

Oracle 10g: Build J2EE Applications 12-18


Deployment Descriptor

<?xml version = '1.0' encoding = 'windows-1252'?>


<!DOCTYPE ejb-jar PUBLIC "-//Sun Microsystems, Inc.//DTD
Enterprise JavaBeans 2.0//EN" "http://java.sun.com/dtd/ejb-
jar_2_0.dtd">
<ejb-jar>
<enterprise-beans>
<session>
<description>Session Bean ( Stateless ) </description>
<display-name>statelessejb</display-name>
<ejb-name>Statelessejb</ejb-name>
<home>StatelessejbHome</home>
<remote>Statelessejb</remote>
<ejb-class>StatelessejbBean</ejb-class>
<session-type>Stateless</session-type>
<transaction-type>Container</transaction-type>
</session>
</enterprise-beans>
</ejb-jar>

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor
The code in the slide is an example of a deployment descriptor written in Extensible Markup
Language (XML) for the stateless session bean StatelessejbBean.
The <ejb-jar> tag is the root element that is defined for a deployment descriptor. The
body of the deployment descriptor is enclosed within the <ejb-jar> and </ejb-jar>
tags.
Between the <enterprise-beans> and </enterprise-beans> tags, you declare
the definition of the beans that are contained in this JAR file. In the above example, the code
between the <session> and </session> tags indicates that the JAR file contains a
session bean. Within these tags, there are tags for:
• Optional description of the bean.
• Mandatory logical name of the bean that is used by the container while diverting the
client’s method calls to the appropriate bean on the server (Statelessejb).
• Mandatory home interface, remote interface, and bean class names.
• Mandatory session-type indicating that the bean is a stateless session bean. If the
bean is a stateful bean, then the session-type is stateful.
• Mandatory transaction-type (applicable only to session beans), indicating
whether the transaction is managed by the container or by the bean.

Oracle 10g: Build J2EE Applications 12-19


Client Application

To access methods on the bean instance, an EJB


client must perform the following operations:
• Obtain access to the naming service (Java Naming
and Directory Interface [JNDI]) where the bean’s
home interface is published
• Authenticate itself with the naming service
interface
• Obtain a reference to the bean’s home interface
from the naming service by using the bean’s URL
• Invoke the create() method on the home
interface
• Invoke business methods

Copyright © 2005, Oracle. All rights reserved.

Client Application
An EJB client cannot access an EJB method directly. It must obtain a bean reference by
using the create() method of a bean’s home interface, and then invoke the business
methods on the bean reference that have been obtained.
To use the create() method of a bean’s home interface, the client must first obtain the
reference to the home interface of the bean. When a bean is deployed in a server or
container, the server or container publishes the home interface of the bean in a publicly
available JNDI service. The create() method creates an instance of the bean in the server
and returns its reference to the client. The clients can obtain the reference to the bean home
interface by looking for it in the JNDI.
JNDI consists of several published objects that are arranged in a hierarchical manner. You
must know the URL of the object that you want to locate.

Oracle 10g: Build J2EE Applications 12-20


Client Application for Stateless
Session Beans
...
public class StatelessejbClient
{
public static void main(String [] args)
{
StatelessejbClient statelessejbClient = new
StatelessejbClient();
try
{Context context = getInitialContext();
StatelessejbHome statelessejbHome =
(StatelessejbHome)PortableRemoteObject.narrow
(context.lookup("Statelessejb"),
StatelessejbHome.class);
//create 3 instances
Statelessejb obj[] = new Statelessejb[3];
for (int i=0;i<3;i++)
{ obj[i]= statelessejbHome.create(); }
...

Copyright © 2005, Oracle. All rights reserved.

Client Application for Stateless Session Beans


The code in the slide shows a part of the client for a stateless session bean. The client
application imports classes in the javax.naming package that are necessary to create the
contexts and environment parameters for the JNDI naming service. Context is an interface
in the javax.naming package. All EJB clients that use JNDI methods to look up and
activate the remote or local objects must import this interface.
The first JNDI call to code is the one that gets a context object. The first context object that
you get is called the InitialContext and is bound to the root naming context of the
JNDI namespace. EJB home interfaces are published in the EJB server, arranged in a file
system–like hierarchy. You get the root naming context by creating a new JNDI
InitialContext, as shown in the slide.
To find the Statlessejb home object in the context path, you use the lookup method.
The result of the lookup is cast to obtain the home interface by using the
javax.rmi.PortableRemoteObject.narrow method.

Oracle 10g: Build J2EE Applications 12-21


Client Application for Stateless Session Beans (continued)
The lookup() method to obtain remote reference returns an Object type. The EJB 1.0
specification uses Java RMI type arguments and return types, assuming that the client and
server are Java applications. Because the clients can be written in any programming
language, in the EJB 2.0 specification, Java RMI-IIOP (Java RMI over IIOP) is the required
programming model to follow Common Object Request Broker Architecture (CORBA)
standards. Internet Inter-ORB Protocol (IIOP) requires the returned remote references from
any method to be narrowed to a specific type that can be used by any protocol that accesses
the bean. This can be implemented by using the
javax.rmi.PortableRemoteObject.narrow method. The narrow()method
takes two parameters: the remote reference to be narrowed and the type it to which it should
be narrowed. This method returns a stub that implements the specified remote reference,
which can then be cast to the required remote interface type. In the previous example, the
lookup() method returns an Object type homeObject for remote reference of
Statelessejb. This reference homeObject is then narrowed to
StatelessejbHome class and cast to the StatelessejbHome interface type.
You explicitly narrow the reference by using the narrow() method, only when a method
returns a general remote reference such as EJB home or EJB object. In this case, you must
narrow and cast the returned type to a more specific remote interface type, as shown in the
above example.
You do not explicitly narrow a remote reference if a method returns a specific remote
interface type.
You obtain reference to the home interface and remote interface and narrow the objects to
the EJB home and remote interfaces.

Oracle 10g: Build J2EE Applications 12-22


Client Application for Stateless
Session Beans

...
// Invoke the business methods with each of the
// instances created to observe the state of each
// instance
for (int i=0;i<3;i++)
{
System.out.println("Value before increment for
object" + i + " "+ obj[i].getValue());
System.out.println( "Calling incrementValue with
object" + i+" " +obj[i].incrementValue());
System.out.println("Calling getValue with
object" + i+" " +obj[i].getValue()+"\n");
}
for (int i=0;i<3;i++)
{ obj[i].remove(); }
...

Copyright © 2005, Oracle. All rights reserved.

Client Application for Stateless Session Beans (continued)


The code in the slide is the continuation of the client application for a stateless session bean.
The client code creates three instances and invokes the incrementValue() and
getValue() methods with each instance. Recollect that the variable value is initialized
to zero in the bean class.
The output of the client application is as follows:
Value before increment for object0 0
Calling incrementValue with object0
value incremented by 1
Calling getValue with object0 1

Value before increment for object1 1


Calling incrementValue with object1
value incremented by 1
Calling getValue with object1 2

Value before increment for object2 2


Calling incrementValue with object2
value incremented by 1
Calling getValue with object2 3

Oracle 10g: Build J2EE Applications 12-23


Client Application for Stateless Session Beans (continued)
Initially the value is zero (initialized in the bean class). When object[0] calls the
incrementValue() method, the value is incremented to 1. When the method is invoked
with object[1], the container has not created another instance of the session bean. The
same bean is used to serve this client. Therefore, the value is incremented to 2, and so on.
The instance variable cannot be reinitialized to zero, because the create() method of a
stateless session bean does not take a parameter such as the create() method of a stateful
session bean.

Oracle 10g: Build J2EE Applications 12-24


Life Cycle of a Stateful Session Bean

Does not
exist

setSessionContext(sessCtx), Container invokes


and ejbCreate() ejbRemove()

ejbPassivate()

Ready Passivated
instances
ejbActivate()

Copyright © 2005, Oracle. All rights reserved.

Life Cycle of a Stateful Session Bean


The client initiates the life cycle of the stateful session bean by invoking the create()
method. The EJB container instantiates the bean and calls the setSessionContext()
and ejbCreate() methods of the session bean. The client can now invoke business
methods on the session bean instance. When the objects are in the pool, the EJB container
can passivate the bean by moving it from memory to secondary storage. The container
invokes the ejbPassivate() method just before passivating the instance. If a client
invokes a business method on the bean while it is in the passive stage, the EJB container
activates the bean. It calls the ejbActivate()method.
To remove the bean instance, the container invokes the ejbRemove() method and the
bean instance is ready for garbage collection.

Oracle 10g: Build J2EE Applications 12-25


Home Interface for Stateful Session Bean

import javax.ejb.EJBHome;
import java.rmi.RemoteException;
import javax.ejb.CreateException;
public interface StatefulejbHome extends
EJBHome
{
Statefulejb create(int x) throws
RemoteException, CreateException;
}

Copyright © 2005, Oracle. All rights reserved.

Home Interface for Stateful Session Bean


This is the same example that was used to demonstrate the stateless session bean. The home
interface contains the create() method as in the case of a stateless session bean.
However, the difference is that the create() method of a stateful session bean can take
parameters. The create() method shown in the slide takes an integer as parameter to
initialize the value of the value variable.
The remote interface for the stateful session bean is the same as that for a stateless session
bean. The bean class for the stateful session bean implements the business methods as in a
stateless session bean. However, the implementation of the ejbCreate()method in the
bean class is as follows:
public void ejbCreate(int x)
{ value=x; }

Oracle 10g: Build J2EE Applications 12-26


Client Application for Stateful
Session Bean

...
Statefulejb obj[]= new Statefulejb[3];
for (int i=0;i<3;i++)
{ obj[i]= StatefulejbHome.create(0); }
for (int i=0;i<3;i++)
{
System.out.println("Value before increment for
object" + i + " "+ obj[i].getValue());
System.out.println( "Calling incrementValue with
object" + i+" " +obj[i].incrementValue());
System.out.println("Calling getValue with
object" + i+" " +obj[i].getValue()+"\n");
}
for (int i=0;i<3;i++)
{ obj[i].remove(); }
...

Copyright © 2005, Oracle. All rights reserved.

Client Application for Stateful Session Bean


The slide shows a part of the client application that is used to invoke the business methods
of the bean. The bean instances are created by passing a value 0 in the create() method.
Therefore, the value for the variable value is initialized to zero. The following output is
displayed when you run the client application:
Value before increment for object0 0
Calling incrementValue with object0
value incremented by 1
Calling getValue with object0 1

Value before increment for object1 0


Calling incrementValue with object1
value incremented by 1
Calling getValue with object1 1

Value before increment for object2 0


Calling incrementValue with object2
value incremented by 1
Calling getValue with object2 1
Note that for all instances, the value variable is 0 and then incremented to 1, unlike in
stateless session beans.

Oracle 10g: Build J2EE Applications 12-27


Summary

In this lesson, you should have learned how to:


• Describe session beans
• Differentiate stateless session beans from stateful
session beans
• Develop a stateless session bean
• Develop a client application to invoke a stateless
session bean

Copyright © 2005, Oracle. All rights reserved.

Summary
In this lesson, you should have learned about session beans and the types of session beans.
You should have also learned to develop a stateless session bean and invoke it with a client
application.

Oracle 10g: Build J2EE Applications 12-28


Practices 12-1 and 12-2: Overview

These practices cover the following topics:


• Creating a session bean to validate a card
• Creating a session bean to display the
first_name, last_name, email, and
department_name of an employee whose
employee_id is provided

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 12-29


Practice 12-1
The purpose of this practice is to create a stateless session bean that validates the entry made
for the customer card number. The bean should contain a business method that takes the
customer card number in the form of a string and validates the card. Note that this practice
does not validate the card number against the database. A card number can be alphanumeric.
A card is valid if:
• The length of the number is nine characters.
• It starts with AN, BN, CN, or LN
• The last character is A
• The rest of the characters are numbers and not letters
The workspace for this practice is practice12oneske.jws. Open the
validatecard project. This project contains the necessary skeleton files for this
practice.
1. Expand the validatecard node, select the ValidateCard EJB, and double-
click ValidateCard.java in the Structure Pane to open it in the code editor. This
is the remote interface.
a. Import the java.rmi package.
b. Declare a method called validate(), which takes a string as parameter and
returns a string. This method should throw a RemoteException exception.
2. Add code to the bean class. Open ValidateCardBean.java in the code editor.
Implement the validate()method that is declared in the remote interface. This
method should verify that the card is valid. The conditions for the validity of the card
are given above.
3. Generate a sample Java client. Right-click the ValidateCard bean in the navigator
and select New Sample Java Client. Select Connect to OC4J Embedded in JDeveloper
if you are testing your EJB with the embedded OC4J, otherwise select Connect to
Remote Application Server. Click OK.
4. Invoke the validate()business method from the client application
ValidateCardClient.java:
Add code to the try block of the main()method to invoke the validate()
method. Invoke the method twice: once with a valid card number and once with an
invalid card number.
5. Test and run the application:
a. Right-click ValidateCard bean and select Make (optional).
b. Right-click ValidateCard bean and select Run.
c. Right-click the client application and select Run.

Oracle 10g: Build J2EE Applications 12-30


Practice 12-1 (continued)
6. Sample Input/Output:
If the following lines are added to the client application:
System.out.println("Passing a valid customer card number
BN349672A ");
System.out.println(validateCard.validate("BN349672A"));
System.out.println("Passing an invalid customer card
number BN3496723A");
System.out.println(validateCard.validate("BN3496723A"));
The output is:
Passing a valid customer card number BN349672A
THANKYOU FOR PROVIDING YOUR CUSTOMER CARD NUMBER
Passing an invalid customer card number BN3496723A
Ensure that you enter right number of characters
Note: This is only a sample input/output. The error messages may be different
depending on your implementation.

Oracle 10g: Build J2EE Applications 12-31


Practice 12-2
The purpose of this practice is to create a stateless session bean that interacts with the
database by using JDBC. So far you have used the oe schema for the practices. In this
practice, you create a connection to the hr schema and create the data source reference to it.
The bean should contain a business method that takes the employee_id and retrieves
first_name, last_name, email, and department_name from the EMPLOYEES
table and the DEPARTMENTS table. The business method returns an instance of
EmployeeDetails class. This instance has variables to hold the first name, last name, e-
mail, and department name of the employee.
Note: The EMPLOYEES table has many fields, some of them are first_name,
last_name, and email. However, the EMPLOYEES table does not contain the
department_name. The DEPARTMENTS table has department_name, and the
common field in both the EMPLOYEES and DEPARTMENTS table is department_id.
Therefore, you can join the two tables to obtain the department_name. For the
description of each of these tables, refer to Appendix B.
The workspace for this practice is practice12twoske.jws. Open the
employeedetails project and expand the employeedetails node. The Employee
bean contains the skeleton files that are required to implement the session bean.
1. Create the connection to use as the data source for the session bean:
a. In the Connection Navigator, right-click Database and select New Database
Connection. You see the Connection Wizard. Click Next.
b. Provide hr for Connection Name and select Oracle (JDBC) as Connection Type.
Click Next.
c. Provide the username and password as oraxx/oracle (as provided by your
instructor). Click Next.
d. Specify the Host Name, JDBC port, and SID, as indicated by your instructor.
Click Next.
e. Test the connection by clicking the Test Connection button. Click Finish.
2. Edit the EmployeeDetails.java file in the code editor:
a. Import java.io package.
b. Declare four string variables: fname, lname, email, and deptname.
c. Provide a constructor that takes parameters to initialize all four instance
variables.
d. Override the toString() method to provide a string representation of the
object.
3. Modify the remote interface:
a. Navigate to Employee.java and open it in the code editor.
b. Import the java.rmi package.
c. Declare a getDetails() method that takes an integer as argument and returns
an EmployeeDetails object. This method should throw the
RemoteException exception.

Oracle 10g: Build J2EE Applications 12-32


Practice 12-2 (continued)
4. Modify the bean class:
a. Open the EmployeeBean.java file in the code editor.
b. Import the packages java.sql, javax.naming, javax.sql, and
employeedetails (contains the EmployeeDetails class).
c. Declare the following instance variables: Connection variable conn,
Statement variable st, and ResultSet variable rs.
5. Implement an establishConnection() method that returns a Connection
object as follows:
a. Declare variable ds of type DataSource.
b. Start a try block, and get the initial context and lookup for the data source
jdbc/hrDS. This code can throw a NamingException exception.
c. Get the connection by invoking the getConnection() method on the data
source. This can throw a SQLException exception. You can have two catch
blocks, or you can catch the generic exception.
d. Close the try block and add catch blocks.
e. Return the connection.
6. Implement the getDetails() method as follows:
a. It should take an integer as argument, which is the employee_id of an
employee, and return an instance of EmployeeDetails class.
b. Create a variable emp of type EmployeeDetails.
c. Start a try block. Call the establishConnection() method to initialize
the Connection object conn. Create a Statement with this object.
d. Execute the query to retrieve employee first_name, last_name, and
email from the EMPLOYEES table and department_name from the
DEPARTMENTS table.
e. Create an instance called EmployeeDetails class with first_name,
last_name, email, and department_name as parameters.
f. Close the try block and catch generic exception.
g. Return EmployeeDetails object emp.
7. Edit the client application EmployeeClient.java in the code editor. Invoke the
getDetails()business method:
a. Add code to the try block of the main() method to invoke the
getDetails() method.
8. Test and run the application:
a. Right-click Employee bean and select Make (optional).
b. Right-click Employee bean and select Run.
c. Right-click the client application and select Run.
9. Sample Input/Output:
If the following line is added to the client application:
System.out.println(employee.getDetails(119));
The output is:
Karen Colmenares KCOLMENA Purchasing

Oracle 10g: Build J2EE Applications 12-33


Managing Persistent Data in
the Business Tier

Entity EJBs

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Identify the features of an entity bean
• Distinguish between session beans and entity
beans
• Decide when to use an entity bean
• Describe the various components of an entity
bean
• Differentiate bean-managed persistent beans from
container-managed persistent beans

Copyright © 2005, Oracle. All rights reserved.

Objectives
This lesson introduces the concept of entity beans and the different types of entity beans.
You learn about the different components of an entity bean and the differences between
entity beans and session beans.

Oracle 10g: Build J2EE Applications 13-2


Entity Beans

• Are objects that can be stored in permanent


storage
• Represent persistent data in the database
• Can be uniquely identified
• Do not contain complex business logic
• Do not model business processes but manage
data for such processes
• Can serve multiple clients simultaneously

Copyright © 2005, Oracle. All rights reserved.

Entity Beans
Entity beans are objects that can be stored permanently. They represent data stored in the
database in the form of objects. Each object can represent a row in a table, and each field of
the table can be a variable of the object.
Why Data Should Be in the Form of Objects
Data in the form of objects is easier to handle and manage. Related data can be grouped
together. For example, all data related to a particular employee (employee ID, first name,
last name, and so on) can be grouped together in an object. You can also provide methods to
retrieve or manipulate the information that is associated with an object.
To summarize, entity beans are objects just like session bean objects. However, they
represent persistent data in the database. Entity beans are generally represented by nouns
such as names, departments, bank accounts, addresses, phone numbers, and so on.

Oracle 10g: Build J2EE Applications 13-3


Entity Beans (continued)
How to Identify a Particular Entity Bean
You have learned that an entity bean can represent a row in a table. Consider 10 entity bean
objects that contain data corresponding to 10 employees. How can you find an entity bean
that represents data for employee X? Entity beans are uniquely identified by primary keys.
The primary key in our case can be the employee ID; it can be a combination of different
fields. The primary key is an object that can contain any number of attributes. This object
basically contains data that is needed to identify the entity bean.
Entity beans do not model business processes, which means they do not contribute to
workflow management. However, they manage data for business processes. Entity beans can
perform data validation and transformation. For example, an entity bean can take employee
details, validate them, and update the table. They do not contain complex business logic.
Entity beans can serve multiple clients simultaneously. If personnel from two different
departments want to check the details for employee X and update the details, they need not
deal with the same instance. Many entity bean instances can represent the same underlying
data. The synchronization of the bean with the underlying data storage is handled by the
container. Therefore, multiple clients can use the same data while operating with separate
instances.
The instance of an entity bean need not always point to the same data in the database. Bean
instances are pooled and dynamically assigned to handle different data instances. For
example, one instance holding the data of employee X can serve a client. When this bean is
passivated and placed in the pool, the container can pick up the same instance to represent
the data of employee Y. However, the data must be of type employee.

Oracle 10g: Build J2EE Applications 13-4


Representing Data in Entity Beans

int x
String s
float f
int y
double d

Entity bean object


Table

Copyright © 2005, Oracle. All rights reserved.

Representing Data in Entity Beans


Entity beans are long-lived and can survive system crashes because they represent persistent
data stored in a database. Entity beans can survive even database crashes because the entity
bean instances can be created and populated with the required data when the database is
functioning.
To store the state of any object, the object should be serialized and stored in permanent
storage. Similarly, business data can be serialized and stored. However, obtaining individual
data from the serialized business data is difficult and tedious. Instead of serializing each
object, you can dismantle each object into its parts and store them separately in an object.
The table in the slide contains five fields and the entity bean contains five variables that
correspond to each of these fields. It is like creating a class with five variables that can hold
data from the table. When these objects have to be loaded with the data from the database,
you can instantiate an object of this class, read the data from the database, and populate the
instance variables with the data read. Loading and storing the data is automatically done by
containers and you do not have to provide any code. There are two callback methods that
perform the data transfer: ejbLoad() and ejbStore(). The ejbLoad() method reads
the data from the database into the entity bean’s in-memory fields. The entity bean objects
can then be modified in memory to change the values of data. The ejbStore() method
saves the bean instance fields to the database.
Oracle 10g: Build J2EE Applications 13-5
When to Use Entity Beans

You can use an entity bean in the following situations:


• To represent a business entity
• When the state of the bean must be persistent
• When you need to represent a relationship
between entities

Copyright © 2005, Oracle. All rights reserved.

When to Use Entity Beans


You can use an entity bean in any of the following situations.
• When you need to represent a business entity with a bean: An entity bean represents
real-world business entities such as employees, products, and so on. The sole purpose
of an entity bean is to represent and manage the persistent data. Each entity bean can
represent a row of data in a database. In an online shopping business scenario, you can
use entity beans to represent products, prices, customers, or shopping carts, whereas
you use session beans to represent business logic such as calculating the total price of
the products in the shopping cart, and so on.
• When you must store bean state to a persistent storage: Entity beans store persistent
state and can survive a server crash. That is, even if the server crashes, you do not lose
the bean state, which is stored in the database or any other persistent storage. When
you restart your application, you can load the bean state from the persistent storage.
• When you need to represent relationships between various entities: Because an entity
bean may represent a relational database table, you can form relationships between
various database tables, representing each of them as an entity bean. For example, a
CUSTOMER bean may have a one-to-many relationship with an ORDER entity bean.

Oracle 10g: Build J2EE Applications 13-6


Callback Methods to Load and Store Data

• ejbLoad()loads the
data from the
persistent storage to
the bean.
• ejbStore()saves the
data from the bean
instance to the
persistent storage.

Copyright © 2005, Oracle. All rights reserved.

Callback Methods to Load and Store Data


All session beans implement javax.ejb.SessionBean, whereas entity beans
implement the javax.ejb.EntityBean interface. The EntityBean interface also
has callback methods that are used by the container for life-cycle management, as in the
SessionBean interface. They are setEntityContext(),
unSetEntityContext(), ejbActivate(), ejbPassivate(), and
ejbRemove(). In addition to these callback methods, the EntityBean interface has two
more methods—ejbLoad() and ejbStore()—that are used to transfer data between
persistent storage and the bean instance. You now see who invokes these methods and when
they are invoked.
The Enterprise JavaBeans (EJB) container provides the run-time environment for EJB. It
also provides necessary services such as transaction management, resource management,
security, and so on. The container manages the life cycle of the EJB by instantiating the
bean and by allocating and deallocating the resources as the need arises. It is responsible for
invoking the ejbLoad() and ejbStore() methods. The container automatically
calculates when the data needs to be refreshed, depending on the transactions that happen
with an entity bean.

Oracle 10g: Build J2EE Applications 13-7


Callback Methods to Load and Store Data (continued)
Therefore, you need not synchronize the objects with the underlying database to reflect the
latest data. The container can invoke these methods anytime but ensures that they are not
invoked when a business method is being executed. You do not need to decide when to
retrieve (ejbLoad()), persist (ejbStore()), create (ejbCreate()), or delete
(ejbRemove()) persistent entries.
Entity beans are objects that are placed in permanent storage. When an entity bean instance
is passivated, the state of that instance must be stored, which means the fields of the instance
must be loaded into persistent storage. To achieve this, the container invokes the
ejbStore() method immediately before passivating the bean.
When an entity bean instance is activated, its fields must have the recent data from the
database. To load data into the bean instance, the container invokes the ejbLoad()
method after activating the bean.

Oracle 10g: Build J2EE Applications 13-8


Session Beans Versus Entity Beans

Session Beans: Entity Beans:


• Are represented by • Are represented by
verbs because they nouns because they
model workflow model business data
• Are short-lived and • Are long-lived and do
have a lifetime of a not depend on a
client session client’s session
• Manage their state, but • Contain callback
do not contain methods for
callback methods to managing data
manage data because (create, retrieve,
they do not represent persist, and so on) in
data in the persistent the persistent storage
storage
Copyright © 2005, Oracle. All rights reserved.

Comparing Session Beans with Entity Beans


Session beans model a workflow. In an online shopping scenario, the session beans can be
responsible for displaying a catalog to the client, calculating the total price of the products in
the shopping cart, and so on. The session beans contain complex business logic to
successfully manage the workflow. Entity beans model business data. They can be
responsible for persistent storage of the products in the shopping cart of a client, storage of
product information and customer information, and so on. They do not contain complex
business logic.
Session beans are represented by verbs, and their actions are initiated by the client and end
when the client closes the session. They are short-lived. Entity beans are independent of a
client’s session and because they represent persistent data, they can last for years.
Both stateful sessions and entity beans manage their states and, therefore, can undergo
passivation and activation. However, entity beans have separate callback methods for saving
state during passivation and for loading state during activation. Stateful session beans can
implement the Synchronization interface, so they can be notified of any “database”
commit or abort operations. For stateful session beans, passivation means that the instance is
“flattened” and possibly the instance is swapped out of the main memory. Activation means
the bean is swapped into the main memory.

Oracle 10g: Build J2EE Applications 13-9


Comparing Session Beans with Entity Beans (continued)
For entity beans, passivation means that the bean loses its identity. Activation means that the
bean gains its identity.
Session beans are destroyed in the event of server, machine, or network crashes. However,
for OC4J clustering, the stateful session beans survive crashes. Entity beans are objects that
can be stored permanently. Therefore, crashes do not affect the life cycle of an entity bean.
In the event of a crash, the entity bean instances can be re-created and initialized with the
previous state of the bean instance.

Oracle 10g: Build J2EE Applications 13-10


Types of Entity Beans

• Container-managed persistent (CMP) beans: The


container provides the logic to search and
manipulate the persistent data.
• Bean-managed persistent (BMP) beans: The bean
provider codes the logic to search and manipulate
the persistent data in the callback methods.

Copyright © 2005, Oracle. All rights reserved.

Types of Entity Beans


Based on the mechanism of managing persistent data, the entity beans are classified as:
• Bean-managed persistent beans: In bean-managed persistent (BMP) beans, the bean
developer must code the logic for persisting data. The bean class should include a set
of JDBC calls and database queries to retrieve, insert, and delete data from the
database. Therefore, in BMP beans, the bean contains the code to manage the
persistent data. The developer should know what database is used and the mapping of
the beans’ fields to the database. BMP beans can store data in a Lightweight Directory
Access Protocol (LDAP) directory.
• Container-managed persistent beans: Unlike BMP beans, in container-managed
persistent (CMP) beans, the container manages the persistent data. You need not hard-
code persistence in the bean. The necessary information about managing the
persistence is provided to the container in the bean’s deployment descriptor. The
deployment descriptor specifies the public fields of the bean that are mapped to the
database tables and columns. These fields are called container-managed persistent
fields (CMP fields). After these CMP fields are defined, the container generates the
Java Database Connectivity (JDBC) logic that is needed to search or save the state of
the bean instance into the database.
In EJB 2.0, CMP beans use abstract persistence schema to represent and manage complex
relationships between entity beans.
Oracle 10g: Build J2EE Applications 13-11
BMP Beans Versus CMP Beans

• BMP beans:
– Contain code for managing data persistence
– Provide flexibility for bean developers to manage
state
– Are complicated to program
• CMP beans:
– Do not contain code for managing persistence
because the container manages the persistence
– Use abstract persistence schema and define the
data retrieval/manipulation logic in the deployment
descriptor
– Are easier to program and contain lesser code

Copyright © 2005, Oracle. All rights reserved.

BMP Beans Versus CMP Beans


Persistence Management
• For bean-managed persistence, the bean developer should provide the logic to store
and reload the data into and from the database. For example, this can be done through
the SQL INSERT/UPDATE statements in ejbCreate()and ejbStore(),
respectively, and SQL SELECT statements in the ejbLoad()callback method.
• For container-managed persistence, the container invokes abstract persistence schema
that defines storing and reloading data into and from the database. The container
always invokes the ejbStore()method immediately before commit, and invokes
the ejbLoad()method immediately after instantiating CMP data from the database.
The bean developer can provide additional logic such as preparing the data before
committing or manipulating the data after it is refreshed from the database. The data
retrieval/manipulation logic is specified in the deployment descriptor by using EJB
query language (EJB QL).

Oracle 10g: Build J2EE Applications 13-12


BMP Beans Versus CMP Beans (continued)
Advantages and Disadvantages of Using a CMP Bean
The advantage of container-managed persistence is that the bean can be defined
independently of the database that is used to store its state. Because the bean state is defined
independently, it provides more reusability and flexibility across applications.
The disadvantage of container-managed persistence is that sophisticated mapping tools are
required to define the mapping of a bean’s fields to the database. The mapping could be as
simple as a direct mapping of one bean field to a column in one table. In some cases, it could
be as complicated as mapping a bean’s field to a complex relational database join.
Advantages and Disadvantages of Using a BMP Bean
The advantage of a bean-managed persistence is that it gives you more flexibility in
managing the state between the bean instance and the database. When it is complicated to
map bean instance fields to the database using a CMP bean (as when defining complex
joins), bean-managed persistence is an alternative.
The disadvantage of bean-managed persistence is that it is more complicated to define the
bean persistence, because this is dependent on the type of database and data manipulation on
that database. Any changes in the database structure must be reflected in the bean instance’s
definition. The persistence mechanism must be defined in the callback methods. You must
also define the methods that are defined in the bean’s home interface.

Oracle 10g: Build J2EE Applications 13-13


Components of an Entity Bean

• Home interface: Is used by clients to create, find,


and destroy EJB objects
• Component interface: Contains the declaration of
all business methods in the bean class that can be
invoked by the client
• Bean class: Represents persistent data and
contains methods to access or manipulate that
data
• Primary key class: Is used to uniquely identify an
entity bean instance
• Deployment descriptor: Contains information that
is used by the container

Copyright © 2005, Oracle. All rights reserved.

Components of an Entity Bean


A client uses the home interface reference to create, find, or destroy entity objects. The
functionality of home interfaces for entity beans is the same as that for session beans.
A client uses the component interface reference to access business methods from a bean
instance. This interface is mainly used to expose business methods to the client.
The bean class implements the methods that are declared in home and component interfaces.
The bean class mainly contains business logic to access or manipulate business data. For
BMP beans, the bean class also implements the persistence mechanism.
The primary key class is the unique identifier for the entity bean.
The container provides the run-time environment for the beans and manages its life cycle.
The information that is needed by the container is picked up from the deployment
descriptors on deployment.

Oracle 10g: Build J2EE Applications 13-14


Creating, Removing, Finding, and
Selecting Entity Beans
• ejbCreate(): Initializes the entity bean in
memory. This method may also insert the
corresponding data into the persistent storage.
• ejbRemove(): Removes the database data but
does not remove the in-memory entity bean
instance. The instance may return to the pool and
release all resources in the ejbPassivate()
method.
• Finder methods: Used to find an entity bean.
• Selector methods: Used to select entity beans and
values of CMP fields.

Copyright © 2005, Oracle. All rights reserved.

Creating, Removing, Finding, and Selecting Entity Beans


Entity beans directly represent the persistent data in the database. Entity beans are
synchronized by the container to reflect the latest data in the database. Entity beans are
initialized by the ejbCreate() method. This method is invoked by the container.
Initializing the entity bean means initializing the database data or inserting data into the
persistent storage. In a bean-managed persistent bean, the ejbCreate() method should
contain code to create the database data. In a container-managed persistent bean, the
container manages the database data and, therefore, the ejbCreate() method does not
have any implementation.
To destroy the entity bean’s data in the database, the container calls the ejbRemove()
method. This method does not remove the in-memory entity bean instance, but removes the
database data. Therefore, the entity bean instance can be used to represent some other data.
The finder methods are used to find an existing entity bean. You can have many different
finder methods for an entity bean. This enables you to search an entity bean or multiple
beans with different attributes. The logic for finding data can be specified in the deployment
descriptor by using EJB QL.
In addition to finder methods, a CMP bean can have ejbSelect() methods, which are
implemented through EJB QL in the deployment descriptor.

Oracle 10g: Build J2EE Applications 13-15


Creating, Removing, Finding, and Selecting Entity Beans (continued)
The ejbSelect() methods are similar to ejbFind() methods. They also use EJB QL
to retrieve information. However, unlike ejbFind() methods, these methods are not
exposed to a client and they are used only in the EJB’s implementation. ejbFind()
methods return entities, whereas ejbSelect() methods can return entities and the values
of CMP fields.
Though ejbSelect() methods are not exposed to clients, they provide component
developers with access to the powerful facilities of the query language to access entities and
their container-managed fields.

Oracle 10g: Build J2EE Applications 13-16


Home Interface of an Entity Bean

• Remote home interface:


– Extends the javax.ejb.EJBHome interface
– Can be accessed by remote clients by using Java
Naming and Directory Interface (JNDI)
– Allows client to create handles for later reference
• Local home interface:
– Extends the javax.ejb.EJBLocalHome interface
– Can be accessed by local clients
• Remote/local home interface:
– Contains methods to create, find, or remove entity
objects
– Contains business methods that are not applicable
to a specific instance (home methods)

Copyright © 2005, Oracle. All rights reserved.

Home Interface of an Entity Bean


Home interface contains methods that enable the client to create, find, or remove entity
objects. Home interface also supports business methods called home methods that are not
specific to any bean instance. You can use finder methods to select the bean based on any of
its attributes. A client can save the handle of a home interface reference, which is used to
access the home interface at a later time.
A client locates the home interface of an entity bean by first finding the JNDI initial context.
Context initCtx = new InitialContext();
Then, a reference to the home interface is obtained by looking up the home interface at that
context.
ProdHome pHome = (ProdHome)
javax.rmi.PortableRemoteObject.narrow
(initCtx.lookup("java:comp/env/ejb/product"),
ProdHome.class);
If it is a local home interface, then the syntax is:
ProdLocalHome pHome = (ProdLocalHome)initCtx.lookup
("java:comp/env/ejb/product");

Oracle 10g: Build J2EE Applications 13-17


Creating a Bean Instance

• An entity bean can have one or more create()


methods, or none defined in its home interface.
• The create() method:
– Enables a client to create a row in the database
table that corresponds to the entity bean
– Contains parameters that initialize the state of the
created entity object
– Returns the remote/local interface reference of the
entity beans
– Throws CreateException and any user-defined
exceptions
– Throws RemoteException if it is part of a remote
home interface

Copyright © 2005, Oracle. All rights reserved.

Creating a Bean Instance


An entity bean can have one or more create() methods, or none defined in its home
interface. A create() method is invoked by the client application to create a bean
instance. If there is no create() method available, then the client cannot request a bean
instance. However, an entity bean instance can be created by creating a record in the
underlying database. In this case, the bean can only be accessed through the findxxx()
methods. The general naming standard of methods to create bean instances is
create(...).
The parameters of a create() method are used to initialize the state of the entity bean.
The create() method of a home interface should throw the
javax.ejb.CreateException exception. The create() method of a remote home
interface should additionally throw the java.rmi.RemoteException exception.
A create() method must return the component interface reference of the entity bean.

Oracle 10g: Build J2EE Applications 13-18


Creating a Bean Instance (continued)
An example of a create() method in a home interface is as follows:
public interface ProductHome extends javax.ejb.EJBHome
{
public Product create() throws javax.ejb.CreateException,
java.rmi.RemoteException;
public Product create(Integer prodId, String
description) throws javax.ejb.CreateException,
java.rmi.RemoteException;
...
}
A client can then create a new bean instance as follows:
Product prod = productHome.create(123, "Keyboard");

Oracle 10g: Build J2EE Applications 13-19


Finding an Entity Bean Instance

An entity bean:
• Can have one or more finder methods in home
interface
• Must have a findByPrimaryKey(primarykey)
method
• Has finder methods that:
– Find row or rows in the database table
– Contain parameters that locate the requested entity
object
– Return entity bean’s component interface reference
or collection of objects of component interface type
– Must throw FinderException
– Must throw RemoteException in a remote home
interface
– Have find as a prefix in their names

Copyright © 2005, Oracle. All rights reserved.

Finding an Entity Bean Instance


An entity bean can have one or more finder methods defined in its home interface. Because
each entity bean represents a record from the database, there must be a primary key to
uniquely identify each bean instance. To be able to uniquely identify each entity bean
instance, the home interface must contain a mandatory
findByPrimaryKey(primarykey) method. This method can accept only one
argument, of the primary key type. In addition to this method, the home interface can also
define a few other finder methods. The return type of each finder method is either the bean’s
component interface or Collection of objects of the component interface type.
The naming standard of methods to find bean instances is findxxx(...). For each finder
method in the home interface, there should be a corresponding ejbFindxxx() method in
the bean class.
Finder methods should throw the javax.ejb.FinderException exception. Finder
methods of a remote home interface should additionally throw the
java.rmi.RemoteException exception.

Oracle 10g: Build J2EE Applications 13-20


Finding an Entity Bean Instance (continued)
An example of a find method in a home interface is as follows:
public interface ProductHome extends javax.ejb.EJBHome
{
public Product findByPrimaryKey(Integer proId) throws
javax.ejb.FinderException,
java.rmi.RemoteException;
public Product findByDescription(String description)
throws javax.ejb.FinderException,
java.rmi.RemoteException;
...
}
Note that the finder methods return a component interface reference, which is nothing but
the EJB object. A client can then find a bean instance as follows:
Product prod = productHome.findByDescription("Keyboard");

Oracle 10g: Build J2EE Applications 13-21


Removing an Entity Bean

• An entity bean with remote home interface:


– Can have one or more remove() methods:
remove(Handle handle) and remove(Object
primarykey)
– Throws RemoteException and RemoveException
from remove() methods
• An entity bean with local home interface:
– Can have one remove() method: remove(Object
primarykey)
– Throws RemoveException from the remove()
method
• remove() methods remove the entity object and
the row from the underlying database.

Copyright © 2005, Oracle. All rights reserved.

Removing an Entity Bean


An entity bean contains a remove()method, which when invoked by a client, removes the
entity object and the underlying record in the database. The container may decide not to
remove the instance, because it can be used to hold another row of the table. An entity bean
with a remote home interface may contain one or more remove() methods. The
remove(Handle handle) method removes the entity object that is identified by the
handle.
The handle identifies the entity object on a network. A client can obtain the handle of the
entity object by invoking the getHandle() method on the component interface reference.
The handle extends the java.io.Serializable interface. A client serializes the
handle and the object to reobtain the reference to the entity object identified by the handle.
The remove(Object primarykey) method removes the entity object that is
identified by the primary key. The remove() methods should throw the
RemoteException and RemoveException exceptions.
An entity bean with local home interface contains only the remove(Object
primarykey) method which throws RemoveException. Because there is no handle
for local objects, there is only one remove() method for the entity bean with a local home
interface.
Accessing an entity object after it is removed throws the NosuchEntityException
exception.
Oracle 10g: Build J2EE Applications 13-22
Home Methods of Entity Beans

• Home methods are provided by a bean provider.


• Home methods contain business logic that is not
specific to any bean instance.
• An entity bean can have one or more home
methods, or none.
• The arguments and return types of remote home
methods should be of RMI-IIOP type.

Copyright © 2005, Oracle. All rights reserved.

Home Methods of Entity Beans


What Are Home Methods?
Home methods are methods in the home interface of an entity bean. The home interface can
contain business methods that are not specific to one instance of an entity object. Such
methods in the home interface are called home methods. The business methods in the home
interface should be generally applicable to any instance of the entity bean. The home
methods of a home interface should throw RemoteException, and their return type
should be of a legal RMI-IIOP type.
When to Use Home Methods?
If you want to code a method that applies equal discounts to all the products in the company,
then you can implement the logic as a home method, because it is not specific to any
particular product. Similarly, if you want to learn the total amount that is being paid as
salary to the employees in an organization, then you can implement the logic as a home
method, because it is not specific to any employee.

Oracle 10g: Build J2EE Applications 13-23


Component Interfaces of an Entity Bean

• Component interfaces define:


– Business methods that are accessible by clients
– Accessor methods for the bean attributes
• Remote interfaces:
– Are referenced by remote clients
– Extend the javax.ejb.EJBObject interface
• Local interfaces:
– Are referenced by local clients
– Extend the javax.ejb.EJBLocalObject interface

Copyright © 2005, Oracle. All rights reserved.

Component Interfaces of an Entity Bean


A remote interface is the component interface of an entity bean. Clients access the entity
object through the component interface reference. Component interfaces can be remote or
local interfaces.
Component interfaces define business methods that are accessible by the client. A
component interface can also define accessor methods (get() or set()) to get or set bean
attributes. The business and accessor methods are implemented in the bean class
implementation. The component interfaces inherit methods that enable the client to obtain
home interface reference and the primary key of the entity object.
A remote interface that extends the javax.ejb.EJBObject interface is created
similarly to a session bean. In addition to the methods specified above, a remote interface
contains a method to obtain the handle of the entity object. Methods that are declared in the
remote interface should throw the RemoteException exception.
A local interface is the component interface that is accessed by local clients. A local
interface extends the javax.ejb.EJBLocalObject interface. Methods in the local
interface must not throw the RemoteException exception.

Oracle 10g: Build J2EE Applications 13-24


Primary Key Class of an Entity Bean

• Primary key:
– Uniquely identifies each bean instance
– Is used to find or remove an entity bean
– Can be of any legal value type in RMI-IIOP
• The primary key class:
– Should implement java.io.Serializable
– Can have a single primary key (a single field) to
identify the entity bean
– Can have composite keys (multiple fields) to
identify the entity bean

Copyright © 2005, Oracle. All rights reserved.

Primary Key Class of an Entity Bean


A primary key uniquely identifies an entity bean according to the bean type, home interface,
and container context from which it is used. The type of the primary key can be either a
well-known type such as java.lang.String or primitive wrappers such as
java.lang.Integer. In this case, you can define the type in the deployment descriptor.
If the type is a complex type, then you create a serializable class. A primary key is
applicable only to entity beans because entity beans represent records in the underlying
database. Session beans do not represent any particular data in the database and, therefore,
are not uniquely represented by primary keys.
It is useful to create a primary key class when the primary key type is a complex data type.
If the primary key class is a well-known data type, such as java.lang.String or
Integer, then it can be directly supplied in the <prim-key-field> element of an
XML deployment descriptor. The EJB specification requires that the fields in the primary
key class be declared public. The primary key class is specified in the deployment descriptor
of an entity bean.
You learn about the primary key classes for BMP and CMP beans later in this course.

Oracle 10g: Build J2EE Applications 13-25


Bean Class of an Entity Bean

• Initializes the bean instance through the


ejbCreate() and ejbPostCreate() methods
• Implements:
– Finder methods through ejbFindxxx() methods
– Home methods through ejbHomexxx() methods
– Callback methods from the EntityBean interface
– Business and private methods

Copyright © 2005, Oracle. All rights reserved.

Bean Class of an Entity Bean


A bean class implementation is mainly created with the implementation of business logic
methods and callback methods. Container initializes the bean instance by using the
ejbCreate() and ejbPostCreate() methods that are defined in the bean class. For
each create(), find(), and findByPrimaryKey() methods declared in the home
interface, implement the corresponding ejbCreate(), ejbFindxxx(), and
ejbFindByPrimaryKey() methods in the bean class.
A bean class implements business logic methods that are declared in the component
interface. Any home() methods declared in the home interface are implemented in the bean
class through the ejbHomexxx() methods. You can also add any private methods that are
necessary in the bean class. In addition to the methods mentioned above, the bean class
implements the life-cycle methods that are defined in the javax.ejb.EntityBean
interface.
Note: The method names corresponding to the create(), find(), and home()
methods of the home interface have ejb as prefix and the word create/find/home
following the prefix, with an uppercase first letter.

Oracle 10g: Build J2EE Applications 13-26


Bean Class of an Entity Bean

• Contains ejbCreate() and ejbPostCreate()


methods for each create() method.
• The ejbCreate() method:
– Is invoked when a client invokes the create()
method to initialize persistent fields
– Has primary key as return type
• The ejbPostCreate() method:
– Is invoked after the entity bean is created and
before any other request from a client is processed
– Has void as return type
– Initializes any relationship fields for an entity bean

Copyright © 2005, Oracle. All rights reserved.

Bean Class of an Entity Bean (continued)


For each create() method in the home interface, there should be matching
ejbCreate() and ejbPostCreate() methods in the bean class. When a client
invokes the create() method on the home interface, the container invokes the
ejbCreate() method. A row is inserted into the database with the values that are
supplied in this method.
The ejbPostCreate() method should match in signature to its corresponding
ejbCreate() method. This method is invoked after the bean is created but before any
client requests are serviced. This method is useful for initializing any relationship fields for
the bean. Relationship fields can occur only after the ejbCreate() method is invoked
and a bean is inserted into the database. The return type of the ejbPostCreate()
method is void.

Oracle 10g: Build J2EE Applications 13-27


javax.ejb.EntityBean Interface

All entity bean classes should implement the


javax.ejb.EntityBean interface.
public interface javax.ejb.EntityBean
implements javax.ejb.EnterpriseBean
{
public void ejbActivate();
public void ejbLoad();
public void ejbPassivate();
public void ejbRemove();
public void ejbStore();
public void setEntityContext(EntityContext
ctx);
public void unSetEntityContext();
}

Copyright © 2005, Oracle. All rights reserved.

javax.ejb.EntityBean Interface
The slide shows the definition of the EntityBean interface. This interface contains
callback methods that are used during the life cycle of an entity bean.
After the entity bean is created through the ejbCreate() method, the data is inserted into
the database and is ready to be accessed by the client. When a client requests information,
the data must be retrieved from the database and stored into the database when there is data
manipulation such as update or delete of the entity bean. The container manages these
activities by using the callback methods that are described in the slide.
You have already learned that the ejbLoad()and ejbStore() methods are used to
transfer data between persistent storage and the bean instance. These are the callback
methods that are used for saving state during passivation and for loading state during
activation. The ejbActivate() and ejbPassivate() methods are called by the
container before and after an entity bean is swapped out and into the temporary storage.
The container invokes the ejbRemove() method when the client invokes the remove()
method. For a BMP bean, you must remove the data from the database that is associated
with the bean within this method. For a CMP bean, this method is automatically
implemented by the container.

Oracle 10g: Build J2EE Applications 13-28


javax.ejb.EntityBean Interface (continued)
The RemoveException exception is thrown as an attempt to remove an EJB object when
the enterprise bean or the container does not allow the EJB object to be removed.
Any information about the bean that must be accessed during the lifetime of the bean can be
initialized in the setEntityContext() method. This method is invoked only once by
the container when the bean is initialized.
Any resources that need to be released when the bean instance is destroyed, can be released
in the unsetEntityContext() method.

Oracle 10g: Build J2EE Applications 13-29


Life Cycle of an Entity Bean
Does not
exist
newInstance() unsetEntityContext()
setEntityContext()

Pooled

ejbCreate()
ejbPostCreate() ejbActivate() ejbPassivate() ejbRemove()

ejbLoad() Ready ejbStore()

Clients invoke
business methods

Copyright © 2005, Oracle. All rights reserved.

Life Cycle of an Entity Bean


• The container calls the newInstance() method to create a new instance of the
bean. The container invokes the setEntityContext() callback method to
associate the entity bean with a context. The container creates instances when it wants
to increase the number of instances in the pool, and not necessarily when the client
calls the create() method. The bean instance is placed in the pool and is not
associated with any particular entity object.
• The client invokes the create() method to create new data. The container then uses
the instance in the pool to represent the new data. It invokes the ejbCreate()and
ejbPostCreate() methods and initializes the entity bean. If the pool contains a
passivated bean, then the container can use the same bean by invoking the
ejbActivate() method before populating the bean with the data. This is indicated
by dotted lines in the graphics because this method is executed only if there are already
some beans that are passivated.
• Now, the bean instance is in the ready state. The container can invoke the
ejbLoad() and ejbStore() methods to synchronize the entity bean data with the
underlying data source. Clients can invoke the business methods on this bean.

Oracle 10g: Build J2EE Applications 13-30


Life Cycle of an Entity Bean (continued)
• If the container decides to passivate the bean instance, it invokes the ejbStore()
method to load the data from the in-memory instance to the persistent storage. The
container invokes the ejbPassivate() method when the container wants to
dissociate the instance from the entity object without removing the entity object. When
the instance is in the pool, it is no longer associated with an entity object identity. The
container releases all the resources that are used by the bean, and the bean instance is
then placed in the pool.
• If the client invokes the remove() method on the home object, then the container
invokes the ejbRemove() method. The database data that is represented by the bean
is deleted and the bean instance can be retained for reuse.
• If there are too many instances in the pool, or when there is no request for the
instances, then the container dissociates the context associated with the bean by
invoking the unsetEntityContext() callback method.

Oracle 10g: Build J2EE Applications 13-31


Deployment Descriptor
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE …>
<ejb-jar>
<enterprise-beans>
<entity>
<ejb-name>...</ejb-name>
<home>...</home>
<remote>...</remote>
<ejb-class>...</ejb-class>
<persistence-type>...</persistence-type>
<prim-key-class>...</prim-key-class>
<reentrant>False</reentrant>
<abstract-schema-name>...</abstract-schema-name>
<cmp-field> <field-name>...</field-name> </cmp-field>
<primkey-field>...</primkey-field>
</entity>
</enterprise-beans>
...

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor
The two main elements in the deployment descriptor of an entity bean are <enterprise-
beans> and <assembly-descriptor>.
The <enterprise-beans> element contains the details of the bean class, primary key
class, and interfaces. This element contains a subelement called <entity>, which
indicates that the enterprise bean being described is an entity bean.
The <assembly-descriptor> element contains information about the security roles,
methods that are accessible for different roles on different beans, and so on. It is the bean
assembler’s responsibility to define these roles and responsibilities.
The slide shows the elements in a deployment descriptor. <ejb-jar> is the root element
of the descriptor. Note the various tags in <entity>. The <home>, <remote>, and
<ejb-class> tags provide information about the elements of the entity bean. The
<persistence-type> tag is used to specify whether the bean is a BMP bean or a CMP
bean. <prim-key-class> contains the name of the primary class, which is used to
uniquely identify the entity bean.

Oracle 10g: Build J2EE Applications 13-32


Deployment Descriptor (continued)
Reentrance
You learned that when a client application invokes a method on an enterprise bean, the
method is accessed through the remote interface of the bean. The client is not allowed to
access the bean directly. This process is the same even if the client application is another
enterprise bean. Also, you learned that multiple threads are not allowed into a bean. That is,
even though entity bean instances are sharable (accessed concurrently), a client can access a
bean only after another client who is using a method of that bean has finished. The bean
instances are always single-threaded.
Consider a client invoking a method on bean A, which further invokes a method on bean B.
Here, bean A is a client of bean B. If bean B now tries to invoke a method on bean A, this
situation is called a loopback.
This is considered a reentrance and is not allowed in EJB. Session beans can never be
reentrant. If a loopback is attempted, the RemoteException exception is thrown. Entity
beans can be set to reentrant during deployment time. Reentrance is okay for entity beans if
it is specified in the <reentrant> tag. Different transactions have their own entity
beans on which to operate. If multiple threads have the same transaction context (very
unlikely) and access the same bean, then the calls are serialized.
Note: A bean instance invoking its own methods is not considered as reentrance.
The <reentrant> tag contains a Boolean value, which is used to indicate whether the
entity bean is reentrant or not. The default value is False.
For a CMP bean, the <abstract-schema-name> tag specifies the schema name to
which the entity bean should be mapped. The <cmp-field> tags specify the field names
whose persistence should be managed by the container.
<primkey-field> indicates the CMP field that is the primary key field.

Oracle 10g: Build J2EE Applications 13-33


Deployment Descriptor

...
<assembly-descriptor>
<security-role>
<description>Public</description>
<role-name>PUBLIC</role-name>
</security-role>
<method-permission>
<description>Public methods</description>
<role-name>PUBLIC</role-name>
<method>
<ejb-name>...</ejb-name>
<method-name>*</method-name>
</method>
</method-permission>
</assembly-descriptor>
</ejb-jar>

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor (continued)


The optional <assembly-descriptor> tag is used to define security attributes for the
application.
The <method-permission> tag in the above example indicates that all the methods of
the EJB are accessible to a role named PUBLIC. The * in the method-name stands for all
the methods of the bean.

Oracle 10g: Build J2EE Applications 13-34


Summary

In this lesson, you should have learned how to:


• Identify features of an entity bean
• Use entity beans
• Distinguish between a session bean and an entity
bean
• Develop components of an entity bean
• Differentiate BMP beans from CMP beans
• Describe the life cycle of an entity bean

Copyright © 2005, Oracle. All rights reserved.

Summary
In this lesson, you should have learned about entity beans and different types of entity beans.
You have seen the differences between session beans and entity beans, and should now be
able to decide when to use entity beans. You should also have learned about the various
components that build an entity bean and the life cycle of the entity bean.

Oracle 10g: Build J2EE Applications 13-35


Practice 13-1: Overview

This practice reviews entity bean concepts using


paper-based questions.

Copyright © 2005, Oracle. All rights reserved.

Oracle 10g: Build J2EE Applications 13-36


Practice 13-1
1. Which two of the following statements regarding entity beans are true?
a. Live for the lifetime of a client
b. Are long-lived and, therefore, are independent of a client’s session
c. Model a process or workflow and, therefore, are represented by verbs
d. Contain complex business logic that is needed to process the workflow
e. Represent persistent data. They model data but not business process and,
therefore, are represented by nouns.
2. Which three of the following statements regarding finder methods are true?
a. An entity bean can have one or more finder methods.
b. Finder methods find one row at a time in the database table.
c. Finder methods find a row or rows in the database table.
d. These methods must throw FinderException but need not throw
RemoteException.
e. These methods must throw both FinderException and
RemoteException.
f. They return home interface reference or collection of objects of home interface
type.
3. For methods given in column A, choose appropriate statements from column B.
A B

ejbFind() Removes or deletes the database data, but the in-memory


entity bean instance is retained by the container to handle
different data/row of the table.
ejbPassivate() Saves the data from the bean instance to the persistent
storage
ejbRemove() Does not create new database data but loads some existing
entity bean data. The developer must implement this
method for BMP beans, and the container implements this
for CMP beans.
ejbLoad() Loads the data from the persistent storage to the bean

ejbStore() Releases the resources held by the entity bean and saves
the bean state to the underlying storage. The bean instance
is put into a generic instance pool.

Oracle 10g: Build J2EE Applications 13-37


Practice 13-1 (continued)
4. The ejbRemove()method of entity beans does not take any parameters. This method
is not called if the client times out. (True/False)
5. Which two of the following statements regarding primary key classes are true?
a. Used to uniquely identify the entity bean instances
b. Contain only a single primary key to identify bean instances
c. Should implement java.io.Serializable
d. Can be used to create an instance, but cannot be used to remove the instance

Oracle 10g: Build J2EE Applications 13-38


Achieving State Management in the
Business Tier

Copyright © 2005, Oracle. All rights reserved.


Objectives

After completing this lesson, you should be able to do


the following:
• Describe the features of bean-managed persistent
(BMP) entity beans
• Identify the features of a container-managed
persistent (CMP) entity bean
• Describe the benefits of a CMP bean as compared
with a BMP bean
• Develop and deploy a CMP bean
• Develop a client for a CMP bean

Copyright © 2005, Oracle. All rights reserved.

Objectives
You have learned about different types of entity beans in the lesson titled “Managing
Persistent Data in the Business Tier.” This lesson provides an overview of BMP beans and
discusses CMP beans in detail. You learn to develop a CMP bean, deploy the bean, and
invoke the methods on the bean with a client application.

Oracle 10g: Build J2EE Applications 14-2


Features of BMP Entity Beans

• The Bean provider provides the code for


persistence management.
• BMP beans provide more flexibility in managing
persistent data.
• The bean class of a BMP entity bean contains
code for data access and manipulation.
• Callback methods contain code to map the entity
bean instance to the data, load the data, and store
the data in persistent storage.
• BMP beans are less portable.

Copyright © 2005, Oracle. All rights reserved.

Features of BMP Entity Beans


In bean-managed persistent beans, the bean provider provides the logic to access data and
manipulate data in the persistent storage. This involves writing a lot of Java Database
Connectivity (JDBC) code in the callback methods and business logic methods. For
example, the ejbCreate() method contains a SQL INSERT statement to insert data into
the database. When this method is executed, appropriate data is inserted into the database
and this data is associated with an entity bean instance.
When the data to be manipulated is more complex, involving complex joins between various
tables from the underlying database, the BMP beans provide more flexibility to the bean
provider for managing the interaction between the bean instance and the database.
Bean-managed persistence is more complicated than container-managed persistence because
the bean developer must explicitly write the persistence logic in the bean class, and this is
dependent on the type of database and data manipulation on that database. Any changes in
the database structure must be reflected in the bean instance’s definition. The persistence
mechanism must be defined in the callback methods. Therefore, the BMP beans are less
portable. For container-managed persistence, the details for the persistence, fields, and
relationships to be managed are provided in the deployment descriptor.

Oracle 10g: Build J2EE Applications 14-3


Developing a BMP Entity Bean

To develop a BMP entity bean, you must create the


following:
• A remote interface for the bean
• A home interface
• The primary key class
• The bean class implementation
• Support classes, such as exceptions
• Necessary database tables
• The J2EE deployment descriptor
• A client application to access the EJB

Copyright © 2005, Oracle. All rights reserved.

Developing a BMP Entity Bean


In the lesson titled “Managing Persistent Data in the Business Tier,” the components of an
entity bean and the differences between BMP entity beans and CMP entity beans were
discussed. To develop a BMP entity bean, you must create the following components:
• A remote interface that contains declarations of business methods that are accessible to
a client
• A home interface that contains the create(), find(), and home() methods to be
implemented in the bean class
• A primary key class to uniquely identify each bean instance
• A bean class implementation with all the persistent data management
• Any support classes, such as exceptions
• The database tables involved in the business logic of the entity bean
• The deployment descriptor to identify the EJB, security roles, and the relationships
between various beans involved in the business process
• A client application to access the EJB
You can also create an OC4J-specific deployment descriptor for mapping the resources that
are used in the entity bean. This descriptor is optional, but provides portability.

Oracle 10g: Build J2EE Applications 14-4


Features of CMP Entity Beans

• Developers need not code the persistence logic in


the bean because the containers provide it.
• CMP beans provide:
– Portability across all EJB-compliant containers
– A layer of data independence
– Container-managed fields, which represent the
persistent fields in the database
• Bean developers concentrate on the business
logic and provide empty implementations of the
callback methods.

Copyright © 2005, Oracle. All rights reserved.

Features of CMP Entity Beans


The main goal of CMP beans is to provide portable EJBs across all compliant Enterprise
JavaBeans (EJB) containers. You have already learned about BMP beans. In BMP beans, the
bean provider must include JDBC code in the bean class to implement the persistence logic.
The persistence logic may vary slightly depending on the persistence provider. Therefore, to
be able to access the methods of the bean with a different persistence provider, the bean
class may have to be redefined and recompiled.
The CMP architecture mainly provides a layer of data independence between the entity bean
instance and the persistence representation. In CMP beans, the bean class is an abstract class
in which the bean provider provides only the business logic. The implementation of the logic
(to manipulate the persistent data) is left to the container. CMP beans usually contain empty
implementations of the callback methods. However, you can provide implementation for
methods such as ejbActivate()if you want to acquire any bean-specific resources when
the bean moves to the ready state. If you want a bean to serve a particular client whose state
is available, then you can populate the bean with the client state information and then
service the client. Similarly, you provide implementation for methods such as
ejbPassivate()or unsetEntityContext() to release any such resources.

Oracle 10g: Build J2EE Applications 14-5


Features of CMP Entity Beans (continued)
Container-Managed Fields
The bean provider specifies the fields and relationships to be persisted through the
deployment descriptor. The container collects the information and generates classes and
interfaces that are necessary to persist the data and relationships during deployment and run
time. This allows an entity bean to be redeployed on different containers and persistence
providers without redefining or recompiling the class implementation. This also enables the
bean developer to concentrate more on the business logic, leaving the implementation
details to the container.
The bean class contains fields called container-managed fields. These fields represent the
fields in the table of a database that are represented by the entity bean. These fields are not
explicitly defined in the bean class. However, the bean class contains abstract set() and
get() methods for these fields. These methods should be public, because the container has
to implement them and should have access to these methods.

Oracle 10g: Build J2EE Applications 14-6


Implementing Methods in CMP Beans and
BMP Beans

Method BMP CMP

ejbFind()

ejbcreate()

ejbLoad()

ejbStore()

setXXX() and
getXXX() abstract

Copyright © 2005, Oracle. All rights reserved.

Implementing Methods in CMP Beans and BMP Beans


Finder methods: CMP beans contain finder methods but the bean provider need not code
the finder methods, such as findAll()and findByPrimaryKey(), in the bean class.
The EJB container is responsible for finding data. In BMP beans, the bean provider can
implement any number of ejbFind()methods and is responsible for finding data. Finder
methods use SELECT statements to find appropriate data.
ejbcreate(): In BMP beans, the create() methods are implemented to create new
database data and initialize the bean instance. These methods use INSERT statements to
create the data. In CMP beans, the create() methods do not create database data with
INSERT statements. The container takes care of this. The ejbcreate()method in a CMP
bean calls the set method to initialize the bean instance with the data.
ejbLoad(): The ejbLoad() method of a BMP bean contains code to load the bean
instance with the persistent data in the table. The ejbLoad() method uses a SELECT
statement to load the data. In CMP beans, the container is responsible for loading the data;
therefore, this method has an empty implementation.

Oracle 10g: Build J2EE Applications 14-7


Implementing Methods in CMP Beans and BMP Beans (continued)
ejbStore(): In a BMP bean, this method uses an UPDATE statement to store the data in
the bean instance to the persistent storage. The container automatically extracts the
container-managed fields and updates the data in the persistent storage. Therefore, this
method has an empty implementation in CMP bean.
set() and get() methods: The BMP bean contains the implementation for the set()
and get() methods. In a CMP bean, these methods are abstract and are implemented by
the container to set and get the container-managed fields.

Oracle 10g: Build J2EE Applications 14-8


Developing a CMP Entity Bean

To develop a CMP entity bean, you must:


• Create a component interface
• Create a home interface
• Define a primary key for the bean
• Create the bean class implementation
• Create optional support classes such as
exceptions
• Create the bean deployment descriptor
• Ensure that the correct database table exists for
the bean

Copyright © 2005, Oracle. All rights reserved.

Developing a CMP Entity Bean


The following components must be developed for a CMP bean:
• A component interface that contains declarations of business methods that are
accessible to a client. All CMP beans that participate in container-managed
relationships must be in the same local scope. That is, the beans must reside in the
same EJB container and use local interfaces rather than remote interfaces for obtaining
related information. However, if the beans are not participating in such relationships,
you can define a remote interface and access it from a remote client.
• A home interface that contains the create(), find(), and home() methods
• A primary key class to uniquely identify each bean instance. The primary key field
must be declared in <prim-key-field> of the deployment descriptor.
• An abstract bean class that is implemented by the container. The bean class provides
abstract methods for the CMP fields.
• Any support classes such as user-defined exceptions and any dependent value classes.
Dependent value classes are serialized classes that an entity bean may use internally in
its private methods, or expose to the client through public interface methods.
• The deployment descriptor to identify the EJB, the abstract persistence schema name,
the CMP and container-managed relationship (CMR) fields, the type of relationship
with other entity beans involved in the business process, the CMP bean version, the
security roles, and so on. JDeveloper automatically creates the deployment descriptor
for the bean.
Oracle 10g: Build J2EE Applications 14-9
CMP Bean: Example

• The example in this lesson creates a CMP entity


bean to represent the DEPARTMENTS table with the
following components:
– Remote interface: Departments
– Home interface: DepartmentsHome
– Bean class: DepartmentsBean
– Deployment descriptor: ejb-jar.xml
• Client for Departments bean:
DepartmentsClient

Copyright © 2005, Oracle. All rights reserved.

CMP Bean: Example


In this lesson, you create a Departments entity bean that represents the DEPARTMENTS
database table. The slide shows the various components that must be developed for the
Departments CMP entity bean.
The DEPARTMENTS table is a relational table that contains the department_id (primary
key), department_name, manager_id, and location_id (a foreign key that
references the LOCATIONS table) columns.
This example shows how to create the data in the persistent storage by using CMP beans.
You will also see how to use the get() and set() methods of the CMP fields to access
and modify the fields.
The description of this table and other tables used in this course are detailed in Appendix B.

Oracle 10g: Build J2EE Applications 14-10


Bean Class of a CMP EJB: CMP Fields

• The bean class of a CMP EJB is an abstract class


because it does not implement persistence logic.
• CMP fields in the deployment descriptor:
– Correspond to columns of the persistent data table
– Have names starting with a lowercase letter
– Must be Java primitive types or Java serializable
objects
• CMP field accessor methods in the bean instance:
– Must be abstract public methods; the container
implements these methods
– Must have names in the following form:
getFieldname()or setFieldname()

Copyright © 2005, Oracle. All rights reserved.

Bean Class for a CMP EJB


The bean instance of a CMP EJB is much different from that of a BMP EJB. The main
difference between the two beans is in the implementation of the persistence logic. In a
CMP bean, the container implements the persistence logic. The bean class is an abstract
class that does not define the instance variables to hold container-managed persistent and
container-managed relationship fields. The container generates the class that is necessary to
implement the abstract classes defined in the abstract bean class.
• Container-managed persistence (CMP) fields:
- Represent the columns in the underlying persistent database table related to the
CMP bean
- Are defined in the deployment descriptor
- Have names starting with a lowercase letter, and can be Java primitive or Java
serializable object types
• Accessor methods for CMP fields:
- Are defined as get() or set() methods in the bean class implementation.
- Must be public and abstract. They must follow the naming convention
getFieldname or setFieldname where fieldname is the CMP field name
as defined in the deployment descriptor (starts with an uppercase initial letter).

Oracle 10g: Build J2EE Applications 14-11


Remote Interface: Departments

...
import javax.ejb.EJBObject;
import java.rmi.RemoteException;
public interface Departments extends EJBObject
{
// set and get methods for CMP fields
Long getDepartment_id() throws RemoteException;
void setDepartment_id(Long newDepartment_id)
throws RemoteException;
String getDepartment_name()throws
RemoteException;
void setDepartment_name(String
newDepartment_name) throws RemoteException;
...
}

Copyright © 2005, Oracle. All rights reserved.

Remote Interface: Departments


The code in the slide shows the remote interface of the Departments bean. The business
methods defined for the CMP fields are exposed. These methods and one pair of get() and
set() accessor methods for each of the CMP fields of the Departments bean are
defined as abstract methods of the bean class DepartmentBean.
No business method is declared to keep the example simple.

Oracle 10g: Build J2EE Applications 14-12


Home Interface: DepartmentsHome

import javax.ejb.EJBHome;
import java.rmi.RemoteException;
import javax.ejb.CreateException;
import javax.ejb.FinderException;
import java.util.Collection;
public interface DepartmentsHome extends EJBHome
{
Departments create() throws RemoteException,
CreateException;
Departments findByPrimaryKey(Long primaryKey) throws
RemoteException, FinderException;
Collection findAll() throws RemoteException,
FinderException;
Departments create(Long department_id, String
department_name) throws RemoteException,
CreateException;
}

Copyright © 2005, Oracle. All rights reserved.

Home Interface: DepartmentsHome


The code in the slide shows the home interface DepartmentsHome for the
Departments bean.
The example contains two create() methods: a no-argument method and a method that
accepts all the CMP fields as parameters. The abstract bean class defines the equivalent
ejbCreate()and ejbPostCreate()methods.
The findByPrimaryKey() finder method accepts the primary key of type Long and
returns a Departments object.
The findAll() method lists all the departments, and the findByPrimaryKey()
method lists the department with the specified department_id.

Oracle 10g: Build J2EE Applications 14-13


Bean Class: DepartmentsBean

...
import javax.ejb.EntityBean;
import javax.ejb.EntityContext;
public abstract class DepartmentsBean implements
EntityBean
{ private EntityContext context;
public void setEntityContext(EntityContext
ctx)
{
context = ctx;
}
public void unsetEntityContext()
{
context = null;
}
public abstract Long getDepartment_id();
public abstract void setDepartment_id(Long
newDepartment_id);
...

Copyright © 2005, Oracle. All rights reserved.

Bean Class: DepartmentsBean


The code in the slide shows the abstract bean class DepartmentsBean. This bean
defines:
• An instance variable context to hold the entity context of the bean
• setEntityContext and unsetEntityContext() methods to associate and
dissociate the entity bean and the context information
Note that there are no declarations for the CMP fields in the bean implementation.
The information about the CMP fields and their mapping to the fields in the database is
provided in the deployment descriptor.
The get() or set() pair of accessor methods for each CMP field is declared. The
accessor methods for only one field, department_id, are shown in this example. These
methods have their names prefixed with get or set, followed by the name of the CMP
field as defined in the deployment descriptor, with an uppercase initial letter.

Oracle 10g: Build J2EE Applications 14-14


Bean Class: DepartmentsBean

...
public Long ejbCreate()
{ return null; }
public void ejbPostCreate()
{ }
public Long ejbCreate(Long department_id,
String department_name)
{
setDepartment_id(department_id);
setDepartment_name(department_name);
return department_id;
}
public void ejbPostCreate(Long department_id,
String department_name)
{ }
...

Copyright © 2005, Oracle. All rights reserved.

Bean Class: DepartmentsBean (continued)


The slide shows the code for the ejbCreate()and ejbPostCreate()methods that are
equivalent to the create()methods defined in the home interface. The slide shows only
two forms of the ejbCreate()method. You can have different overloaded forms of the
ejbCreate() method. You set the values for the CMP fields by using the set()
methods that are implemented for the CMP fields as shown earlier in this lesson.

Oracle 10g: Build J2EE Applications 14-15


Bean Class: DepartmentsBean

...
public void ejbActivate()
{ }
public void ejbLoad()
{ }
public void ejbPassivate()
{ }
public void ejbRemove()
{ }
public void ejbStore()
{ }
}

Copyright © 2005, Oracle. All rights reserved.

Bean Class: DepartmentsBean (continued)


The slide shows the callback methods that are implemented by the container.

Oracle 10g: Build J2EE Applications 14-16


Deployment Descriptor ejb-jar.xml

The main tags of the deployment descriptor for a CMP


bean are:
• <prim-key-class>: Type of primary key
• <persistence-type>: Container
• <cmp-version>: CMP 1.1 or 2.0 (default)
• <abstract-schema-name>: For each entity bean
• <cmp-field><field-name>: List of CMP field
names

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor ejb-jar.xml


The deployment descriptor plays an important role in a CMP EJB. In a BMP bean, the bean
provider furnishes the statements to obtain and close the connection to data sources, perform
the JDBC calls, define and manipulate the relationship among the beans, and so on. Because
the container manages all the persistence in the CMP entity beans, the information necessary
for the container to persist this data and the SQL statements must be defined in the
deployment descriptor.
The slide describes some of the important tags for a CMP bean.
The mandatory <prim-key-class> tag indicates the type of the primary key for the
table that the CMP entity bean represents. The primary key can be of system-defined data
type such as String or Integer, or it can be a user-defined class type. If the primary key
consists of a single field, then there must be a <primkey-field> tag that indicates
which CMP field is used to represent the primary key.

Oracle 10g: Build J2EE Applications 14-17


Deployment Descriptor ejb-jar.xml (continued)
The mandatory <persistence-type> tag describes whether the bean or the container
provides persistence to the bean. For a CMP bean, the value is Container.
The <cmp-version> tag indicates that the CMP bean implements CMP version 2.0
features. The EJB container vendors must support both the CMP 2.0 and 1.1 versions. If this
optional tag is not defined, then the default value is 2.0.
The optional <abstract-schema-name> tag is used to uniquely identify the abstract
persistence schema name for each of the entity beans. An abstract persistence schema is a
combination of the CMP and CMR fields that are defined in the deployment descriptor.
The list of fields defined with the combination of <cmp-field><field-name> tags
indicates the container-managed persistence fields in the bean class. In addition to the
mandatory <field-name> tag, there can also be an optional <description> tag to
describe the CMP field. There must be one set of accessor methods in the abstract bean class
corresponding to each of the CMP fields declared in the deployment descriptor.

Oracle 10g: Build J2EE Applications 14-18


Deployment Descriptor ejb-jar.xml
...
<ejb-jar>
<enterprise-beans>
<entity> <description>Entity Bean
( CMP )</description>
<display-name>Departments</display-name>
<ejb-name>Departments</ejb-name>
<home>mypackage1.DepartmentsHome</home>
<remote>mypackage1.Departments</remote>
<ejb-class>
mypackage1.impl.DepartmentsBean</ejb-class>
<persistence-type>Container</persistence-
type>
<prim-key-class>java.lang.Long</prim-key-
class>
<reentrant>False</reentrant>
<cmp-version>2.x</cmp-version>
...

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor ejb-jar.xml (continued)


This slide shows the deployment descriptor for the Departments bean example.
The logical name for the EJB is given as Departments in the <ejb-name> element.
The home interface and the remote interface names are given along with the names of their
packages in the <home> and <remote> tags. The bean class name is specified in the
<ejb-class> tag.
The value Container for the <persistence-type> element indicates that the entity
bean is a CMP bean.
The <prim-key-class> element shows that the example primary key class is of
java.lang.Long type. This element is mandatory for an entity bean. If the primary key
comprises a single field, then the CMP field that is used as primary key must be specified in
the <primkey-field> element. This is shown in the following slide.
The <reentrant> flag is set to False because the methods of the Departments bean
do not call themselves. That is, loopbacks are not allowed in the methods of this CMP bean.
The <cmp-version> tag indicates that CMP version 2.0 is used.

Oracle 10g: Build J2EE Applications 14-19


Deployment Descriptor ejb-jar.xml

<cmp-field>
<field-name>department_id</field-name>
</cmp-field>
<cmp-field>
<field-name>department_name</field-name>
</cmp-field>
<cmp-field>
<field-name>manager_id</field-name>
</cmp-field>
<cmp-field>
<field-name>location_id</field-name>
</cmp-field>
<primkey-field>department_id</primkey-field>
</entity>
</enterprise-beans>
</ejb-jar>

Copyright © 2005, Oracle. All rights reserved.

Deployment Descriptor ejb-jar.xml (continued)


The container-managed persistence (CMP) fields are declared within the <cmp-field>
element. There should be one CMP field declaration for each pair of get() or set()
CMP field accessor methods that is defined in the bean class. This element contains an
optional <description> element to describe the field and a mandatory <field-
name> element to declare the field name. The name of this field should match the CMP
field accessor method that is defined in the bean class. The name of the get() accessor
method of a CMP field with a name field1 would be getField1().

Oracle 10g: Build J2EE Applications 14-20


Mapping CMP Fields to
Database Table Columns

• Accept the defaults that are supplied by the


container.
• Map explicitly to the columns in a database table
by using the orion-ejb-jar.xml file:
– Deploy the application by using only ejb-jar.xml
– Modify the generated orion-ejb-jar.xml file with
the custom database, table, and column details
– Use for more complex data representation of a bean
• JDeveloper provides easy mapping of the
persistent fields to database tables.

Copyright © 2005, Oracle. All rights reserved.

Mapping CMP Fields to Database Table Columns


After defining the CMP fields in the deployment descriptor, these fields must be mapped to
database tables and columns. For these fields to be mapped to a database, you can take one
of the following alternatives:
• Accept the defaults for these fields and avoid more deployment descriptor
configuration. If you define the persistent fields in the ejb-jar.xml file, then OC4J
provides the following mappings of these fields to the database.
• The persistent data mapping is configured within the orion-ejb-jar.xml file. If
the data represented by your bean is more complex or you do not want to accept the
defaults that OC4J provides for you, then you can map the persistent data to an
existing database table and its columns within the orion-ejb-jar.xml file.
You can use JDeveloper to provide easy mapping of the persistent fields to the database
tables and columns.

Oracle 10g: Build J2EE Applications 14-21


Default Mapping of CMP Fields
to Database Table Columns

• Database: Default database as specified in the


data-sources.xml file, which can be customized
• Table: Default table is created by a container with
a unique name that combines the following:
– EJB name defined in the deployment descriptor
– JAR file name including .jar extension
– Application name defined during deployment
– An underscore and five-character hash code
– Example: DeptBean_dept_jar_dept_xxxxx
• Column: With the same name as the CMP fields
defined in the deployment descriptor; Java data
types are translated to database data types in
oracle.xml
Copyright © 2005, Oracle. All rights reserved.

Default Mapping of CMP Fields to Database Table Columns


The container provides mappings of the persistent fields that are defined in the ejb-
jar.xml file to the database:
• Database: This is the default database that is specified in data-sources.xml. For
the Java Naming and Directory Interface (JNDI) name, use the <location> element
for nonemulated data sources and the <ejb-location> element for emulated data
sources. Upon installation, the default database is a locally installed Oracle database
that must be listening on port 1521 with a system identified (SID) of ORACLE. To
customize the default database, change the first configured database to point to your
database.
• Table: The container creates a default table with a unique table name. The table name
is constructed with an EJB name, a JAR file name including the .jar extension (all
dashes [-] and periods [.] are converted to underscores [_]) and an application name
that you define during deployment. If the constructed name is greater than 30
characters, then the name is truncated at 24 characters. An underscore followed by five
characters made up of an alphanumeric hash code is appended to the name for
uniqueness. For example, if the EJB name is DeptBean, the JAR file is dept.jar,
and the application name is dept, then the default table name is
DeptBean_dept_jar_dept_xxxxx.
• Column names: Column names in the entity bean table have the same name as the
<cmp-field> elements in the deployment descriptor.

Oracle 10g: Build J2EE Applications 14-22


Explicit Mapping of CMP Fields
to Database Table Columns

<enterprise-beans>
<entity-deployment name="Departments"
data-source="jdbc/hrDS" table="DEPARTMENTS">
<primkey-mapping>
<cmp-field-mapping name="department_id“
persistence-name="DEPARTMENT_ID"
persistence-type="NUMBER(4)"/>
</primkey-mapping>
<cmp-field-mapping name="department_id“
persistence-name="DEPARTMENT_ID"
persistence-type="NUMBER(4)"/>
<cmp-field-mapping name="department_name“
persistence-name="DEPARTMENT_NAME“
persistence-type="VARCHAR2(30)"/>
...

Copyright © 2005, Oracle. All rights reserved.

Explicit Mapping of CMP Fields to Database Table Columns


Deploy your application with only the ejb-jar.xml elements that are configured. Oracle
Application Server 10g Containers for J2EE (OC4J) creates an orion-ejb-jar.xml file
for you with the default mappings in them, which you can modify. When you create an
entity bean, JDeveloper automatically creates this file. The mapping is done implicitly. The
slide shows the orion-ejb-jar.xml file for the Departments bean. The
<entity-deployment> element in the orion-ejb-jar.xml file contains
information about the database table and the bean’s CMP fields.
The example in the slide demonstrates how to map persistent data fields in your
Departments bean instance to the database tables, and how to map the columns to the
Oracle database table DEPARTMENTS.
The <entity-deployment> name attribute identifies the bean. The data-source
attribute defines the data source that is used by this bean. The table attribute defines the
database table.
The bean primary key, department_id, is mapped to the database table column
department_id within the <primkey-mapping> element.
The bean persistent data field department_name is mapped to the database table column
department_name within the <cmp-field-mapping> element. Similarly, all the
CMP fields are mapped to the corresponding columns in the table.

Oracle 10g: Build J2EE Applications 14-23


Explicit Mapping of CMP Fields to Database Table Columns (continued)
Mcomplex Data Types in CMP Beans
While mapping CMP fields to database table columns, you need to take care of the data
types that are being mapped. You can define simple data types and Java user classes that are
serializable. If you have complex native data types, then you have to map them to the
appropriate database type. For example, if you have java.util.Date or
java.util.Time, then you should map it to Oracle database type DATE. The Date and
Time map to DATE in the database because Date contains the time.
You can map the database type CLOB to java.lang.String or a character array. You
can also map VARCHAR2 for a string or character array; however, it can hold only up to 2
KB. To map string or character array larger than 2 KB, specify CLOB in the persistent-
type attribute. You can map a byte array to BLOB. There is a size limitation of 4 KB when
mapping a serialized object to BLOB type.
Mapping java.sql.CLOB and java.sql.BLOB directly is not supported because these
objects are not serializable.

Oracle 10g: Build J2EE Applications 14-24


Client for Departments Bean

import java.util.Hashtable;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.rmi.PortableRemoteObject;
...
public class DepartmentsClient
{
public static void main(String [] args)
{
DepartmentsClient departmentsClient =
new DepartmentsClient();
try
{
Context context = getInitialContext();
DepartmentsHome departmentsHome =
(DepartmentsHome)PortableRemoteObject.narrow
(context.lookup("Departments"), DepartmentsHome.class);
Departments departments;
...

Copyright © 2005, Oracle. All rights reserved.

Client for Departments Bean


The slide shows the client for the Departments bean. The client for a CMP entity bean is
the same as the client for a BMP entity bean.
Import the necessary packages. The slide shows only a few of the packages that are
imported. The client application should have the following import statements:
import java.util.Hashtable;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.rmi.PortableRemoteObject;
import mypackage1.Departments;
import mypackage1.DepartmentsHome;
import java.util.Collection;
import java.util.Iterator;
import javax.naming.NamingException;
Note that the client application gets the initial context by invoking the
getInitialContext() method, which is a private method of the bean. The
implementation of this method is the same as in BMP beans. This method is not shown in
this example. The lookup()method returns the reference to the home object
(departmentsHome). This reference can now be used to create an EJB object. A variable
of type Departments is declared.

Oracle 10g: Build J2EE Applications 14-25


Client for Departments Bean

System.out.println(" CREATING A NEW DEPARTMENT WITH


ID 404... ") ;
departments =departmentsHome.create(new Long(404),
"Security");
System.out.println(" SUCCESSFUL ");
System.out.println("Get the DEPARTMENT_NAME " +
departments.getDepartment_name());
System.out.println("Changing the DEPARTMENT_NAME to
Security Services " );
departments.setDepartment_name("Security Services");
System.out.println("PRINTING THE DEPARTMENT_ID AND
DEPARTMENT_NAME");
System.out.println(departments.getDepartment_id() +
" " + departments.getDepartment_name());
...

Copyright © 2005, Oracle. All rights reserved.

Client for Departments Bean (continued)


The code shown in the slide is the continuation of the client application. The client
application:
• Invokes the create() method to create a new database data. One row with
department_id 404 and department_name Security is added to the
DEPARTMENTS table.
• Invokes the getDepartment_name() method to check if the
department_name is Security
• Invokes the setDepartment_name()method to change the department_name
from Security to Security Services
• Prints department_id and department_name

Oracle 10g: Build J2EE Applications 14-26


Client for Departments Bean
// Retrieve all instances using the findAll() method
Collection coll = departmentsHome.findAll();
Iterator iter = coll.iterator();
while (iter.hasNext())
{
departments = (Departments)iter.next();
System.out.println("department_id = " +
departments.getDepartment_id());
System.out.println("department_name = " +
departments.getDepartment_name());
System.out.println("manager_id = " +
departments.getManager_id());
System.out.println("location_id = " +
departments.getLocation_id());
System.out.println();
}
}
catch(Throwable ex)
{...

Copyright © 2005, Oracle. All rights reserved.

Client for Departments Bean (continued)


The client application can retrieve all instances by invoking the findAll() method. The
code in the slide shows how to retrieve each field from the Collection by using an
Iterator.

Oracle 10g: Build J2EE Applications 14-27


Summary

In this lesson, you should have learned how to:


• Describe the features of a BMP entity bean
• List the components that have to be created to
develop a BMP bean
• Describe the features of a CMP entity bean
• List the steps in developing a CMP bean
• Develop and deploy a CMP bean
• Develop a client for CMP EJB

Copyright © 2005, Oracle. All rights reserved.

Summary
In this lesson, you should have learned that:
• The bean provider furnishes the logic to manage the persistence in case of BMP entity
beans
• The container provides the persistence logic in CMP entity beans
You should have also learned how to develop a CMP bean and how to invoke the bean
methods from a client application.

Oracle 10g: Build J2EE Applications 14-28


Practice 14-1: Overview

This practice covers the following topics:


• Developing a CMP entity bean to represent and
update the EMPLOYEES table
• Creating a remote interface, and a home interface
for a CMP entity bean by using Oracle JDeveloper
10g
• Implementing the create() methods, callback
methods, and methods of the remote interface in
the entity bean class
• Testing the entity bean with a client application

Copyright © 2005, Oracle. All rights reserved.

Practice 14-1: Overview


In this practice, you develop a CMP entity bean by using Oracle JDeveloper 10g. This bean
represents the EMPLOYEES table. You include a business method to update the
EMPLOYEES table, and provide set() and get() methods for the CMP fields. You
generate a client to test the entity bean.

Oracle 10g: Build J2EE Applications 14-29


Practice 14-1
The purpose of this practice is to create a CMP entity bean (UpdateEmployee) that
represents the EMPLOYEES table of the hr schema. The bean should contain the set()
and get() methods for the CMP fields. It should also contain a business method called
updateDetails() that updates the EMPLOYEES table.
Note: For this practice, you can use the database connection hr, which was created in step 1
of practice 12-2.
The workspace for this practice is practice14ske.jws. Open the
updateemployeeCMP project. This project contains the necessary skeleton files for this
practice. Note that these files are created by using the entity beans from the Tables option of
JDeveloper, which was demonstrated in this lesson.
1. Navigate to UpdateEmployee.java in the UpdateEmployee bean and open it
in the code editor. This is the remote interface:
Declare an updateDetails()method, which takes the following as parameters:
Long empid (this corresponds to employee_id, which is the primary key of the
table), String lname, String fname, String email, Timestamp hdate, and String
jid. This method should throw RemoteException.
2. Add code to the bean class. Open UpdateEmployeeBean.java in the code editor.
Implement the updateDetails() method declared in the remote interface:
- Invoke the set() methods for the CMP fields lname, fname, email,
hdate, and jid in the updateDetails() method.
3. Edit the UpdateEmployeeClient.java file:
a. Import java.sql.Timestamp.
b. Add code to the try block of the main() method. Use the second form of
create()method with parameters and add a new employee with the following
data: employee_id=600, last_name=shenoy, email=pshenoy,
hire_date=21-jul-2001, and job_id=ST_MAN
Note: Observe the code that creates a Calendar object with the hire_date.
Time in milliseconds is obtained with this object. Use this long value to create
the Timestamp object while invoking the create()and updateDetails()
methods. Pass the long value to the constructor of Timestamp. Other forms of
constructors are deprecated.
c. After the record is added, use the set() method to set the first name to
Preetham. Invoke the get() methods to display the first_name and
last_name.
d. Invoke the updateDetails()business method to update the details of the
employee. Change first_name to Joseph, last_name to Dsouza and
email to jdsouza. Display the first_name and last_name.
e. Find details of the employee whose employee_id=120.
Hint: Use findByPrimaryKey()method. Display the first_name and
last_name of this employee.

Oracle 10g: Build J2EE Applications 14-30


Practice 14-1 (continued)
4. Test and run the application:
a. Right-click UpdateEmployee bean and select Make (optional).
b. Right-click the UpdateEmployee bean and select Run.
c. Right-click the client application and select Run.
5. Sample Output:
Adding a new employee with employee_id 600
Added successfully...
Calling setFirst_name() to set the first_name to Preetham
Displaying the first_name and last_name
PREETHAM SHENOY
CALLING THE updateDetails() BUSINESS METHOD TO UPDATE THE
DETAILS OF THE EMPLOYEE
Displaying the first_name and last_name
JOSEPH DSOUZA
Finding details of an employee whose employee_id=120,
using the findByPrimaryKey() method
Displaying the first_name and last_name
MATTHEW WEISS

Oracle 10g: Build J2EE Applications 14-31

You might also like