The application server supports both unshareable and shareable
connections. An unshareable connection is not shared with other components
in the application. The component using this connection has full control
of this connection.
Access to a resource marked as unshareable means that
there is a one-to-one relationship between the connection handle a
component is using and the physical connection with which the handle
is associated. This access implies that every call to the getConnection
method returns a connection handle solely for the requesting user.
Typically, you must choose unshareable if you might do things to
the connection that could result in unexpected behavior occurring
in another application that is sharing the connection (for example,
unexpectedly changing the isolation level).
Marking a resource
as shareable allows for greater scalability. Instead of retrieving
a new physical connection from the connection pool for every getConnection()
invocation, the physical connection (that is, managed connection)
is shared through multiple connection handles, as long as each getConnection
request has the same connection properties. However, sharing a connection
means that each user must not do anything to the connection that could
change its behavior and disrupt a sharing partner (for example, changing
the isolation level). The user also cannot code an application that
assumes sharing to take place because it is up to the run time to
decide whether or not to share a particular connection.
Connection property requirements
To permit
sharing of connections used within the same transaction, the following
data source properties must be the same:
- Java Naming and Directory Interface (JNDI) name.
While not actually a connection property, this requirement simply
means that you can only share connections from the same data source
in the same server.
- Resource authentication
- In relational databases:
- Isolation level (corresponds to access intent policies applied
to CMP beans)
- Readonly
- Catalog
- TypeMap
For more information on sharing a connection with a CMP
bean, see the topic Sharing a connection with a CMP bean.
To
permit sharing of connections within the same transaction, the following
properties must be the same for the connection factories:
- JNDI name. While not actually a connection property, this requirement
simply means that you can only share connections from the same connection
factory in the same server.
- Resource authentication
In addition, the ConnectionSpec object that is used to
get the connection must also be the same.
Note: Java Message
Service (JMS) connections cannot be shared with non-JMS connections.
JMS
connections for the WebSphere MQ JMS Provider cannot be shareable
because they are non-transactional, and the Java™ EE Connector Architecture
(JCA) specification only allows transactional resources to be shareable.
If the res-sharing-scope is set to shareable in a JMS resource reference,
the setting will be ignored and unshareable connections will be used.
However, JMS sessions for MQ are transactional, and can be shareable.
JMS sessions are shareable by default, and APAR PK59605 provides
the ability to specify unshareable sessions.
JMS connections
for the Default Messaging Provider are different. With the Default
Messaging Provider, connections can be shareable. Sessions, on the
other hand, are not managed by a connection pool, and therefore cannot
be shareable or unshareable.
Sharing a connection with a CMP bean
The
application server allows you to share a physical connection among
a CMP bean, a BMP bean, and a JDBC application to reduce the resource
allocation or deadlock scenarios. There are several ways to ensure
that all of these entity beans and the JDBC applications are sharing
the same physical connection.
- Sharing a connection between CMP beans or methods
When
all CMP bean methods use the same access intent, they all share the
same physical connection. A different access intent policy triggers
the allocation of a different physical connection. For example, a
CMP bean has two methods; method 1 is associated with wsPessimisticUpdate intent,
whereas method 2 has wsOptimisticUpdate access intent.
Method 1 and method 2 cannot share the same physical connection within
a transaction. In other words, an XA data source is required to run
in a global transaction.
You can experience some deadlocks
from a database if both methods try to access the same table. Therefore,
sharing a connection is determined by the access intents that are
defined in the CMP methods.
- Sharing a connection between CMP and BMP beans
Remember
to first verify that the getConnection methods of both the
BMP bean and the CMP bean set the same connection properties. To match
the authentication type of the CMP bean resource, set the authentication
type of the BMP bean resource to container-managed, which is designated
in the deployment descriptor as res-auth = Container.
Additionally,
use one of the following options to ensure connection-sharing between
the bean types:
- Define the same access intent on both CMP and BMP bean methods.
Because both use the same access intent, they share the same physical
connection. The advantage to using this option is that the backend
is transparent to a BMP bean. However, this option also makes the
BMP non-portable because it uses the WebSphere® extended
API to handle the isolation level. For more information, refer
to the code example in the topic, Example: Accessing data using IBM® extended
APIs to share connections between container-managed and bean-managed
persistence beans.
- Determine the isolation level that the access intent uses on a
CMP bean method, then use the corresponding isolation level that is
specified on the resource reference to look up a data source and a
connection. This option is more of a manual process, and the isolation
level might be different from database to database. For more information
refer to the isolation level and access intent mapping table in the
topic, Access intent isolation levels and update locks, and the topic,
Isolation level and resource reference section.
- Sharing a connection between CMP and a JDBC application that
is used by a servlet or a session beanDetermine the isolation
level that the access intent uses on a CMP bean method, then use the
corresponding isolation level specified on the resource reference
to look up a data source and a connection. For more information see
the topic, Access intent isolation levels, and the topic, Isolation
level and resource reference section.
Factors that determine sharing
The
listing here is not an exhaustive one. The product might or might
not share connections under different circumstances.
- Only connections acquired with the same resource reference (resource-ref)
that specifies the res-sharing-scope as shareable are candidates for
sharing. The resource reference properties of res-sharing-scope and
res-auth and the IBM extension isolationLevel help determine if
it is possible to share a connection. IBM extension
isolationLevel is stored in IBM deployment descriptor extension
file; for example: ibm-ejb-jar-ext.xmi.
Supported configurations: For IBM extension
and binding files, the .xmi or .xml file name extension is different
depending on whether you are using a pre-Java EE 5 application or
module or a Java EE 5 or later
application or module. An IBM extension
or binding file is named ibm-*-ext.xmi or ibm-*-bnd.xmi where * is
the type of extension or binding file such as app, application, ejb-jar,
or web. The following conditions apply:
- For an application or module that uses a Java EE version prior to version 5, the file
extension must be .xmi.
- For an application or module that uses Java EE 5 or later, the file extension must
be .xml. If .xmi files are included with the application or module,
the product ignores the .xmi files.
However, a Java EE
5 or later module can exist within an application that includes pre-Java
EE 5 files and uses the .xmi file name extension.
The ibm-webservices-ext.xmi, ibm-webservices-bnd.xmi, ibm-webservicesclient-bnd.xmi, ibm-webservicesclient-ext.xmi,
and ibm-portlet-ext.xmi files continue to use
the .xmi file extensions.
sptcfg
- You can only share connections that are requested with the same
properties.
- Connection sharing only occurs between different component instances
if they are within a transaction (container- or user-initiated transaction).
- Connection sharing only occurs within a sharing boundary. Current® sharing
boundaries include Transactions and LocalTransactionContainment (LTC)
boundaries.
- Connection sharing rules within an LTC Scope:
- For shareable connections, only Connection Reuse is allowed
within a single component instance. Connection reuse occurs when
the following actions are taken with a connection: get, use, commit/rollback,
close; get, use, commit/rollback, close. Note that if you use the
LTC resolution-control of ContainerAtBoundary then no start/commit
is needed because that action is handled by the container.
The
connection returned on the second get is the same connection
as that returned on the first get (if the same properties are
used). Because the connection use is serial, only one connection
handle to the underlying physical connection is used at a time, so
true connection sharing does not take place. The term "reuse" is
more accurate.
More importantly, the LocalTransactionContainment boundary
enclosing both get actions is not complete; no cleanUp() method
is invoked on the ManagedConnection object. Therefore the second get action
inherits all of the connection properties set during the first getConnection()
call.
- Shareable connections between transactions (either container-managed
transactions (CMT), bean-managed transactions (BMT), or LTC transactions)
follow these caching rules:
- In general, setting properties on shareable connections is not
allowed because a user of one connection handle might not anticipate
a change made by another connection handle. This limitation is part
of the Java Platform, Enterprise Edition (Java EE) standard.
- General users of resource adapters can set the connection properties
on the connection factory getConnection() call by passing them in
a ConnectionSpec.
However, the properties set on the connection
during one transaction are not guaranteed to be the same when used
in the next transaction. Because it is not valid to share connections
outside of a sharing scope, connection handles are moved off of the
physical connection with which they are currently associated when
a transaction ends. That physical connection is returned to the free
connection pool. Connections are cleaned before going in the free
pool. The next time the handle is used, it is automatically associated
with an appropriate connection. The appropriateness is based on the
security login information, connection properties, and (for the JDBC
API) the isolation level specified in the extended resource reference,
passed in on the original request that returned the current handle.
Any properties set on the connection after it was retrieved are lost.
- For JDBC users, the application server provides an extension to
enable passing the connection properties through the ConnectionSpec.
Use
caution when setting properties and sharing connections in a local
transaction scope. Ensure that other components with which the connection
is shared are expecting the behavior resulting from your settings.
- You cannot set the isolation level on a shareable connection for
the JDBC API using a relational resource adapter in a global transaction.
The product provides an extension to the resource reference to enable
you to specify the isolation level. If your application requires the
use of multiple isolation levels, create multiple resource references
and map them to the same data source or connection factory.
Maximal connection sharing
To
maximize connection sharing opportunities for an application, ensure
that each component has the local transaction containment (LTC) Resolver
attribute set to ContainerAtBoundary. This
setting specifies that the component container, rather than the application
code, resolves all resource manager local transactions (RMLTs) within
the LTC scope. The container begins an RMLT when a connection is first
used within the LTC scope, and completes it automatically at the end
of the LTC scope.
See the topic, Configuring transactional deployment
attributes, for instructions on setting the transaction resolution
control and other attributes.
Connection sharing violations
There
is a new exception, the sharing violation exception, that the resource
adapter can issue whenever an operation violates sharing requirements.
Possible violations include changing connection attributes, security
settings, or isolation levels, among others. When such a mutable
operation is performed against a managed connection, the sharing violation
exception can occur when both of the following conditions are true:
- The number of connection handles associated with the managed connection
is more than one.
- The managed connection is associated with a transaction, either
local or XA.
Both the component and the J2C run time might need to
detect this sharing violation exception, depending on when and how
the managed connection becomes unshareable. If the managed connection
becomes unshareable because of an operation through the connection
handle (for example, you change the isolation level), then the component
needs to process the exception. If the managed connection becomes
unshareable without being recognized by the application server (due
to some component interaction with the connection handle), then the
resource adapter can reject the creation of a connection handle by
issuing the sharing violation exception.