Mis favoritos | Español | Acceder

Uso de JDO con App Engine

Objetos de datos Java (JDO) es una interfaz estándar para almacenar objetos que contienen datos en una base de datos. El estándar define interfaces para la anotación de objetos Java, la recuperación de objetos a través de consultas y la interacción con una base de datos a través de transacciones. Una aplicación que utiliza la interfaz JDO puede funcionar con diferentes tipos de bases de datos sin utilizar un código específico de bases de datos, incluidas bases de datos relacionales, bases de datos jerárquicas y bases de datos de objetos. Al igual que con otros estándares de interfaz, JDO permite que tu aplicación migre fácilmente entre diferentes soluciones de almacenamiento.

El SDK de Java de App Engine incluye una implementación de JDO 2.3 para el almacén de datos de App Engine. La implementación está basada en DataNucleus Access Platform, la implementación de referencia de software libre para JDO 2.3.

Para obtener más información sobre JDO, consulta la documentación de Access Platform 1.1. En concreto, consulta "JDO Mapping" (Asignación de JDO) y "JDO API" (API JDO).

Configuración de JDO

Para utilizar JDO y acceder al almacén de datos, una aplicación de App Engine necesita lo siguiente:

  • Los JAR del complemento de App Engine de DataNucleus y de JDO deben estar en el directorio war/WEB-INF/lib/ de la aplicación.
  • Un archivo de configuración llamado jdoconfig.xml debe estar en el directorio war/WEB-INF/classes/META-INF/ de la aplicación, junto con configuración que indica a JDO el uso del almacén de datos de App Engine.
  • El proceso de compilación del proyecto debe realizar un paso de "mejora" de la post-compilación en las clases de datos compiladas para asociarlas a la implementación de JDO.

Si utilizas el complemento de Google para Eclipse, debes tener en cuenta estos tres aspectos. El nuevo asistente de proyecto guarda los JAR de App Engine de DataNucleus y de JDO en la ubicación correcta y crea el archivo jdoconfig.xml. El proceso de compilación realiza el paso de "mejora" de forma automática.

Si utilizas Apache Ant para crear tu proyecto, puedes utilizar una tarea de Ant incluida en el SDK para realizar el paso de mejora. Si configuras tu proyecto, debes copiar los JAR y crear el archivo de configuración. Para obtener más información sobre la tarea de Ant, consulta Uso de Apache Ant.

Copia de los JAR

Los JAR del almacén de datos y de JDO se incluyen en el SDK de Java de App Engine. Los puedes encontrar en el directorio appengine-java-sdk/lib/user/orm/.

Copia los JAR en el directorio war/WEB-INF/lib/ de tu aplicación.

Asegúrate de que el JAR appengine-api.jar también esté en el directorio war/WEB-INF/lib/. (Es posible que ya lo hayas copiado al crear el proyecto). El complemento de DataNucleus de App Engine utiliza este JAR para acceder al almacén de datos.

Creación del archivo jdoconfig.xml

La interfaz JDO necesita un archivo de configuración llamado jdoconfig.xml en el directorio war/WEB-INF/classes/META-INF/ de la aplicación. Puedes crear este archivo directamente en esta ubicación o copiarlo del directorio de origen durante el proceso de compilación.

Crea el archivo con el contenido que se muestra a continuación:

<?xml version="1.0" encoding="utf-8"?>
<jdoconfig xmlns="http://java.sun.com/xml/ns/jdo/jdoconfig"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:noNamespaceSchemaLocation="http://java.sun.com/xml/ns/jdo/jdoconfig">

    <persistence-manager-factory name="transactions-optional">
        <property name="javax.jdo.PersistenceManagerFactoryClass"
            value="org.datanucleus.store.appengine.jdo.DatastoreJDOPersistenceManagerFactory"/>
        <property name="javax.jdo.option.ConnectionURL" value="appengine"/>
        <property name="javax.jdo.option.NontransactionalRead" value="true"/>
        <property name="javax.jdo.option.NontransactionalWrite" value="true"/>
        <property name="javax.jdo.option.RetainValues" value="true"/>
        <property name="datanucleus.appengine.autoCreateDatastoreTxns" value="true"/>
    </persistence-manager-factory>
