Programmers Guide
Programmers Guide
3
Transaction Core Programmers Guide
TX-PG-4/4/07
T-PG-4/4/07 i
Legal Notices
JBoss Inc. makes no warranty of any kind with regard to this material, including, but not limited to, the
implied warranties of merchantability and fitness for a particular purpose. JBoss Inc. shall not be liable for
errors contained herein or for incidental or consequential damages in connection with the furnishing,
performance, or use of this material.
Java™ and J2EE is a U.S. trademark of Sun Microsystems, Inc. Microsoft® and Windows NT® are
registered trademarks of Microsoft Corporation. Oracle® is a registered U.S. trademark and Oracle9™,
Oracle9 Server™ Oracle9 Enterprise Edition™ are trademarks of Oracle Corporation. Unix is used here
as a generic term covering all versions of the UNIX® operating system. UNIX is a registered trademark in
the United States and other countries, licensed exclusively through X/Open Company Limited.
Copyright
JBoss, Home of Professional Open Source Copyright 2006, JBoss Inc., and individual contributors as
indicated by the @authors tag. All rights reserved.
See the [Link] in the distribution for a full listing of individual contributors. This copyrighted
material is made available to anyone wishing to use, modify, copy, or redistribute it subject to the terms
and conditions of the GNU General Public License, v. 2.0. This program is distributed in the hope that it
will be useful, but WITHOUT A WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU General Public License for more details. You should have received a copy of the GNU
General Public License, v. 2.0 along with this distribution; if not, write to the Free Software Foundation,
Inc., 51 Franklin Street, Fifth Floor, Boston, * MA 02110-1301, USA.
Software Version
Use, duplication, or disclosure is subject to restrictions as set forth in contract subdivision (c)(1)(ii) of the
Rights in Technical Data and Computer Software clause 52.227-FAR14.
Index ................................................................73
iv TX-PG-04/04/07
AC-PG-4/4/07 5
JBoss Transactions 4.2.3Transaction Core Programmers Guide
The Transaction Core Programmers Guide contains information on how to use JBoss
Transactions 4.2.3. This document provides a detailed look at the design and operation of the
TxCore transaction engine and the Transactional Objects for Java toolkit. It describes the
architecture and the interaction of components within this architecture.
Audience
This guide is most relevant to engineers who are responsible for administering JBoss
Transactions 4.2.3 installations. Although this guide is specifically intended for service
developers, it will be useful to anyone who would like to gain an understanding of
transactions and how they function.
Prerequisites
This guide assumes a basic familiarity with Java service development and object-oriented
programming. A fundamental level of understanding in the following areas will also be
useful:
• General understanding of the APIs, components, and objects that are present in Java
applications.
• A general understanding of the Windows and UNIX operating systems.
Organization
• Chapter 1, Overview: this chapter contains a description of the use of the TxCore
transaction engine the Transactional Object for Java classes and facilities.
• Chapter 2, Using TxCore: gives details on interfaces and classes defined by
TxCore and describes how they can be used to construct transactional applications.
• Chapter 3, General transactions issues: presents advanced issues with TxCore.
• Chapter 4, Hints and tips: illustrates some hints on the way to use TxCore
6 TX-PG-04/04/07
About This Guide
• Chapter 5, Tools: how to use the management tools shipped with TxCore.
• Chapter 6, Constructing a Transactional Object for Java application: this
chapter describes a detailed implementation of an application to illustrate various
mechanisms provided by TxCore.
• Chapter 7, Configuration options: shows configurations options of TxCore.
Documentation Conventions
Convention Description
Italic In paragraph text, italic identifies the titles of documents that are
being referenced. When used in conjunction with the Code text
described below, italics identify a variable that should be replaced
by the user with an actual value.
Bold Emphasizes items of particular importance.
Code Text that represents programming code.
Function | Function A path to a function or dialog box within an interface. For example,
“Select File | Open.” indicates that you should select the Open
function from the File menu.
( ) and | Parentheses enclose optional items in command syntax. The
vertical bar separates syntax items in a list of choices. For
example, any of the following three items can be entered in this
syntax:
Additional Documentation
In addition to this guide, the following guides are available in the JBoss Transactions 4.2.3
documentation set:
TX-PG-4/4/07 7
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Contacting Us
Questions or comments about JBoss Transactions 4.2.3 should be directed to our support
team.
8 TX-PG-04/04/07
Chapter 1
Overview
Introduction
This chapter contains a description of the use of the TxCore transaction engine and the
Transactional Objects for Java classes and facilities. The classes mentioned in this chapter
are the key to writing fault-tolerant applications using transactions. Thus, after describing
them we shall apply them in the construction of a simple application. The classes to be
described in this chapter can be found in the [Link] and
[Link] packages.
In keeping with the object-oriented view, the mechanisms needed to construct reliable
distributed applications are presented to programmers in an object-oriented manner. Some
mechanisms need to be inherited, for example, concurrency control and state management;
while other mechanisms, such as object storage and transactions, are implemented as TxCore
objects that are created and manipulated like any other object.
Note: When the manual talks about using persistence and concurrency control
facilities it assumes that the Transactional Objects for Java (TXOJ)
classes are being used. If this is not the case then the programmer is
responsible for all of these issues.
AC-PG-4/4/07 9
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Atomic
Lock LockManager
Transaction
StateManager
Apart from specifying the scopes of transactions, and setting appropriate locks within objects,
the application programmer does not have any other responsibilities: TxCore and
Transactional Objects for Java (TXOJ) guarantee that transactional objects will be registered
with, and be driven by, the appropriate transactions, and crash recovery mechanisms are
invoked automatically in the event of failures.
Persistent objects are assigned unique identifiers (instances of the Uid class), when they are
created, and this is used to identify them within the object store. States are read using the
read_committed operation and written by the write_(un)committed operations.
10 TX-PG-04/04/07
Overview
Objects are assumed to be of three possible flavours. They may simply be recoverable, in
which case StateManager will attempt to generate and maintain appropriate recovery
information for the object. Such objects have lifetimes that do not exceed the application
program that creates them. Objects may be recoverable and persistent, in which case the
lifetime of the object is assumed to be greater than that of the creating or accessing
application, so that in addition to maintaining recovery information StateManager will
attempt to automatically load (unload) any existing persistent state for the object by calling
the activate (deactivate) operation at appropriate times. Finally, objects may possess
none of these capabilities, in which case no recovery information is ever kept nor is object
activation/deactivation ever automatically attempted.
If an object is recoverable or recoverable and persistent then StateManager will invoke the
operations save_state (while performing deactivate), and restore_state (while
performing activate) at various points during the execution of the application. These
operations must be implemented by the programmer since StateManager cannot detect user
level state changes. (We are examining the automatic generation of default save_state and
restore_state operations, allowing the programmer to override this when application
specific knowledge can be used to improve efficiency.) This gives the programmer the ability
to decide which parts of an object’s state should be made persistent. For example, for a
spreadsheet it may not be necessary to save all entries if some values can simply be
recomputed. The save_state implementation for a class Example that has integer member
variables called A, B and C could simply be:
try
{
[Link](A);
[Link](B);
TX-PG-4/4/07 11
JBoss Transactions 4.2.3Transaction Core Programmers Guide
[Link](C));
}
catch (Exception e)
{
return false;
}
return true;
}
ObjectStore::read_committed UserObject::restore_state
ObjectStore::write_committed UserObject::save_state
ObjectStore::commit_state
• The object is initially passive, and is stored in the object store as an instance of the
class OutputObjectState.
12 TX-PG-04/04/07
Overview
The primary programmer interface to the concurrency controller is via the setlock
operation. By default, the runtime system enforces strict two-phase locking following a
multiple reader, single writer policy on a per object basis. However, as shown in Figure 1, by
inheriting from the Lock class it is possible for programmers to provide their own lock
implementations with different lock conflict rules to enable type specific concurrency control.
Lock acquisition is (of necessity) under programmer control, since just as StateManager
cannot determine if an operation modifies an object, LockManager cannot determine if an
operation requires a read or write lock. Lock release, however, is under control of the system
and requires no further intervention by the programmer. This ensures that the two-phase
property can be correctly maintained.
TX-PG-4/4/07 13
JBoss Transactions 4.2.3Transaction Core Programmers Guide
The LockManager class is primarily responsible for managing requests to set a lock on an
object or to release a lock as appropriate. However, since it is derived from StateManager,
it can also control when some of the inherited facilities are invoked. For example,
LockManager assumes that the setting of a write lock implies that the invoking operation
must be about to modify the object. This may in turn cause recovery information to be saved
if the object is recoverable. In a similar fashion, successful lock acquisition causes activate
to be invoked.
The code below shows how we may try to obtain a write lock on an object:
[Link]();
if ([Link]() == [Link])
{
result = true;
}
}
else
[Link]();
return result;
}
}
14 TX-PG-04/04/07
Overview
Example
The simple example below illustrates the relationships between activation, termination and
commitment:
{
. . .
O1 objct1 = new objct1(Name-A);/* (i) bind to "old" persistent object A */
O2 objct2 = new objct2(); /* create a "new" persistent object */
[Link]().begin(); /* (ii) start of atomic action */
The execution of the above code involves the following sequence of activities:
1. Creation of bindings to persistent objects; this could involve the creation of stub
objects and a call to remote objects. In the above example we re-bind to an existing
persistent object identified by Name-A, and a new persistent object. A naming
system for remote objects maintains the mapping between object names and locations
and is described in a later chapter.
2. Start of the atomic transaction.
3. Operation invocations: as a part of a given invocation the object implementation is
responsible to ensure that it is locked in read or write mode (assuming no lock
conflict), and initialised, if necessary, with the latest committed state from the object
store. The first time a lock is acquired on an object within a transaction the object’s
state is acquired, if possible, from the object store.
4. Commit of the top-level action. This includes updating of the state of any modified
objects in the object store.
5. Breaking of the previously created bindings.
TX-PG-4/4/07 15
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Most TxCore system classes are derived from the base class StateManager, which provides
primitive facilities necessary for managing persistent and recoverable objects. These facilities
include support for the activation and de-activation of objects, and state-based object
recovery. The class LockManager uses the facilities of StateManager and provides the
concurrency control required for implementing the serialisability property of atomic actions.
Consider a simple example. Assume that Example is a user-defined persistent class suitably
derived from the LockManager. An application containing an atomic transaction Trans
accesses an object (called O) of type Example by invoking the operation op1 which involves
state changes to O. The serialisability property requires that a write lock must be acquired on
O before it is modified; thus the body of op1 should contain a call to the setlock operation
of the concurrency controller:
The operation setlock, provided by the LockManager class, performs the following
functions in this case:
1. Check write lock compatibility with the currently held locks, and if allowed:
2. Call the StateManager operation activate that will load, if not done already, the
latest persistent state of O from the object store. Then call the StateManager operation
modified which has the effect of creating an instance of either RecoveryRecord or
PersistenceRecord for O depending upon whether O was persistent or not (the Lock is
a WRITE lock so the old state of the object must be retained prior to modification) and
inserting it into the RecordList of Trans.
3. Create and insert a LockRecord instance in the RecordList of Trans.
Now suppose that action Trans is aborted sometime after the lock has been acquired. Then
the rollback operation of AtomicAction will process the RecordList instance
associated with Trans by invoking an appropriate Abort operation on the various records.
16 TX-PG-04/04/07
Overview
The implementation of this operation by the LockRecord class will release the WRITE lock
while that of RecoveryRecord/PersistenceRecord will restore the prior state of O.
It is important to realise that all of the above work is automatically being performed by
TxCore on behalf of the application programmer. The programmer need only start the
transaction and set an appropriate lock; TxCore and Transactional Objects for Java take care
of participant registration, persistence, concurrency control and recovery.
TX-PG-4/4/07 17
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Chapter 2
Using TxCore
Introduction
In this section we shall describe TxCore and Transactional Objects for Java in more detail,
and show how it can be used to construct transactional applications.
State management
Object states
TxCore needs to be able to remember the state of an object for several purposes, including
recovery (the state represents some past state of the object), and for persistence (the state
represents the final state of an object at application termination). Since all of these
requirements require common functionality they are all implemented using the same
mechanism - the classes Input/OutputObjectState and Input/OutputBuffer.
OutputBuffer
public class OutputBuffer
{
public OutputBuffer ();
InputBuffer
public class InputBuffer
{
public InputBuffer ();
18 TX-PG-04/04/07
Using TxCore
The Input/OutputBuffer class maintains an internal array into which instances of the
standard Java types can be contiguously packed (unpacked) using the pack (unpack)
operations. This buffer is automatically resized as required should it have insufficient space.
The instances are all stored in the buffer in a standard form (so-called network byte order) to
make them machine independent.
OutputObjectState
class OutputObjectState extends OutputBuffer
{
public OutputObjectState (Uid newUid, String typeName);
InputObjectState
class InputObjectState extends InputBuffer
{
public OutputObjectState (Uid newUid, String typeName, byte[] b);
TX-PG-4/4/07 19
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Note: as with all TxCore classes the default object stores are pure Java
implementations; to access the shared memory and other more complex
object store implementations it is necessary to use native methods.
All of the object stores hold and retrieve instances of the class
Input/OutputObjectState. These instances are named by the Uid and Type of the
object that they represent. States are read using the read_committed operation and written
by the system using the write_uncommitted operation. Under normal operation new object
states do not overwrite old object states but are written to the store as shadow copies. These
shadows replace the original only when the commit_state operation is invoked. Normally
all interaction with the object store is performed by TxCore system components as
appropriate thus the existence of any shadow versions of objects in the store are hidden from
the programmer.
When a transactional object is committing it is necessary for it to make certain state changes
persistent in order that it can recover in the event of a failure and either continue to commit,
or rollback. When using Transactional Objects for Java, TxCore will take care of this
automatically. To guarantee ACID properties, these state changes must be flushed to the
persistence store implementation before the transaction can proceed to commit; if they are
not, the application may assume that the transaction has committed when in fact the state
changes may still reside within an operating system cache, and may be lost by a subsequent
machine failure. By default, TxCore ensures that such state changes are flushed. However,
doing so can impose a significant performance penalty on the application. To prevent
transactional object state flushes, set the
[Link] variable to OFF.
20 TX-PG-04/04/07
Using TxCore
StateManager
The TxCore class StateManager manages the state of an object and provides all of the
basic support mechanisms required by an object for state management purposes.
StateManager is responsible for creating and registering appropriate resources concerned
with the persistence and recovery of the transactional object. If a transaction is nested, then
StateManager will also propagate these resources between child transactions and their
parents at commit time.
Objects in TxCore are assumed to be of three possible basic flavours. They may simply be
recoverable, in which case StateManager will attempt to generate and maintain appropriate
recovery information for the object (as instances of the class Input/OutputObjectState)
. Such objects have lifetimes that do not exceed the application program that creates them.
Objects may be recoverable and persistent, in which case the lifetime of the object is
assumed to be greater than that of the creating or accessing application so that in addition to
maintaining recovery information StateManager will attempt to automatically load
(unload) any existing persistent state for the object by calling the activate (deactivate)
operation at appropriate times. Finally, objects may possess none of these capabilities in
which case no recovery information is ever kept nor is object activation/deactivation ever
automatically attempted. This object property is selected at object construction time and
cannot be changed thereafter. Thus an object cannot gain (or lose) recovery capabilities at
some arbitrary point during its lifetime.
TX-PG-4/4/07 21
JBoss Transactions 4.2.3Transaction Core Programmers Guide
If an object is recoverable (or persistent) then StateManager will invoke the operations
save_state (while performing deactivation), restore_state (while performing
activate) and type at various points during the execution of the application. These
operations must be implemented by the programmer since StateManager does not have
access to a runtime description of the layout of an arbitrary Java object in memory and thus
cannot implement a default policy for converting the in memory version of the object to its
passive form. However, the capabilities provided by Input/OutputObjectState make the
writing of these routines fairly simple. For example, the save_state implementation for a
class Example that had member variables called A, B and C could simply be the following:
try
{
[Link](A);
[Link](B);
[Link](C);
return true;
}
catch (IOException e)
{
return false;
}
}
In order to support crash recovery for persistent objects it is necessary for all save_state
and restore_state methods of user objects to call super.save_state and
super.restore_state.
22 TX-PG-04/04/07
Using TxCore
Note: The type method is used to determine the location in the object store
where the state of instances of that class will be saved and ultimately
restored. This can actually be any valid string. However, you should avoid
using the hash character (#) as this is reserved for special directories that
TxCore requires.
The get_uid operation of StateManager provides read only access to an object’s internal
system name for whatever purpose the programmer requires (such as registration of the name
in a name server). The value of the internal system name can only be set when an object is
initially constructed - either by the provision of an explicit parameter or by generating a new
identifier when the object is created.
The destroy method can be used to remove the object’s state from the object store. This is
an atomic operation, and therefore will only remove the state if the top-level transaction
within which it is invoked eventually commits. The programmer must obtain exclusive access
to the object prior to invoking this operation.
Since object recovery and persistence essentially have complimentary requirements (the only
difference being where state information is stored and for what purpose) StateManager
effectively combines the management of these two properties into a single mechanism. That
is, it uses instances of the class Input/OutputObjectState both for recovery and
persistence purposes. An additional argument passed to the save_state and
restore_state operations allows the programmer to determine the purpose for which any
given invocation is being made thus allowing different information to be saved for recovery
and persistence purposes.
Object models
TxCore supports two models for objects, which as we shall show affect how an objects state
and concurrency control are implemented:
• SINGLE: only a single copy of the object exists within the application; this will
reside within a single JVM, and all clients must address their invocations to this
server. This model provides better performance, but represents a single point of
failure, and in a multi-threaded environment may not protect the object from
corruption if a single thread fails.
TX-PG-4/4/07 23
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Object store
object
Server process
client
Figure 4 SINGLE object model.
• MULTIPLE: logically a single instance of the object exists, but copies of it are
distributed across different JVMs; the performance of this model is worse than the
SINGLE model, but it provides better failure isolation.
Object store
object object
Server process
client
The default model is SINGLE. The programmer can override this on a per object basis by
providing an appropriate instance of the
[Link] class at object construction.
24 TX-PG-04/04/07
Using TxCore
Note: The model can be changed between each successive instantiation of the
object, i.e., it need not be the same during the object’s lifetime.
For example:
{
ObjectName attr = new ObjectName(“SNS:myObjectName”);
[Link](ArjunaNames.StateManager_objectModel(),
[Link]);
Summary
In summary, the TxCore class StateManager manages the state of an object and provides
all of the basic support mechanisms required by an object for state management purposes.
Some operations must be defined by the class developer. These operations are: save_state,
restore_state, and type.
Invoked whenever the state of an object might need to be saved for future use - primarily for
recovery or persistence purposes. The ObjectType parameter indicates the reason that
save_state was invoked by TxCore. This enables the programmer to save different pieces
of information into the OutputObjectState supplied as the first parameter depending upon
whether the state is needed for recovery or persistence purposes. For example, pointers to
other TxCore objects might be saved simply as pointers for recovery purposes but as Uid’s
for persistence purposes. As shown earlier, the OutputObjectState class provides
convenient operations to allow the saving of instances of all of the basic types in Java. In
order to support crash recovery for persistent objects it is necessary for all save_state
methods to call super.save_state.
Note: save_state assumes that an object is internally consistent and that all
variables saved have valid values. It is the programmer's responsibility to
ensure that this is the case.
boolean restore_state (InputObjectState state, int ObjectType)
Invoked whenever the state of an object needs to be restored to the one supplied. Once again
the second parameter allows different interpretations of the supplied state. In order to support
crash recovery for persistent objects it is necessary for all restore_state methods to call
super.restore_state.
TX-PG-4/4/07 25
JBoss Transactions 4.2.3Transaction Core Programmers Guide
String type ()
The TxCore persistence mechanism requires a means of determining the type of an object as
a string so that it can save/restore the state of the object into/from the object store. By
convention this information indicates the position of the class in the hierarchy. For example,
“/StateManager/LockManager/Object”.
Caution: The type method is used to determine the location in the object store
where the state of instances of that class will be saved and ultimately
restored. This can actually be any valid string. However, you should avoid
using the hash character (#) as this is reserved for special directories that
TxCore requires.
Example
Consider the following basic Array class derived from the StateManager class (in this
example, to illustrate saving and restoring of an object’s state, the highestIndex variable is
used to keep track of the highest element of the array that has a non-zero value):
try
{
packInt(highestIndex);
/*
26 TX-PG-04/04/07
Using TxCore
* Traverse array state that we wish to save. Only save active elements
*/
return true;
}
catch (IOException e)
{
return false;
}
}
public boolean restore_state (InputObjectState os, int ObjectType)
{
if (!super.restore_state(os, ObjectType))
return false;
try
{
int i = 0;
highestIndex = [Link]();
return true;
}
catch (IOException e)
{
return false;
}
}
public String type ()
{
return "/StateManager/Array";
}
Concurrency control information within TxCore is maintained by locks. Locks which are
required to be shared between objects in different processes may be held within a lock store,
similar to the object store facility presented previously. The lock store provided with TxCore
deliberately has a fairly restricted interface so that it can be implemented in a variety of ways.
For example, lock stores are implemented in shared memory; on the Unix file system (in
several different forms); and as a remotely accessible store. More information about the
object stores available in TxCore can be found in the Appendix.
Note: as with all TxCore classes the default lock stores are pure Java
implementations; to access the shared memory and other more complex
lock store implementations it is necessary to use native methods.
TX-PG-4/4/07 27
JBoss Transactions 4.2.3Transaction Core Programmers Guide
java -D [Link]=/var/tmp/LockStore
myprogram
or
If neither of these approaches is taken, then the default location will be at the same level as
the etc directory of the installation.
LockManager
The concurrency controller is implemented by the class LockManager which provides
sensible default behaviour while allowing the programmer to override it if deemed necessary
by the particular semantics of the class being programmed. The primary programmer
interface to the concurrency controller is via the setlock operation. By default, the TxCore
runtime system enforces strict two-phase locking following a multiple reader, single writer
policy on a per object basis. Lock acquisition is under programmer control, since just as
28 TX-PG-04/04/07
Using TxCore
The LockManager class is primarily responsible for managing requests to set a lock on an
object or to release a lock as appropriate. However, since it is derived from StateManager,
it can also control when some of the inherited facilities are invoked. For example, if a request
to set a write lock is granted, then LockManager invokes modified directly assuming that
the setting of a write lock implies that the invoking operation must be about to modify the
object. This may in turn cause recovery information to be saved if the object is recoverable.
In a similar fashion, successful lock acquisition causes activate to be invoked.
TX-PG-4/4/07 29
JBoss Transactions 4.2.3Transaction Core Programmers Guide
The setlock operation must be parameterised with the type of lock required (READ /
WRITE), and the number of retries to acquire the lock before giving up. If a lock conflict
occurs, one of the following scenarios will take place:
If the lock cannot be obtained initially then LockManager will try for the specified number
of retries, waiting for the specified timeout value between each failed attempt. The default is
100 attempts, each attempt being separated by a 0.25 seconds delay; the time between retries
is specified in micro-seconds.
If a lock conflict occurs the current implementation simply times out lock requests, thereby
preventing deadlocks, rather than providing a full deadlock detection scheme. If the requested
lock is obtained, the setlock operation will return the value GRANTED, otherwise the value
REFUSED is returned. It is the responsibility of the programmer to ensure that the remainder
of the code for an operation is only executed if a lock request is granted. Below are examples
of the use of the setlock operation.
The concurrency control mechanism is integrated into the atomic action mechanism, thus
ensuring that as locks are granted on an object appropriate information is registered with the
currently running atomic action to ensure that the locks are released at the correct time. This
frees the programmer from the burden of explicitly freeing any acquired locks if they were
acquired within atomic actions. However, if locks are acquired on an object outside of the
scope of an atomic action, it is the programmer's responsibility to release the locks when
required, using the corresponding releaselock operation.
Locking policy
Unlike many other systems, locks in TxCore are not special system types. Instead they are
simply instances of other TxCore objects (the class Lock which is also derived from
StateManager so that locks may be made persistent if required and can also be named in a
simple fashion). Furthermore, LockManager deliberately has no knowledge of the semantics
of the actual policy by which lock requests are granted. Such information is maintained by
the actual Lock class instances which provide operations (the conflictsWith operation) by
which LockManager can determine if two locks conflict or not. This separation is important
in that it allows the programmer to derive new lock types from the basic Lock class and by
30 TX-PG-04/04/07
Using TxCore
LockManager ():
This constructor allows the creation of new objects, that is, no prior state is assumed to exist.
As above, this constructor allows the creation of new objects, that is, no prior state is assumed
to exist. The ObjectType parameter determines whether an object is simply recoverable
(indicated by RECOVERABLE); recoverable and persistent (indicated by ANDPERSISTENT) or
neither (NEITHER). If an object is marked as being persistent then the state of the object will
be stored in one of the object stores. The shared parameter only has meaning if ot is
RECOVERABLE; if attr is not null and the object model is SINGLE (the default behaviour)
then the recoverable state of the object is maintained within the object itself (i.e., it has no
TX-PG-4/4/07 31
JBoss Transactions 4.2.3Transaction Core Programmers Guide
external representation), otherwise an in-memory (volatile) object store is used to store the
state of the object between atomic actions.
Constructors for new persistent objects should make use of atomic actions within themselves.
This will ensure that the state of the object is automatically written to the object store either
when the action in the constructor commits or, if an enclosing action exists, when the
appropriate top-level action commits. Later examples in this chapter illustrate this point
further.
LockManager(Uid objUid):
This constructor allows access to an existing persistent object, whose internal name is given
by the objUid parameter. Objects constructed using this operation will normally have their
prior state (identified by objUid) loaded from an object store automatically by the system.
As above, this constructor allows access to an existing persistent object, whose internal name
is given by the objUid parameter. Objects constructed using this operation will normally
have their prior state (identified by objUid) loaded from an object store automatically by the
system. If the attr parameter is not null, and the object model is SINGLE (the default
behaviour), then the object will not be reactivated at the start of each top-level transaction.
32 TX-PG-04/04/07
General transaction issues
Chapter 3
General transaction
issues
Advanced transaction issues with TxCore
Atomic actions (transactions) can be used by both application programmers and class
developers. Thus entire operations (or parts of operations) can be made atomic as required by
the semantics of a particular operation. This chapter will describe some of the more subtle
issues involved with using transactions in general and TxCore in particular.
Checking transactions
In a multi-threaded application, multiple threads may be associated with a transaction during
its lifetime, i.e., the thread’s share the context. In addition, it is possible that if one thread
terminates a transaction other threads may still be active within it. In a distributed
environment, it can be difficult to guarantee that all threads have finished with a transaction
when it is terminated. By default, TxCore will issue a warning if a thread terminates a
transaction when other threads are still active within it; however, it will allow the transaction
termination to continue. Other solutions to this problem are possible, e.g., blocking the thread
which is terminating the transaction until all other threads have disassociated themselves from
the transaction context. Therefore, TxCore provides the
[Link] class, which allows the
thread/transaction termination policy to be overridden. Each transaction has an instance of
this class associated with it, and application programmers can provide their own
implementations on a per transaction basis.
When a thread attempts to terminate the transaction and there are active threads within it, the
system will invoke the check method on the transaction’s CheckedAction object. The
parameters to the check method are:
TX-PG-4/4/07 33
JBoss Transactions 4.2.3Transaction Core Programmers Guide
• list: a list of all of the threads currently marked as active within this transaction.
When check returns, the transaction termination will continue. Obviously the state of the
transaction at this point may be different from that when check was called, e.g., the
transaction may subsequently have been committed.
Statistics gathering
By default, the JBossTS does not maintain any history information about transactions.
However, by setting the [Link]
property variable to YES, the transaction service will maintain information about the number
of transactions created, and their outcomes. This information can be obtained during the
execution of a transactional application via the [Link]
class:
/**
* Returns the number of transactions (top-level and nested)
* created so far.
*/
/**
* Returns the number of nested (sub) transactions created so far.
*/
/**
* Returns the number of transactions which have terminated with
* heuristic outcomes.
*/
/**
* Returns the number of committed transactions.
*/
/**
* Returns the number of transactions which have rolled back.
*/
34 TX-PG-04/04/07
General transaction issues
for two-phase commit. However, what if there are multiple resources in the transaction? In
this case, the Last Resource Commit optimization (LRCO) comes into play. It is possible for
a single resource that is one-phase aware (i.e., can only commit or roll back, with no prepare),
to be enlisted in a transaction with two-phase commit aware resources. The coordinator treats
the one-phase aware resource slightly differently, in that it executes the prepare phase on all
other resource first, and if it then intends to commit the transaction it passes control to the
one-phase aware resource. If it commits, then the coordinator logs the decision to commit and
attempts to commit the other resources as well.
try
{
boolean success = false;
AtomicAction A = new AtomicAction();
OnePhase opRes = new OnePhase(); // used OnePhase interface
[Link]();
[Link](new LastResourceRecord(opRes));
[Link](new ShutdownRecord(ShutdownRecord.FAIL_IN_PREPARE));
[Link]();
Nested transactions
There are no special constructs for nesting of transactions: if an action is begun while another
action is running then it is automatically nested. This allows for a modular structure to
applications, whereby objects can be implemented using atomic actions within their
operations without the application programmer having to worry about the applications which
use them, i.e., whether or not the applications will use atomic actions as well. Thus, in some
applications actions may be top-level, whereas in others they may be nested. Objects written
in this way can then be shared between application programmers, and TxCore will guarantee
their consistency.
If a nested action is aborted then all of its work will be undone, although strict two-phase
locking means that any locks it may have obtained will be retained until the top-level action
commits or aborts. If a nested action commits then the work it has performed will only be
committed by the system if the top-level action commits; if the top-level action aborts then all
of the work will be undone.
The committing or aborting of a nested action does not automatically affect the outcome of
the action within which it is nested. This is application dependant, and allows a programmer
to structure atomic actions to contain faults, undo work, etc.
TX-PG-4/4/07 35
JBoss Transactions 4.2.3Transaction Core Programmers Guide
• In the case of many registered resources, the prepare operating can logically be
invoked in parallel on each resource. The disadvantage is that if an “early” resource
in the list of registered resource forces a rollback during prepare, possibly many
prepare operations will have been made needlessly.
• In the case where heuristic reporting is not required by the application, the second
phase of the commit protocol can be done asynchronously, since its success or
failure is not important.
36 TX-PG-04/04/07
General transaction issues
B
A
Figure 6 shows a typical nesting of atomic actions, where action B is nested within action A.
Although atomic action C is logically nested within action B (it had its Begin operation
invoked while B was active) because it is an independent top-level action, it will commit or
abort independently of the other actions within the structure. Because of the nature of
independent top-level actions they should be used with caution and only in situations where
their use has been carefully examined.
Top-level actions can be used within an application by declaring and using instances of the
class TopLevelTransaction. They are used in exactly the same way as other transactions.
Caution must be exercised when writing the save_state and restore_state operations
to ensure that no atomic actions are started (either explicitly in the operation or implicitly
through use of some other operation). This restriction arises due to the fact that TxCore may
invoke restore_state as part of its commit processing resulting in the attempt to execute
an atomic action during the commit or abort phase of another action. This might violate the
atomicity properties of the action being committed (aborted) and is thus discouraged.
Example
If we consider the Array example given previously, the set and get operations could be
implemented as shown below.
[Link]();
TX-PG-4/4/07 37
JBoss Transactions 4.2.3Transaction Core Programmers Guide
return result;
}
[Link]();
return elements[index];
}
else
[Link]();
return -1;
}
Transaction timeouts
By default transactions live until they are terminated by the application that created them or a
failure occurs. However, it is possible to set a timeout (in seconds) on a per transaction basis
such that if the transaction has not terminated before the timeout expires it will be
automatically rolled back.
38 TX-PG-04/04/07
General transaction issues
not be automatically timed out. Any other positive value is assumed to the timeout for the
transaction (in seconds). A value of zero is taken to be a global default timeout, which can be
provided by the property [Link].
Unless changed the default value is 60 seconds.
When a top-level transaction is created with a non-zero timeout, it is subject to being rolled
back if it has not completed within the specified number of seconds. JBossTS uses a separate
reaper thread which monitors all locally created transactions, and forces them to roll back if
their timeouts elapse. To prevent this thread from consuming application time, it only runs
periodically. The default checking period is 120000 milliseconds, but can be overridden by
setting the [Link] property
variable to another valid value, in microseconds. Alternatively, if the
[Link] is set to DYNAMIC, the
transaction reaper will wake whenever a transaction times out. This has the advantage of
terminating transactions early, but may suffer from continually rescheduling the reaper
thread.
TX-PG-4/4/07 39
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Chapter 4
On the other hand, if the constructor does not use transactions then it is possible for
inconsistencies in the system to arise. For example, if no transaction is active when the object
is created then its state will not be saved to the store until the next time the object is modified
under the control of some transaction.
[Link](0);
[Link](obj1.get_uid()); // obj2 now contains reference to obj1
[Link](true); // obj2 saved but obj1 is not
Here the two objects are created outside of the control of the top-level action A. obj1 is a
new object; obj2 an old existing object. When the remember operation of obj2 is invoked
the object will be activated and the Uid of obj1 remembered. Since this action commits the
persistent state of obj2 could now contain the Uid of obj1. However, the state of obj1
itself has not been saved since it has not been manipulated under the control of any action. In
fact, unless it is modified under the control of some action later in the application it will never
be saved. If, however, the constructor had used an atomic action the state of obj1 would have
automatically been saved at the time it was constructed and this inconsistency could not arise.
40 TX-PG-04/04/07
Hints and tips
Caution must be also exercised when writing the save_state and restore_state
operations to ensure that no transactions are started (either explicitly in the operation or
implicitly through use of some other operation). This restriction arises due to the fact that
TxCore may invoke restore_state as part of its commit processing resulting in the
attempt to execute an atomic transaction during the commit or abort phase of another
transaction. This might violate the atomicity properties of the transaction being committed
(aborted) and is thus discouraged.
In order to support crash recovery for persistent objects it is necessary for all save_state
and restore_state methods of user objects to call super.save_state and
super.restore_state.
Packing objects
All of the basic types of Java (int, long, etc.) can be saved and restored from an
Input/OutputObjectState instance by using the pack (and unpack) routines provided
by Input/OutputObjectState. However packing and unpacking objects should be
handled differently. This is because packing objects brings in the additional problems of
aliasing. That is two different object references may in actual fact point at the same item. For
example:
Here, both s1 and s2 point at the same string and a naive implementation of save_state
could end up by copying the string twice. From a save_state perspective this is simply
inefficient. However, it makes restore_state incorrect since it would unpack the two
strings into different areas of memory destroying the original aliasing information. The
current version of TxCore will pack and unpack separate object references.
TX-PG-4/4/07 41
JBoss Transactions 4.2.3Transaction Core Programmers Guide
The examples throughout this manual have always derived user classes from LockManager.
The reasons for this are twofold. Firstly, and most importantly, the serialisability constraints
of atomic actions require it, and secondly it reduces the need for programmer intervention.
However, if only access to TxCore's persistence and recovery mechanisms is required, direct
derivation of a user class from StateManager is possible.
Classes derived directly from StateManager must make use of its state management
mechanisms explicitly (these interactions are normally undertaken by LockManager). From
a programmer's point of view this amounts to making appropriate use of the operations
activate, deactivate and modified, since StateManager's constructors are
effectively identical to those of LockManager.
boolean activate ()
boolean activate (String storeRoot)
Activate loads an object from the object store. The object’s UID must already have been
set via the constructor and the object must exist in the store. If the object is successfully read
then restore_state is called to build the object in memory. Activate is idempotent so
that once an object has been activated further calls are ignored. The parameter represents the
root name of the object store to search for the object. A value of null means use the default
store.
boolean deactivate ()
boolean deactivate (String storeRoot)
The inverse of activate. First calls save_state to build the compacted image of the
object which is then saved in the object store. Objects are only saved if they have been
modified since they were activated. The parameter represents the root name of the object
store into which the object should be saved. A value of null means use the default store.
void modified ()
Must be called prior to modifying the object in memory. If it is not called the object will not
be saved in the object store by deactivate.
42 TX-PG-04/04/07
Tools
Chapter 5
Tools
Introduction
This chapter explains how to start and use the tools framework and what tools are available.
Windows:
Double click on the ‘Start Tools’ link in the JBoss Transaction Service program group in the
start menu.
UNIX:
Once you have done this the tools window will appear. This is the launch area for all of the
tools shipped with the JBoss Transaction Service. At the top of the window you will notice a
menu bar (see Figure 7).
Open JMX Browser – this displays the JMX browser window (see Using the JMX Browser
for more information on how to use the JMX browser).
TX-PG-4/4/07 43
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Open Object Store Browser – this displays the JBossTS Object Store browser window (see
Using the Object Store Browser for more information on how to use the Object Store
browser).
Settings – this option opens the settings dialog which lets you configure the different tools
available.
Exit – this closes the tools window and exits the application, any unsaved/unconfirmed
changes will be lost.
Open – this opens a performance window – see the section named ‘Using the Performance
Tool’ for more information on the performance tool.
Close All – this closes all of the currently open performance windows – see the section
named ‘Using the Performance Tool’ for more information on the performance tool.
Cascade Windows – this arranges the windows in a diagonal line to you find a specific
window.
1. xxxxxx – For each window currently visible an extra menu option will be available here.
Selecting this menu option will bring the associated window to the front of the desktop.
About – this displays the about window which displays the product information.
44 TX-PG-04/04/07
Tools
The performance information is displayed via a multi-series graph. To view this graph
simply open a performance window by selecting Performance > Open (see Figure 8).
This window contains a multi-series graph which can display the following information:
• Number of transactions.
• Number of committed transactions.
• Number of aborted transactions.
• Number of nested transactions.
• Number of heuristics raised.
To turn these series on and off simply select the menu option from the series menu:
When series are turned on they appear in the legend at the bottom of the graph. The colour
next to the series name (e.g. Transactions Created) is the colour of the line representing that
data.
The data shown is graphed against time. The Y-axis represents the number of transactions
and the X-axis represents time.
TX-PG-4/4/07 45
JBoss Transactions 4.2.3Transaction Core Programmers Guide
At any point the sampling of data can be stopped and restarted using the ‘Sampling’ menu
and the data currently visible in the graph can be saved to a Comma Separate Values (CSV)
file for importing the data into a spreadsheet application using the ‘Save to .csv’ menu option
from the ‘Data’ menu.
The window is made up of two main sections: the details panel and the MBean panel. The
MBean panel displays the MBeans exposed by the MBean server. These are grouped by
domain name. The details panel displays information about the currently selected MBean.
To select an MBean just left-click it with the mouse and it will become highlighted. The
information displayed in the details panel is as follows (see Figure 10 for an example):
There is also a View link which when clicked displays the attributes and operations exposed
by this MBean. From there you can view readable attributes, alter writeable attributes and
invoke operations.
46 TX-PG-04/04/07
Tools
At any point you can click the button to refresh the attribute values. If an
exception occurs while retrieving the value of an attribute the exception will be displayed in
place of the attributes value.
You can also invoke operations upon an MBean. A list of operations exposed by an MBean
is displayed below the attributes list. To invoke an operation simply select it from the list and
click the button. If the operation requires parameters a further window will be
displayed, from this window you must specify values for each of the parameters required (see
Figure 12). You specify parameter values in the same way as you specify JMX attribute
values. Once you have specified a value for each of the parameters click the Invoke button to
perform the invocation.
Once the method invocation has completed its return value will be displayed.
TX-PG-4/4/07 47
JBoss Transactions 4.2.3Transaction Core Programmers Guide
48 TX-PG-04/04/07
Tools
Object Store
Hierarchy
Object Details
• Objet Store Roots – this is a pull down of the currently available object store roots.
Selecting an option from the list will repopulate the hierarchy view with the contents
of the selected root.
• Object Store Hierarchy – this is a tree which shows the current object store
hierarchy. Selecting a node from this tree will display the objects stored in that
location.
TX-PG-4/4/07 49
JBoss Transactions 4.2.3Transaction Core Programmers Guide
• Objects – this is a list of icons which represent the objects stored in the selected
location.
• Object Details – this shows information about the currently selected object (only if
the object’s type is known to the state viewer repository see Writing an OSV for
information on how to write a object state viewers).
Writing an OSV
Writing an OSV plugin allows you to extend the capabilities of the Object Store browser to
show the state of user defined abstract records. An OSV plug-in is simply a class which
implements the interface:
[Link]
It must be packaged in a JAR within the plugins directory. This example shows how to create
an OSV plugin for an abstract record subclass which looks as follows:
.....
try
{
50 TX-PG-04/04/07
Tools
_value = [Link]();
}
catch ([Link] e)
{
returnValue = false;
}
return returnValue;
}
try
{
[Link](_value);
}
catch ([Link] e)
{
returnValue = false;
}
return returnValue;
}
}
When this abstract record is viewed in the object store browser it would be nice to see the
current value. This is easy to do as we can read the state into an instance of our abstract
record and call getValue(). The following is the object store browser plug-in source code:
/**
* An entry has been selected of the type this viewer is registered
against.
*
* @param os
* @param type
* @param uid
* @param entry
* @param statePanel
TX-PG-4/4/07 51
JBoss Transactions 4.2.3Transaction Core Programmers Guide
* @throws ObjectStoreException
*/
public void entrySelected(ObjectStore os,
String type,
Uid uid,
ObjectStoreViewEntry entry,
StatePanel statePanel)
throws ObjectStoreException
{
SimpleRecord rec = new SimpleRecord();
/**
* Get the type this state viewer is intended to be registered against.
* @return
*/
public String getType()
{
return “/StateManager/AbstractRecord/SimpleRecord”;
}
}
In this example we read the state from the object store and use the value returned by
getValue() to put an entry into the state panel table. The getType() method returns the
type this plug-in is to be registered against.
To add this plug-in to the object store browser it is necessary to package it into a JAR (Java
Archive) file with a name that is prefixed with 'osbv-'. The JAR file must contain certain
information within the manifest file so that the object store browser knows which classes are
plug-ins. All of this can be performed using an Apache ANT ([Link]
script, as follows:
52 TX-PG-04/04/07
<jar jarfile="[Link]">
<fileset dir="build" includes="*.class”/>
<manifest>
<section name="arjuna-tools-objectstorebrowser">
<attribute name="plugin-classname-1" value="
SimpleRecordOSVPlugin "/>
</section>
</manifest>
</jar>
Once the JAR has been created with the correct information in the manifest file it just needs
to be placed in the 'bin/tools/plugins' directory.
TX-PG-4/4/07 53
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Chapter 6
Constructing a
Transactional Objects for
Java application
Application construction
Although these two phases may be performed in parallel and by a single person, we shall
refer to the first step as the job of the class developer and the second as the job of the
applications developer. The class developer will be concerned about defining appropriate
save_state and restore_state operations for the class, setting appropriate locks in
operations, and invoking the appropriate TxCore class constructors. The applications
developer will be more concerned with defining the general structure of the application,
particularly with regard to the use of atomic actions.
This chapter illustrates the points made in previous sections by outlining a simple application:
in this case a simple FIFO Queue class for integer values will be developed. The
implementation of the Queue will be with a doubly linked list structure, and it will be
implemented as a single object. We shall be using this example throughout the rest of this
manual to help illustrate the various mechanisms provided by TxCore. While this is an
unrealistic example application it enables all of the TxCore modifications to be described
without requiring in depth knowledge of the application code.
In the rest of this chapter we shall assume that the application is not distributed. If this is not
the case, then context information must be propagated either implicitly or explicitly.
Queue description
The queue is a traditional FIFO queue, where elements are added to the front and removed
from the back. The operations provided by the queue class allow the values to be placed on to
the queue (enqueue) and to be removed from it (dequeue), and it is also possible to change
or inspect the values of elements in the queue. In this example implementation, an array is
54 TX-PG-04/04/07
Constructing a Transactional Objects for Java application
used to represent the queue. A limit of QUEUE_SIZE elements has been imposed for this
example.
The Java interface definition of this simple queue class is given below:
public static final int QUEUE_SIZE = 40; // maximum size of the queue
numberOfElements = 0;
}
public TransactionalQueue ()
{
super([Link]);
numberOfElements = 0;
try
{
AtomicAction A = new AtomicAction();
TX-PG-4/4/07 55
JBoss Transactions 4.2.3Transaction Core Programmers Guide
The use of an atomic action within the constructor for a new object follows the guidelines
outlined earlier and ensures that the object’s state will be written to the object store when the
appropriate top level atomic action commits (which will either be the action A or some
enclosing action active when the TransactionalQueue was constructed). The use of
atomic actions in a constructor is simple: an action must first be declared and its begin
operation invoked; the operation must then set an appropriate lock on the object (in this case a
WRITE lock must be acquired), then the main body of the constructor is executed. If this is
successful the atomic action can be committed, otherwise it is aborted.
The destructor of the queue class is only required to call the terminate operation of
LockManager
try
{
[Link](numberOfElements);
if (numberOfElements > 0)
{
for (int i = 0; i < numberOfElements; i++)
[Link](elements[i]);
}
return true;
}
catch (IOException e)
56 TX-PG-04/04/07
Constructing a Transactional Objects for Java application
{
return false;
}
}
public boolean restore_state (InputObjectState os, int ObjectType)
{
if (!super.restore_state(os, ObjectType))
return false;
try
{
numberOfElements = [Link]();
if (numberOfElements > 0)
{
for (int i = 0; i < numberOfElements; i++)
elements[i] = [Link]();
}
return true;
}
catch (IOException e)
{
return false;
}
}
Because the Queue class is derived from the LockManager class, the operation type should
be:
enqueue/dequeue operations
If the operations of the queue class are to be coded as atomic actions, then the enqueue
operation could have the structure given below (the dequeue operation would be similarly
structured):
try
{
[Link](0);
TX-PG-4/4/07 57
JBoss Transactions 4.2.3Transaction Core Programmers Guide
{
[Link]();
throw new UnderFlow();
}
}
if (res)
[Link](true);
else
{
[Link]();
throw new Conflict();
}
}
catch (Exception e1)
{
throw new QueueError();
}
}
queueSize
The implementation of queueSize is shown below:
try
{
[Link](0);
if (size != -1)
[Link](true);
else
{
[Link]();
return size;
}
inspectValue/setValue operations
The implementation of inspectValue is shown below. setValue is similar, and not
shown.
58 TX-PG-04/04/07
Constructing a Transactional Objects for Java application
try
{
[Link]();
if (res)
[Link](true);
else
{
[Link]();
throw new Conflict();
}
}
catch (Exception e1)
{
throw new QueueError();
}
return val;
}
The client
Rather than show all of the code for the client, we shall concentrate on a representative
portion. Before invoking operations on the object, the client must obviously first bind to it. In
the local case this simply requires the client to create an instance of the object.
TX-PG-4/4/07 59
JBoss Transactions 4.2.3Transaction Core Programmers Guide
Before invoking one of the queue’s operations, the client starts a transaction. The queueSize
operation is shown below:
try
{
[Link](0);
try
{
size = [Link]();
}
catch (Exception e)
{
}
if (size >= 0)
{
[Link](true);
Comments
Since the queue object is persistent, then the state of the object will survive any failures of the
node on which it is located. The state of the object that will survive is that produced by the
last top-level committed atomic action performed on the object. If it is the intention of an
application to perform two enqueue operations atomically, for example, then this can be
done by nesting the enqueue operations in another enclosing atomic action. In addition,
concurrent operations on such a persistent object will be serialised, thereby preventing
inconsistencies in the state of the object. However, since the elements of the queue objects are
not individually concurrency controlled, certain combinations of concurrent operation
invocations will be executed serially, whereas logically they could be executed concurrently.
For example, modifying the states of two different elements in the queue. In the next section
we address some of these issues.
60 TX-PG-04/04/07
Configuration options
Chapter 7
Configuration options
Options
The following table shows the configuration features, with default values shown in italics.
More details about each option can be found in the relevant sections of this document.
TX-PG-4/4/07 61
JBoss Transactions 4.2.3Transaction Core Programmers Guide
62 TX-PG-04/04/07
Object store implementations
Appendix A
Object store
implementations
The ObjectStore
In this appendix we shall examine the various TxCore object store implementations and give
guidelines as to how other implementations may be created and plugged into an application.
This release of JBossTS contains several different implementations of a basic object store.
Each serves a particular purpose and is generally optimised for that purpose. All of the
implementations are derived from the ObjectStore interface. This defines the minimum
operations which must be provided in order for an object store implementation to be used by
JBossTS. The default object store implementation can be overridden at runtime by setting the
[Link] property variable to one of
the types described below.
/*
* This is the base class from which all object store types are derived.
* Note that because object store instances are stateless, to improve
* efficiency we try to only create one instance of each type per process.
* Therefore, the create and destroy methods are used instead of new
* and delete. If an object store is accessed via create it *must* be
* deleted using destroy. Of course it is still possible to make use of
* new and delete directly and to create instances on the stack.
*/
TX-PG-4/4/07 63
JBoss Transactions 4.2.3Transaction Core Programmers Guide
JBossTS programmers need not usually interact with any of the object store implementations
directly other than possibly to create them in the first place (even this is not necessary if the
default store type is used as JBossTS will create stores as necessary). All stores manipulate
instances of the class ObjectState which are named using a type (via the object's type()
operation) and a Uid. For atomic actions purposes object states in the store can be principally
in two distinct states: OS_COMMITTED, and OS_UNCOMMITTED. An object state starts
in the OS_COMMITTED state but when modified under the control of an atomic action a
new second object state may be written that is in the OS_UNCOMMITTED state. If the
action commits this second object state replaces the original and becomes
OS_COMMITTED. If the action aborts, this second object state is simply discarded. All of
the implementations provided with this release handle these state transitions by making use of
shadow copies of object states, however, any other implementation that maintains this
abstraction is permissible. Object states may become hidden (and thus inaccessible) under the
control of the crash recovery system.
Browsing of the contents of a store is possible through the allTypes and allObjUids
operations. allTypes returns an InputObjectState containing all of the type names of all
objects in a store, terminated by a null name. allObjUids returns an
InputObjectState that contains all of the Uids of all objects of a given type terminated
by the special [Link]().
64 TX-PG-04/04/07
Object store implementations
Common functionality
In addition to the features mentioned earlier all of the supplied persistent object stores obey
the following rules:
• Each object state is stored in its own file that is named using the Uid of the object.
• The type of an object (as given by the type() operation) determines the directory
into which the object is placed.
• All of the stores have a common root directory that is determined when JBossTS is
configured. This directory name is automatically prepended to any store specific
root information.
• All stores also have the notion of a localised root directory that is automatically
prepended to the type of the object to determine the ultimate directory name. The
localised root name is specified when the store is created. By default the localised
root name is defaultStore.
If overriding the object store implementation, the type of this object store is
“ShadowingStore”.
No file-level locking
Since transactional objects are concurrency controlled through LockManager, it is not
necessary to impose additional locking at the file level, as the basic ShadowingStore
implementation does. Therefore, the default object store implementation for JBossTS,
TX-PG-4/4/07 65
JBoss Transactions 4.2.3Transaction Core Programmers Guide
If overriding the object store implementation, the type of this object store is
“ShadowNoFileLockStore”.
If overriding the object store implementation, the type of this object store is “HashedStore”.
When using the JDBC object store, the application must provide an implementation of the
following interface, located in the [Link] package:
The implementation of this class is responsible for providing the Connection which the
JDBC ObjectStore will use to save and restore object states:
• getConnection: returns the Connection to use. This method will be called whenever
a connection is required and the implementation should use whatever policy is
necessary for determining what connection to return. This method need not return
the same Connection instance more than once.
• putConnection: this method will be called to return one of the Connections acquired
from getConnection. Connections are returned if any errors occur when using them.
• initialise: this can be used to pass additional arbitrary information to the
implementation.
66 TX-PG-04/04/07
Object store implementations
The JDBC object store will initially request the number of Connections defined in the
[Link] property and will use no more than
defined in the [Link] property.
If overriding the object store implementation, the type of this object store is “JDBCStore”.
A JDBC object store can be used for managing the transaction log. In this case, the
transaction log implementation should be set to “JDBCActionStore” and the JDBCAccess
implementation must be provided via the
[Link] property variable. In this
case, the default table name is JBossTSTxTable.
Note: It is possible to use the same JDBCAccess implementation for both the
user object store and also the transaction log.
If overriding the object store implementation, the type of this object store is “CachedStore”.
• [Link] sets
the number of internal stores to hash the states over. The default value is 128.
• [Link] is
the maximum size the cache can reach before a flush is triggered. The default is
10240 bytes.
• [Link]
tems is the maximum number of removed items that the cache can contain before a
flush is triggered. By default, calls to remove a state that is in the cache will simply
remove the state from the cache, but leave a blank entry (rather than remove the
entry immediately, which would affect the performance of the cache). When
triggered, these entries are removed from the cache. The default value is twice the
size of the hash.
• [Link]
s is the maximum number of items that are allowed to build up in the cache before it
is flushed. The default value is 100.
TX-PG-4/4/07 67
JBoss Transactions 4.2.3Transaction Core Programmers Guide
• [Link]
od sets the time in milliseconds for periodically flushing the cache. The default is
120 seconds.
• [Link]
determines whether flushes of the cache are sync-ed to disk. The default is OFF. To
enable, set to ON.
68 TX-PG-04/04/07
Class definitions
Appendix B
Class definitions
Introduction
This appendix contains an overview of those classes that the application programmer will
typically use. The aim of this appendix is to provide a quick reference guide to these classes
for use when writing applications in TxCore. For clarity only the public and protected
interfaces of the classes will be given.
Class library
LockManager
public class LockResult
{
public static final int GRANTED;
public static final int REFUSED;
public static final int RELEASED;
};
TX-PG-4/4/07 69
JBoss Transactions 4.2.3Transaction Core Programmers Guide
StateManager
public class ObjectStatus
{
public static final int PASSIVE;
public static final int PASSIVE_NEW;
public static final int ACTIVE;
public static final int ACTIVE_NEW;
};
Input/OutputObjectState
class OutputObjectState extends OutputBuffer
{
public OutputObjectState (Uid newUid, String typeName);
70 TX-PG-04/04/07
Class definitions
Input/OutputBuffer
public class OutputBuffer
{
public OutputBuffer ();
Uid
public class Uid implements Cloneable
{
public Uid ();
TX-PG-4/4/07 71
JBoss Transactions 4.2.3Transaction Core Programmers Guide
AtomicAction
public class AtomicAction
{
public AtomicAction ();
HeuristicHazard,TransactionRolledBack;
public void rollback () throws SystemException, NoTransaction;
public Control control () throws SystemException, NoTransaction;
public Status get_status () throws SystemException;
/* Allow action commit to be supressed */
public void rollbackOnly () throws SystemException, NoTransaction;
72 TX-PG-04/04/07
Index
Index
ArjunaTS Nested top-level transactions .................... 36
advanced programming ........................... 9 Nested transactions ................................... 35
class hierarchy ....................................... 15 Object identity..................................... 10, 23
object models ......................................... 23 Object serialisation.................................... 41
Asynchronous commit .............................. 36 Object state representation........................ 10
Asynchronous prepare .............................. 36 Object storage ........................................... 10
AtomicTransaction.................................... 14 Object store
Checked transactions ................................ 33 further information ................................ 20
CheckedAction class ..................... 33 overview ................................................ 20
Concurrency control policy....................... 30 selecting ................................................. 21
Configurable options................................. 61 Object store types
Core Classes default implementation .......................... 65
Buffer ..................................................... 71 HashedStore........................................... 66
Lock ....................................................... 31 ShadowingStore..................................... 65
LockManager......................................... 29 ShadowNoFileLockStore....................... 66
ObjectState................................. 19, 70, 71 Object types .............................................. 21
ObjectStore ............................................ 20 OutputBuffer ............................................. 18
StateManager......................................... 21 overview ................................................ 18
Crash recovery OutputObjectState..................................... 19
save_state and restore_state. 12, 22, 25, 41 overview ................................................ 19
Creating objects ........................................ 31 Persistent object lifecycle ......................... 12
Destroying objects .................................... 31 Persistent state........................................... 10
Identifying objects .................................... 10 issues...................................................... 41
InputBuffer................................................ 18 Property variables
overview ................................................ 18 ASYNC_COMMIT ............................... 36
InputObjectState ....................................... 19 ASYNC_PREPARE .............................. 36
overview ................................................ 19 ENABLE_STATISTICS ....................... 34
Lifecycle of a persistent object ................. 12 HASHED_DIRECTORIES ................... 66
Lock store JDBC2_USER_DB_ACCESS............... 67
further information ................................ 27 LOCKSTORE_DIR ................................ 28
implementations..................................... 13 LOCKSTORE_TYPE.............................. 28
overview ................................................ 27 OBJECTSTORE_SYNC......................... 20
selecting ................................................. 28 OBJECTSTORE_TYPE.................. 21, 63
LockManager ...................................... 13, 28 OTS_TX_REAPER_MODE ................. 39
Lock Conflicts ....................................... 30 OTS_TX_REAPER_TIMEOUT ........... 39
locking policy ........................................ 30 releaselock................................................. 30
releaselock ............................................. 30 restore_state .................................. 22, 25, 41
setlock.............................................. 28, 30 Example ................................................. 27
Examples ............................................ 30 super.restore_state ............... 12, 22, 25, 41
TX-PG-4/4/07 73
JBoss Transactions 4.2.3Transaction Core Programmers Guide
74 TX-PG-04/04/07