Anda di halaman 1dari 14

Persistent Java Objects in 3 tier architectures

Bob Bretl, Allen Otis, Marc San Soucie, Bruce Schuchardt, R. Venkatesh
GemStone Systems, Inc.

Abstract
The 3 tier architecture logically separates the functions of an application into a user interface
component, a server business logic component, and a database component. Many application
server products, ORBs, and middleware products provide support for building and deploying
applications using the 3 tier architecture. In most of these cases a primary role of the middle tier
business logic components is to manipulate data stored in and accessed from the 3rd tier. The
GemStone/J application server includes a capability for creating, storing, and using persistent
Java objects in the middle tier. We argue that the use of persistent Java objects in the middle tier
of a 3 tier application offers significant advantages over other approaches.

1. The 3 tier architecture

1.1 Components of the architecture


The standard 3-tier architecture consists of presentation and application logic in the client, application
and business logic in a middle tier application server, and data managed by database servers in the 3rd
tier. The application is typically controlled by user interface in the client with substantial application
processing taking place in the middle tier application server. The middle tier code typically drives 3rd tier
data queries, updates, and transactions and implements shared business logic. Data manipulation
performed by the application is typically done on object representations of 3rd tier data fetched through
queries, or through data manipulation APIs or SQL code that operates in the database server. There may
be some small amount of configuration data used to govern activities in the middle tier, but usually it is
stored in specialized files designed for specific configuration and management purposes.

Client Java VM or Browser On client machine

Middle Tier Application Server On server machine(s)

Relational or IMS Database

FIGURE 1 3 tier architecture

1.2 Example Applications


Customer service application for an electric utility - Employees answer phone calls from customers who
are reporting problems with electric service. The user interface displays customer account and location
information so a trouble ticket can be generated that contains information about the nearest lines,
transformers, etc.. The application server accumulates and dispatches trouble tickets as well as caching
customer account and system information from a 3rd tier mainframe database.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 2

Derivatives trading system - The application is a mathematical modeling system which is used to
simulate and forecast trading based on historical data. The application server retrieves the historical
data, runs the modeling program and updates actual trade information on a 3rd tier database which
contains the official bank records.

Semiconductor fab control - Clients are user interfaces that provide interactive query and update to the
manufacturing process as well as unattended machines which update process data. The application
server maintains accurate work-in-progress, machine scheduling, and historical process control
information for the entire factory. External 3rd tier data sources are accessed to retrieve customer order
information (input to process scheduling) and to update production totals.

Bank information system - The user interface allows a banking officer to view all of a customer’s
accounts in an integrated fashion. The application server caches account state and information about
available products, rates and services and updates the changes on the existing mainframe database.

1.3 Role of the application server


The application server in the middle tier represents an evolution from 2-tier client-server applications. In
a 2-tier client-server system, business logic is either in the client, or in stored procedures in a Relational
DB server. A 2-tier system usually requires transporting a significant amount of data to the client,
because of lack of a complete programming model in the database server. This leads to "fat-client"
problems with too much memory consumption in the client. Also there may be excessive CPU time
spent executing object-relational mapping software. The application server in the middle layer
coordinates, consolidates and presents object views of data to applications.

A scalable application server needs to handle large numbers of clients and access large volumes of 3rd
tier data. This implies many Java virtual machines, many threads per virtual machine, and large object
memory spaces.

2. Overview of GemStone/J
GemStone/J provides an environment for running the middle tier of 3-tier Java and CORBA applications,
offering load-balanced, brokered access to Java processing resources, shared persistent Java objects for
advanced data models, data caching and coordination, managed access to 3rd tier databases, and services
for deploying and managing running systems. A set of client interfaces provide both access to the
application server from a variety of client platforms, offering services from CORBA to interactive,
conversational sessions to scalable transaction management.

2.1 Client Connection options