</jdoconfig>

Mejora de las clases de datos

JDO utiliza un paso de "mejora" de la post-compilación durante el proceso de compilación para asociar clases de datos a la implementación de JDO.

Si utilizas Eclipse, el complemento de Google para Eclipse realiza este paso de forma automática durante la creación.

Si utilizas Apache Ant, el SDK incluye una tarea de Ant para realizar este paso. Para obtener más información sobre la tarea de Ant, consulta Uso de Apache Ant.

Puedes realizar el paso de mejora en clases compiladas desde la línea de comandos con el siguiente comando:

java -cp classpath com.google.appengine.tools.enhancer.Enhance class-files

La ruta de clase debe contener el JAR appengine-tools-api.jar del directorio appengine-java-sdk/lib/, así como todas las clases de datos.

Para obtener más información sobre el mejorador de código de bytes de DataNucleus, consulta la documentación de DataNucleus.

Obtención de una instancia PersistenceManager

Una aplicación interactúa con JDO a través de una instancia de la clase PersistenceManager. Esta se obtiene mediante la creación de una instancia y la ejecución de un método en una instancia de la clase PersistenceManagerFactory. El método predeterminado utiliza la configuración de JDO para crear instancias PersistenceManager.

Puesto que una instancia PersistenceManagerFactory tarda en inicializarse, la aplicación debería reutilizar una única instancia. Para imponer esto, se genera una excepción si la aplicación crea más de una instancia PersistenceManagerFactory (con el mismo nombre de configuración). Una forma sencilla de gestionar la instancia PersistenceManagerFactory es crear una clase envoltorio singleton con una instancia estática, como se muestra a continuación:

PMF.java

import javax.jdo.JDOHelper;
import javax.jdo.PersistenceManagerFactory;

public final class PMF {
    private static final PersistenceManagerFactory pmfInstance =
        JDOHelper.getPersistenceManagerFactory("transactions-optional");

    private PMF() {}

    public static PersistenceManagerFactory get() {
        return pmfInstance;
    }
}

La aplicación utiliza la instancia de método predeterminado para crear una instancia PersistenceManager para cada solicitud que accede al almacén de datos.

import javax.jdo.JDOHelper;
import javax.jdo.PersistenceManager;
import javax.jdo.PersistenceManagerFactory;

import PMF;

// ...
    PersistenceManager pm = PMF.get().getPersistenceManager();

Utiliza el PersistenceManager para almacenar, actualizar y eliminar objetos de datos, así como para realizar consultas de almacén de datos.

Cuando termines con la instancia PersistenceManager, debes ejecutar el método close(). Es un error utilizar la instancia PersistenceManager después de ejecutar el método close().

    try {
        // ... do stuff with pm ...
    } finally {
        pm.close();
    }

Funciones no compatibles de JDO

Las siguientes funciones de la interfaz JDO no son compatibles con la implementación App Engine:

  • relaciones sin propiedad (puedes implementar relaciones sin propiedad a través de valores de Key explícitos; es posible que se admita la sintaxis de JDO para relaciones sin propiedad en una futura versión),
  • relaciones de propiedad varios a varios,
  • consultas con "Join", (no puedes utilizar un campo de una entidad secundaria en un filtro si realizas una consulta en la entidad principal; ten en cuenta que puedes comprobar el campo de relación de la entidad principal directamente en la consulta a través de una clave),
  • agrupación JDOQL y otras consultas agrupadas,
  • consultas polimórficas (no puedes realizar una consulta de una clase para obtener instancias de una subclase; cada clase está representada por un tipo de entidad independiente del almacén de datos),
  • IdentityType.DATASTORE para la anotación @PersistenceCapable (sólo se admite IdentityType.APPLICATION),
  • en la actualidad existe un error que evita que los campos persistentes se guarden en el almacén de datos; esto se solucionará en una futura versión.