10.6 Advanced Topics
There are a few advanced identity topics, which we will consider in
this section.
10.6.1 Choosing an Identity Type
If you are not mapping your JDO object model onto an existing
relational schema and you are using an implementation that supports
both datastore and application identity, you frequently have the
freedom to choose the form of identity. Datastore identity is the
logical choice if there is not a natural primary key to identify
instances of the class. It is also useful if you prefer to have the
JDO implementation generate a unique identity value. Datastore
identity also requires less development work on your part. But for
some entities being modeled, a primary key is the most suitable
solution because of a natural primary-key value that is used to
identify the data.
The primary difference between datastore and application identity in
your persistent class is the need to define equals(
)
and hashCode(
)
methods for your persistent classes that use application identity.
The only other difference is the specification of the identity type
in your metadata. You can develop a persistent class and define an
application identity class for it, but then in the metadata you could
switch between datastore and application identity. If you do change
the identity in the metadata, you need to enhance your classes again,
as the enhanced class contains identity-specific information.
10.6.2 Using Identity Versus a Query
If you want to have the flexibility of changing the type of identity
used for a persistent class, you should insulate your applications
from the particular identity type you choose. When you access an
instance with application identity, you initialize an instance of the
application identity class with values for the primary-key fields and
call getObjectById( ).
As an alternative to getObjectById( ), you could
execute a Query, where the filter tests the
equality of query parameters with fields in the class. Such a query
will work regardless of whether the class uses datastore or
application identity. You could define a method for this purpose,
possibly a static method of your persistent class. It would have a
parameter for each field needed to identify an instance and the
PersistenceManager to use. Internally, the method
could issue a query, or, if you eventually decide to use application
identity, it could call getObjectById( ). Be
aware, though, that calling getObjectById( ) will
likely perform better than a query.
10.6.3 Identity Across PersistenceManagers
Under some circumstances, you can use identity instances across
different PersistenceManager instances from the
same or different implementations. For example, when using multiple
PersistenceManager instances retrieved from the
same PersistenceManagerFactory, you can use the
following code to get an instance in a
PersistenceManager (referenced by the
pm variable) with the same identity as an instance
from a different PersistenceManager:
pm.getObjectById(JDOHelper.getObjectId(obj), validate);
If multiple PersistenceManager instances (which
have been returned by the same
PersistenceManagerFactory instance) have their own
copy of the same persistent instance in their cache, all the identity
instances that are returned by calls to getObjectId(
) return true to equals(
), since they all refer to the same persistent object, even
though the identity instances were acquired from distinct copies of
the same persistent instance.
You can use getObjectById( ) only for instances of
persistent classes using application identity when you are working
with PersistenceManager instances of different JDO
implementations. Since each implementation has its own representation
for datastore identity, you cannot pass a datastore identity value
from one implementation to a PersistenceManager of
a different implementation in a call to getObjectById(
).
|