GemStone/J provides several ways for a client to connect to the application server.
• Distributed Java Beans - GemStone provides both client and server APIs that provide a session
oriented client-server connection using Java Beans.
• EJB - GemStone/J is developing APIs that will conform to the Enterprise Java Beans specification.
• CORBA - GemStone/J 1.1 includes a CORBA ORB .
• RMI can be used for lower level communications.
• An HTTP server implemented in Java can be executed in the GemStone/J server virtual machine.
• Headless Java programs can execute on the server to implement batch-mode operations.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 3

2.2 Java virtual machine in the Server


The GemStone/J application server includes a complete Java virtual machine and JDK. GemStone is a
Java source code licensee. The GemStone/J VM is persistence capable and passes the JCK conformance
tests.

2.3 Persistence model


GemStone/J implements orthogonal persistence by reachability. Any Java object can be made persistent,
without prior work at development time to identify classes of objects that are to be persistent, and
without requiring post-processing of the Java classes whose instances may be made persistent. An object
can be persistent if it is an element of a known root object in the repository, or if it is referred to by
another object which is itself referred to by transitive closure from a root object. Transient and persistent
Java objects look and act exactly the same from the developer’s point of view, which makes use of
GemStone/J persistence very easy to use. For instance, a developer building a GemStone/J application
can use a 3rd party Java class library to create objects that become persistent, even though the 3rd party
knew nothing about GemStone/J when the class library was written.

This means that creation of new persistent objects requires only these steps:
• Create the object
• Begin a transaction
• Establish a reference to the object from another object which is directly or indirectly connected to a
root object
• Commit the transaction

The first and third steps are carried out with typical Java language operations. The second and fourth are
carried out by using a transaction service API, gemstone.services.GsTransactionService.
Additional transaction services, such as the CORBA Object Transaction Service and declarative
Enterprise Java Beans transactions, will be supported in future releases. Also, it is not necessary for a
Java program running in GemStone/J ever to commit a transaction. In such a case, all objects created by
that program live only as long as the application continues to run. This is standard Java behavior.

Persistent objects committed to the repository outlive the application that created them, and are not
subject to garbage collection by the VM while it is running. If a subsequent transaction causes the last
reference to an object to be removed, the object is a candidate for garbage collection. To reclaim space
taken up by such unconnected objects in the repository, the GemStone/J server includes a background
garbage collector that detects such objects and returns the space they occupy to the repository for reuse.

Changes to persistent objects are made permanent and visible to other applications in the repository only
when a transaction is successfully committed by the application making the changes. Until that time,
those changes are visible only to the application that has made them. This is required to insure that
changes to shared objects leave the repository in a consistent state, and is a key characteristic of ACID
transactions. Otherwise, the integrity of the information enclosed in the objects would be compromised.

Persistence Implementation

GemStone/J implements persistence without changing the Java language or class files by replacing the
object manager in the standard Java VM with an object manager that understands persistence and
transactions. The GemStone/J VM is a fully Java 1.1 compliant VM, passing all of the Java
Compatibility Kit tests. The Java JDK 1.1 API suite is available to every GemStone/J VM, and is pre-
Persistent Java Objects in 3 tier architectures 08/17/98 Page 4

loaded into the default object repository. Java object semantics, Java threads, class initialization, and
object finalization all function as specified by the Java 1.1 platform specifications.

The GemStone/J object manager, and its associated garbage collection mechanisms, make use of
operating system shared memory and a number of support processes to implement concurrent access to
the shared object domain from a large number of threads and VMs. The object management algorithms
use shared memory both for shared object access, swapping objects between disk and memory as needed.
This allows a GemStone/J VM to operate on a very large domain of objects – over a billion objects -
without consuming large amounts of private memory. It also provides support for efficient use of very
large objects - images, video, sound samples, et cetera. Use of shared memory and the disk is transparent
to the application and to the developer, and is visible only indirectly to the system manager.

