Now that our classes have been enhanced, their instances can be
stored in a datastore. We now examine how an application establishes a
connection with a datastore and executes operations within a
transaction. We begin to write software that makes direct use of the JDO
interfaces. All JDO interfaces used by an application are defined in the
javax.jdo
package.
JDO has an interface called PersistenceManager
that has a connection with
a datastore. A PersistenceManager
has
an associated instance of the JDO Transaction
interface used to control the
start and completion of a transaction. The Transaction
instance is acquired by calling
currentTransaction( )
on the PersistenceManager
instance.
A PersistenceManagerFactory
is used to configure and acquire a PersistenceManager
. Methods in the PersistenceManagerFactory
are used to set
properties that control the behavior of the PersistenceManager
instances acquired from
the factory. Therefore, the first step performed by a JDO application
is the acquisition of a PersistenceManagerFactory
instance. To get
this instance, call the following static method of the JDOHelper
class:
static PersistenceManagerFactory getPersistenceManagerFactory(Properties props);
The Properties
instance can
be populated programmatically or by loading property values from a
property file. Example 1-6
lists the contents of the property file we will use in our Media Mania
application. The PersistenceManagerFactoryClass
property on line [1]
specifies which JDO implementation we are using by providing the name
of the implementation’s class that implements the PersistenceManagerFactory
interface. In this
case, we specify the class defined in Sun’s JDO reference
implementation. Other properties listed in Example 1-6 include the
connection URL used to connect to a particular datastore and a
username and password, which may be necessary to establish a
connection to the datastore
Example 1-6. Contents of jdo.properties
javax.jdo.PersistenceManagerFactoryClass=com.sun.jdori.fostore.FOStorePMF [1]
javax.jdo.option.ConnectionURL=fostore:database/fostoredb
javax.jdo.option.ConnectionUserName=dave
javax.jdo.option.ConnectionPassword=jdo4me
javax.jdo.option.Optimistic=false
The format of the connection URL depends on the particular
datastore being accessed. The JDO reference implementation has its own
storage facility called File Object Store (FOStore). The ConnectionURL
property in Example 1-6 specifies that the
datastore is located in the database directory, which is located in our
project’s root directory. In this case, we have
provided a relative path; it is also possible to provide an absolute
path to the datastore. The URL specifies that the FOStore datastore
files will have a name prefix of fostoredb.
If you are using a different implementation, you will need to provide different values for these properties. You may also need to provide values for additional properties. Check with your implementation’s documentation to determine the properties that are necessary.
To use FOStore we must first create a datastore. The program in
Example 1-7 creates a
datastore using the jdo.properties file; all applications use
this property file. Line [1] loads
the properties from jdo.properties into a Properties
instance. The program adds the com.sun.jdori.option.ConnectionCreate
property on line [2] to indicate that
the datastore should be created. Setting it to true
instructs the implementation to create
the datastore. We then call getPersistenceManagerFactory(
)
on line [3] to acquire
the PersistenceManagerFactory
. Line
[4] creates a PersistenceManager
.
To complete the creation of the datastore, we must also begin
and commit a transaction. The PersistenceManager
method currentTransaction(
)
is called on line [5] to
access the Transaction
instance
associated with the PersistenceManager
. The Transaction
methods begin( )
and
commit( )
are called
on lines [6] and [7] to start and commit a transaction. When you
execute this application, a FOStore datastore is created in the
database directory. Two files are
created: fostore.btd and
fostore.btx.
Example 1-7. Creating a FOStore datastore
package com.mediamania; import java.io.FileInputStream; import java.io.InputStream; import java.util.Properties; import javax.jdo.JDOHelper; import javax.jdo.PersistenceManagerFactory; import javax.jdo.PersistenceManager; import javax.jdo.Transaction; public class CreateDatabase { public static void main(String[] args) { create( ); } public static void create( ) { try { InputStream propertyStream = new FileInputStream("jdo.properties"); Properties jdoproperties = new Properties( ); jdoproperties.load(propertyStream); [1] jdoproperties.put("com.sun.jdori.option.ConnectionCreate", "true"); [2] PersistenceManagerFactory pmf = JDOHelper.getPersistenceManagerFactory(jdoproperties); [3] PersistenceManager pm = pmf.getPersistenceManager( ); [4] Transaction tx = pm.currentTransaction( ); [5] tx.begin( ); [6] tx.commit( ); [7] } catch (Exception e) { System.err.println("Exception creating the database"); e.printStackTrace( ); System.exit(-1); } } }
The JDO reference implementation provides this programmatic means to create a database. Most databases provide a utility separate from JDO for creating a database. JDO does not define a standard, vendor-independent interface for creating a database. Creation of a datastore is always datastore-specific. This program illustrates how it is done using the FOStore datastore.
In addition, when you are using JDO with a relational database, there is often an additional step of creating or mapping to an existing relational schema. The procedure to follow for establishing a schema that corresponds with your JDO object model is implementation-specific. You should examine the documentation of the implementation you are using to determine the necessary steps.
Get Java Data Objects now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.