VM processes, shared memory caches, repository files, and system processes can be transparently
distributed to as many heterogeneous machines as needed for optimal performance and maximum
leverage of resources. SMP architectures are automatically utilized. Changes to objects are recorded in
transaction logs that allow for point-in-time recovery in the event of hardware failure. Transaction logs
and repository files can be mirrored to standby machines for safety. Backups of the repository are
performed on-line, and an on-line persistent object garbage collector insures that space freed by removal
of objects is made available for reuse. The server provides real-time performance statistics gathering,
which can be used to implement configuration tuning changes while the system is running.

2.4 Selected GemStone API’s (gemstone/services)


GemStone/J provides a number of services, which are uniquely useful to working with persistent objects.
These services can be used directly by applications, by management functions, and by infrastructure
functions. Value-added GemStone/J services are implemented by providing Java APIs that transparently
access unique GemStone/J capabilities. These services are not operating-system dependent, which means
application developers can count on using these services from Java code, on all hardware and operating
system platforms supported by GemStone/J. All services of this kind appear to the developer as Java
APIs. It is never required that developers use the JNI or use non-standard Java code to access
GemStone/J services.

Transactions and locking: GemStone/J transactions are controlled by the application (or the Enterprise
JavaBeans container) by use of a transaction service API, which provides begin/commit/abort methods as
well as a variety of transaction inquiry and support methods. A lock service provides mechanisms to
establish and inquire about object-level locks used to insure successful transactions in concurrent use
situations.

Login and authentication: GemStone/J provides object-level security for persistent objects. As a result,
it is necessary for the application or user to provide a login user name and password to obtain access to
the object repository. Once provided, the VM insures that only allowed object accesses are permitted.

Class loading: GemStone/J can store Java classes and methods in the shared repository. This allows
classes to be loaded from shared memory instead of from the file system through a class path. The use of
shared classes is integrated into the standard class lookup scheme, so that developers and application
code need not be aware of the mechanism. Classes can be accessed from the filesystem as usual, or can
be stored in the repository, from which they will be loaded transparently at runtime.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 5

Naming Objects: GemStone/J provides NameService APIs that allow binding, resolving, and unbinding
objects. Binding an object makes it a named persistent object as of the next transaction commit.
Unbinding makes the object potentially garbage collectable as of the next transaction commit. Both
global and per-user-account name spaces are provided.

Scalable Containers: GemStone/J provides a number of scalable container classes for building large
collections of Java objects. These containers grow dynamically to very large sizes without significant
degradation in performance of common operations such as addition, removal and enumeration. Java
applications do not have to request dynamic growth, and do not have to code around size limitations.

Concurrent Update Objects: Concurrent update objects are designed to provide a higher degree of
concurrency than conventional objects in multi-user update situations. They provide protocol for
common update operations for which locks are not required, even if multiple applications are
concurrently performing updates. Their behavior in transactions is governed by logical concurrency rules
rather than physical read-write conflicts. They greatly simplify the task of designing multi-user
applications. CuQueue, for example, provides a multiple producer, single consumer model of queue
management, which does not require any locking. CuIdentityBag allows multiple applications to
concurrently add elements or remove different elements.

Changed Object Notification: Applications can request notification when other applications or users
commit changes to persistent objects of interest.

Two-phase commit: Two phase commit support is in development and will be included with the release
of EJB functionality. GemStone/J will be able to function as a resource participating in transactions
using the CORBA Object Transaction Service, the Java Transaction Service, or as an X/Open XA
resource.

2.5 GemStone Server System Architecture


The GemStone server uses a scalable architecture (Figure 2 on next page), that allows object sharing
among many server virtual machines. It supports shared memory caching, spreading virtual machines
across multiple CPUs and multiple non-shared-memory machines. It supports 10’s of gigabytes of
persistent Java objects efficiently, allowing great flexibility in caching data retrieved from the 3rd tier.

3. Scaling the middle tier


Scaling the middle tier of a 3 tier system means scaling the application server to support more concurrent
client connections, and efficient access to more and larger data sources.

Scaling the number of clients that can be simultaneously served requires scaling the number of threads
the server can run. There are limits to the number of threads within a single Java virtual machine, based
on operating system limits on number of threads per process, and practical limits imposed by thread
management within the virtual machine. In addition, engaging more than one piece of hardware will
require use of more than one Java VM. This means that a highly scalable middle tier Java server needs to
combine a large number of VMs with a substantial number of threads in each VM. GemStone/J does this.

Scaling the size of the server object space is affected by the limits of garbage collecting large memory
spaces. Also, a purely memory based object manager is probably not extendible outside the boundaries
of one shared memory machine. At some point a large amount of cached data in the server will also run
Persistent Java Objects in 3 tier architectures 08/17/98 Page 6

into restart issues. The time to load or initialize large object caches may become excessive, if those
caches are not made persistent and made quickly recoverable by transaction logging techniques.

The persistent storage manager is able to efficiently manage disk I/O to a large object space on disk, with
just the working set cached in memory. A purely virtual memory based approach to a large object space
may have problems, such as excessive I/O caused by a garbage collector that assumes all objects fit in a
resident set of virtual memory pages. Making cached data persistent within the middle tier allows
garbage collection of long lived objects to be separated from garbage collection of short lived objects,
thus allowing more flexibility in garbage collection algorithms, and scheduling of garbage collection for
off-peak hours of the day.

By including a shared memory cache, as shown in Figure 3, GemStone/J allows multiple virtual
machines running on one shared memory node to efficiently access a large persistent store, and to utilize
multiple CPUs . The shared cache allows disk I/O for commonly accessed objects to be performed by one
virtual machine and then the resulting buffers in the working set can be used by other virtual machines.

By supporting persistence, and by allowing shared caches on multiple shared-memory nodes to be


connected to a single object repository on disk, the virtual machines in a GemStone/J system can be
spread out across multiple machines, thus allowing scaling beyond the limits of one shared-memory
processing node, and allowing support of non-uniform memory architectures. As shown in Figure 4, if a
shared cache is remote from the repository, each remote virtual machine has a connection to a Page I/O
process on the machine containing the repository. Thus each remote virtual machine does it’s own
handling of misses and does it’s own flushing of committed modifications to the repository.

Server applications typically access a large amount of information. Unless all server threads are running
in the same Java VM and care is taken to provide shared access to this information the memory
consumed by each server’s redundant information is quite costly. Trying to control shared information in
this way limits the servers to a single VM and its inherent resource limits, and adds complexity to the
architecture of the system. Pushing the management of shared information into the persistence service
itself, by means of a shared object cache located in shared memory, reduces application complexity while
enabling any number of Java VMs access to the objects in the cache. Having the persistence service
itself manage caching of shared information also provides server applications with the ability to perform
transactional updates on the information, an operation more difficult to achieve when sharing is done at
the application architecture level.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 7

GemStone/J External
Data
Servers
CORBA ORB
ORB Java VM
Client IIOP
Java/C++
Java VM
Web Service JDBC
IIOP

Web VM Broker JDBC


Browser HTTP Java VM

GemStone/J VMs
Web Server

(TCP/IP) Shared Object Cache

Java Beans
Client
Transaction
Log Transaction
Monitor
Clients -
Web Browsers or
Java VMs Garbage
Extents Collector

FIGURE 2 - GemStone/J Architecture


Persistent Java Objects in 3 tier architectures 08/17/98 Page 8

Java VM Java VM
Java VM
Garbage
collector Monitor

Shared Object Cache

Repository Transaction Log

FIGURE 3 - Processes on one machine

Java VM Java VM
Page I/O

Monitor
Shared Cache
Shared Cache
G.C.

Repository Transaction Log

FIGURE 4 - Processes on multiple machines.

4. Benefits of persistence in the middle tier


Persistent objects are superb at modeling business data, but relational and mainframe databases are far
more commonly used. This is largely due to the product and service infrastructure which has developed
around relational and mainframe data management products, and to the fact that these databases pre-date
the object languages now being used for applications. This means that in spite of some significant
Persistent Java Objects in 3 tier architectures 08/17/98 Page 9

modeling, development, and performance advantages, the use of persistent business objects is still a
small part of mainstream commercial application development.

Nonetheless, persistent objects can provide significant benefits to applications written in object
languages, even if those applications are not storing and managing primary business data as persistent
objects. The following sections describe some of the ways in which persistent objects managed by a
middle tier application server provide benefits to applications whose main business is manipulating other
forms of data.

4.1 Synchronized and reliable long term caching of data


A typical use of GemStone/J persistence is to create and manage caches of 3rd tier data as persistent
objects. Caching data as objects – even as transient objects - can provide a number of basic benefits. If a
piece of 3rd tier data is needed more than once by an application, or if it is needed by more than one
application running in a VM, caching an object copy of the data can substantially reduce the amount of
time, CPU, and database server resources needed to use the data. In addition, substantial parts of the
application or applications can operate against the object copy of the data, without need to know how the
data was obtained or how it will be updated. The cache can be created and maintained by a service thread
or VM, coordinating with the application threads or VMs when changes to the cache objects must be
rolled up into the database in transactions.

GemStone/J runtime benefits


• Use of GemStone/J persistent objects in a database cache can increase the reuse of cached objects to
all applications running in all VMs – not just those running a single VM. A cache of purely transient
objects would have to be replicated in each VM. In a high end system 100 VMs might be running
against GemStone's shared memory cache and thus sharing the database cache. Using persistent
objects for the cache also reduces the time to load the cache on a restart of the application server. In
addition, garbage collection of objects discarded from the cache will be performed by a single
dedicated background process, not redundantly by each VM in the system.

• A GemStone/J persistent cache allows for implementation of a delayed cache synchronization


strategy. If the object views of the data and the 3rd tier database are not required to be in constant
synchrony, applications can perform GemStone/J transactions directly against the cached data
objects, maintaining an all Java programming model with ACID transactions. A separate process can
sweep up committed changes to cached objects and replay those changes to the 3rd tier database on a
schedule appropriate to the application and the database.

GemStone/J design and development benefits


• GemStone/J's implicit persistence model makes it straightforward to code the caching mechanisms
needed to support a persistent database cache. GemStone/J's changed object notification services
enable applications and cache management processes to detect changes to cache objects and queue or
post appropriate 3rd tier database updates.

• For the application developer, use of a persistent cache simplifies the programming of data
manipulation substantially. Instead of coding to SQL, JDBC, and/or an object/relational mapping
service, the developer codes Java, and lets the caching mechanisms manage the database interactions.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 10

4.2 3 tier with control objects or metadata


Another typical way applications can take advantage of GemStone/J persistent objects is to use them for
application control or metadata. These objects can represent configuration information, user
customizations, workflow queues, load balancing guidelines, database access information, and more.
This kind of information is needed for efficient, responsive, and customized operation of the application,
and in other systems is usually stored in external files and read into the VM at runtime, or created
dynamically and managed through a variety of file or socket based mechanisms. GemStone/J persistence
provides an efficient and simple way to implement application control objects and metadata.

GemStone/J runtime benefits


• Control objects are accessed from the shared cache like all GemStone/J persistent objects. This
means that multiple individual VMs do not have to individually read control files or other sources,
and control objects do not have to be replicated separately in each VM. Access is faster because of
the sharing, and overall memory usage is reduced. Discarded control objects are garbage collected by
a background process, reducing the burden on individual VMs.

• Control objects will survive system failures and GemStone/J recovery or restore operations. This
makes the application runtime environment fault tolerant. This is particularly valuable for persistent
queues, which require restarting from a known state to insure proper sequencing.

GemStone/J design and development benefits


• GemStone/J’s implicit persistence model makes it straightforward to create, name, share, modify, and
remove application control objects. Use of external storage APIs – file, database, or otherwise, is not
needed. GemStone/J transactions to create and update the objects are independent of 3rd tier database
transactions, so 3rd tier concurrency is not an issue. GemStone/J's concurrent update classes,
including persistent queues, make design of control operations simple.

GemStone/J management benefits


• Control objects can be stored in unshared or restricted namespaces, and can be subject to individual
object security, to insure that only trusted applications can use them.

• GemStone/J's ability to dynamically update persistent Java object structures allows a new version of
an application – with new control object classes – to be installed without sacrificing existing control
objects.

4.3 Reliable infrastructure


Persistence in the middle tier allows server configuration information to be persistent, thus speeding up
server restart after a hardware, operating system, or power failure. Changes to the configuration
information of an EJB, CORBA ORB, HTTP or server application will be logged by the GemStone/J
transaction logging and automatically recovered at system restart. Also, the configuration information
can be accessed through the shared cache, using I/O and memory more efficiently when there are many
virtual machines accessing the same information.

3 tier with object extensions


Frequently, new applications combine new business data, specific to the application, with existing
corporate relational and mainframe data. The new application is intended to provide a new view or a new
way of using existing data, mixing it with new information that describes aspects of the business that did
not exist when the relational or mainframe data was designed. In many cases, this new information is
Persistent Java Objects in 3 tier architectures 08/17/98 Page 11

being modeled and stored as persistent objects. The application in these cases gathers, presents, and
manipulates 3rd tier data alongside new information represented as persistent objects. Transactions may
be separate, if the two classes of information are modified separately by the application, or coordinated in
distributed transactions if single application operations update both kinds of information.

The reasons for doing this may be several. Often the information in question is complex, with a complex
Java object model that may be difficult to express in regular or normalized data management systems,
and which may be expensive to decompose for storage and reconstitute for access. Storing the
information as objects can make it substantially easier to change the object model later, reducing the cost
of application change, and allowing for greater flexibility in responding to business changes. Also,
designers of new applications designed around distributed Java technology and incorporating a variety of
heterogeneous data sources and applications may find that the reduced complexity of using persistent
objects can mean the difference between manageability and unmanageability of the result.

GemStone/J runtime benefits


• The application code which runs in GemStone/J operates directly against the persistent object part of
the information managed by the application. Direct execution in the persistent objects offers
potentially substantial performance advantages over access through a communications API. Also,
persistent objects are directly shared between all VMs using them, which minimizes system memory
usage.

GemStone/J design and development benefits


• Design and development of persistent business information is generally simpler than designing for
external storage. GemStone/J’s implicit persistence model does not require fetch and store calls, O/R
mapping, or communications with external servers. The Java object model is stored and accessed
directly, as Java objects.

• GemStone/J’s ability to run 3rd party Java class libraries and make their instances persistent means
that overall the application developer can reuse a great deal more code than would be possible if all
instances had to be persisted to a relational or mainframe database.

5. How Persistence is Used With CORBA


CORBA is the Object Management Group’s architecture for language-independent distributed object
communications and services. Persistent transactional objects are a natural fit with OMG objects and
services in Java. Persistence provides CORBA applications and services a more natural way of working
with the information they require by eliminating the need to work with files or database structures
directly. Adding the GemStone/J shared object cache allows these CORBA applications and services to
be scaled beyond previous limits. The judicious use of transient modifiers for attributes in recent
CORBA revisions allows a CORBA application or service developer to protect an object’s runtime
information from being subject to transactions.

5.1 Persistent CORBA Services


While a few CORBA services are not benefited by a persistent Java store, most have an underlying
repository of information that can benefit from persistence. Two examples are given here - the Naming
Service and the Interface Repository Service.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 12

5.1.1 The CORBA Naming Service


The CORBA Naming Service’s directory must be durable and the service must provide atomic updates to
the directory. While this can be done with any database, it is easy to take a Naming Service (NS)
directory that is implemented in Java and store it as persistent, transactional Java objects. The
NamingContext objects themselves are made persistent by reachability when they are bound into an
already persistent NamingContext. All of the bindings added to a NamingContext are likewise made
persistent by reachability.

Such an implementation of the NS works with Java objects only and need not perform queries against an
external database. The performance of the NS is dramatically improved while maintaining the durability
and transactional nature of its directory. We have found that most ORB implementations do share a
common shortcoming regarding persistence in that the actual reference information in stubs is held in a
transient variable. The NS has to provide a simple workaround for this by storing the reference
information (typically an IOR object) as additional information in a binding.
5.1.2 Interface Repository
An ORB typically makes an Interface Repository (IR) available to applications to allow the use of
dynamic invocation of operations from a client, and dynamic dispatching of operations in a generalized
skeleton in the server.

While the IR is typically heavily updated during development time it is also typically read-only in a
deployed application. Developers require it to be a shared database with ACID transactions while
deployed applications require very fast read-only queries. Making the IR a persistent object in
GemStone/J satisfies both these needs since persistent objects are also naturally transactional.

At runtime, applications get maximum query performance as the attributes of this IR’s object-oriented
schema can be queried in a natural fashion and the resulting information is already in object form. A
persistent IR can also be used to simplify an ORB by blurring the edges between static and dynamic
invocation methods, as is demonstrated in GemStone’s GemORB Smalltalk ORB. In it the IR is used
during all dispatching by the ORB itself, requiring the implementation classes to implement a one-line
method that identifies the CORBA types supported by instances of the class. This removes the need for
skeletons or TIE objects in the ORB altogether, reducing the size of a CORBA application at runtime
significantly while introducing minimal dispatching overhead. The shared object cache in GemStone
allows each server process to directly access the IR in a shared memory node, allowing this kind of
dispatching to be done with minimal disk access.

5.2 Persistent CORBA Applications and Objects


CORBA applications and the objects that comprise them can benefit from transactional Java persistence
as well. CORBA application servers are typically created by bootstrap applications, which initialize the
application and ORB and then turn control over to the ORB to process client requests. If, instead, the
application server objects are made persistent and CORBA object references are tied to persistent
objects, the ORB can automatically locate and make persistent objects and their services available to
clients.

The use of segmented object identifiers to delegate location of object implementations to persistent
object managers has been demonstrated in the VisiBroker for Java ORB, which is integrated with the
GemStone/J version 1.1 product. While segmented object identifiers can be used to locate information
needed to compose objects in an object-relational mapping system, it is easier to directly map object keys
to persistent object identifiers, or to a persistent name space. Using the VisiBroker Activator service, a
Persistent Java Objects in 3 tier architectures 08/17/98 Page 13

precursor to the new POA servant managers, we identify the Activator service with the initial portion of
the object identifier. The Activator service then uses the remaining portion of the key to look up the
object in the persistent object store. In one implementation this was done by using the persistent object’s
object identifier, embedding the OID in the CORBA object reference when it was formed and given to
clients and using this OID to look up the object in the persistent store directly (a one-step query on the
persistent object manager in GemStone/J). In another implementation the Activator service used a key
from a persistent naming service in GemStone/J to form the CORBA object reference that was given to
clients, and then later used this key in locating the persistent object.

Since persistence is by reachability and not by inheritance in GemStone/J, and since no coding need be
done to make an object persistent, this approach to delivering persistent objects to the CORBA bus can
be used for any CORBA-enabled object. Further, the shared memory architecture of GemStone/J allows
the exact same CORBA object to be serving in multiple Java VMs simultaneously, allowing higher
throughput for CORBA.

6. How Persistence is Used With EJB


Enterprise JavaBeans (EJB) is Sun’s new standard for server-based Java component applications. The
EJB specification defines a server runtime environment for EJB applications which performs many of the
tasks of application and data lifecycle management and transaction processing - object activation, thread
creation and management, transaction demarcation, state management, time-outs, and persistence
management. EJB objects are service objects - activated on demand, providing a public interface with
well-defined methods that are used by applications (or by other EJBs) to perform application functions.

Enterprise JavaBeans architectures can benefit from persistent, transactional object services in the same
way as CORBA architectures. EJB places the additional demand on the persistence mechanism that it
support two phase commit if it is to be used for anything but storage of EJB meta-data.

6.1 Support for Session and Entity EJBs


EJB specifies two kinds of Beans, SessionBeans and EntityBeans. Both have an EJB Home interface
used in creating or finding the bean. A persistent EJB name space provides an indirection from the bean
reference to the bean’s home. This allows a JNDI or CORBA Naming Service to maintain a durable
reference to the Home object and gives fast access to the bean in any GemStone/J VM.
SessionBeans benefit from a transactional persistence service when the classes, methods, meta-data,
deployment descriptors, and other items from an EJB JAR file are objects in a shared object cache from
the persistence service. SessionBeans can make use of the persistence service to hold information, and
can blend in relational or object-relational information as necessary because all resources support a
distributed two-phase commit through the Java Transaction Service. Object-relational information can
also be cached with the persistence service to accelerate applications that might be hindered by the
complexity of the mapping layer in such a system. When this information is stored as GemStone/J
persistence objects, no mapping need be done in order for applications to use it, and the GemStone/J
shared memory cache reduces disk and database access.

EntityBeans can benefit further if the Enterprise Beans themselves can be stored as persistent,
transactional objects. Object reference segmentation can be used, as with CORBA, to quickly locate an
EJB Home for a bean, and the EJB Home then has direct reference to its persistent EntityBeans.
Persistent Java Objects in 3 tier architectures 08/17/98 Page 14

6.2 Container Managed Persistence


When the Enterprise Bean is a persistent Java object, container management of bean transactions
removes the need to write any code to manage the data store for the bean. With GemStone/J, no mapping
code for the bean need be written or configured: a bean’s ejbLoad() method can be empty. Add EJB
declarative transactions to this and you have a persistent transactional Enterprise Bean that need know
nothing about transactions or persistence itself.

6.3 Persistent Configuration and Deployment Attributes


An Enterprise JavaBean’s meta-data (that is, the information kept in an EJB JAR file), benefits from
being persistent in GemStone/J since the objects can be accessed though the shared memory cache,
reducing VM memory use. Configuration and deployment attributes need not be read from a file or
external store as they are directly available to the EJB server in object form at runtime through the shared
object cache. Similarly, the classes of the objects themselves can be resident in the persistent Java store
where they are directly available through the GemStone/J class loader and are shared among VMs
needing them through the shared object cache.

6.4 Persistent Java Naming and Directory Service


The JNDI service can be implemented with the same simple architecture as the CORBA Naming Service
mentioned in the previous section. The JNDI root context is made a persistent object in the GemStone/J
persistent Java store and the JNDI is configured to demarcate GemStone/J transactions. Then the entire
JNDI directory becomes persistent by reachability. This reduces the amount of code required to
implement the JNDI and increases its performance and reliability.

7. Summary
We have described how the ability to use persistent Java objects can provide significant benefits to
application developers and to the performance and manageability of 3 tier applications. Many of these
benefits accrue to the infrastructure of the application server, and so to the applications that run in it,
even though many of those applications do not make explicit use of persistent Java objects. Applications
that do make explicit use of persistent Java objects can reap still more benefits, notably in the simplicity
of data modeling and in performance.

References
1. The Essential Client Server Survival Guide, Orfali, Harkey & Edwards, ISBN 0-471-15325-7 .

2. "Design issues for Persistent Java", Atkinson, Jordan, et.al.,


http://www.dcs.gla.ac.uk/pjama/pjava-pos7.pdf

3. Enterprise JavaBeans specification, www.javasoft.com/products/ejb/docs.html .

4. GemStone/J 1.1 product. Trial copy with html documentation available at www.gemstone.com .

Anda mungkin juga menyukai