Java 为什么';我拥有的一对多关系是否会持久化到GAE数据存储?

Java 为什么';我拥有的一对多关系是否会持久化到GAE数据存储?,java,google-app-engine,google-cloud-datastore,jdo,datanucleus,Java,Google App Engine,Google Cloud Datastore,Jdo,Datanucleus,我定义了两个类并将其映射到GAE数据存储—一个Person类和一个LocationStamp类,它表示一个纬度/经度组合以及一个时间戳。在Person和LocationStamp之间有一个自有的一对多映射,在类似的行上实现 在我的个人DAO中,我有以下方法: public LocationStamp addLocationStampForCurrentUser(LocationStamp ls) { PersistenceManager pm = getPersisten

我定义了两个类并将其映射到GAE数据存储—一个
Person
类和一个
LocationStamp
类,它表示一个纬度/经度组合以及一个时间戳。在
Person
LocationStamp
之间有一个自有的一对多映射,在类似的行上实现

在我的个人DAO中,我有以下方法:

   public LocationStamp addLocationStampForCurrentUser(LocationStamp ls)
   {
      PersistenceManager pm = getPersistenceManager();

      Person p = getProfileForCurrentUser();
      p.getLocationStamps().add(ls);

      pm.currentTransaction().begin();
      try {
         pm.makePersistent(p);
         pm.currentTransaction().commit();
         return ls;
      } finally {
         if (pm.currentTransaction().isActive()) {
            pm.currentTransaction().rollback();
         }
         pm.close();
      }
   }    
当我尝试使用此方法向对象的
LocationStamp
实体集合添加条目时,关系不会持久化。稍后查询相关的
Person
对象时,会返回带有电子邮件地址的正确对象,但
locationStamps
列表为空。此外,App Engine服务器的Data Viewer不显示任何
LocationStamp
实体(并且在
Person
的表中没有为
locationStamps
显示任何列)

我仔细地遵循了论坛帖子中的说明,但我不确定我是否遗漏了什么

以下是我的实体:

@PersistenceCapable(identityType = IdentityType.APPLICATION, detachable = "true")
public class Person
{

   @PrimaryKey
   @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)
   private Key key;

   @Persistent
   private String emailAddress;

   @Persistent
   private String name;

   @Persistent(mappedBy = "person")
   @Element(dependent = "true")
   @Order(extensions = @Extension(vendorName = "datanucleus", key = "list-ordering", value = "timestamp desc"))
   private final List<LocationStamp> locationStamps = new ArrayList<LocationStamp>();

   // ... getters and setters ...
}
由于在上述代码中使用了这些方法,以下是其他几种方法的定义:

   public Person getProfileForCurrentUser()
   {
      PersistenceManager pm = getPersistenceManager();
      try {
         Key k = getKeyForEmailAddress(getCurrentUserEmail());
         return pm.getObjectById(Person.class, k);
      } catch (JDOObjectNotFoundException e) {
         // Create a new profile if the new one isn't found
         return updateProfileForCurrentUser(new Person());
      } finally {
         pm.close();
      }
   }

   public Person updateProfileForCurrentUser(Person p)
   {
      p.setEmailAddress(getCurrentUserEmail());
      return update(p);
   }

   public Person update(Person p)
   {
      PersistenceManager pm = getPersistenceManager();
      try {
         pm.currentTransaction().begin();
         Key k = getKeyForEmailAddress(p.getEmailAddress());
         p.setKey(k);
         pm.makePersistent(p);
         pm.currentTransaction().commit();
         return p;
      } finally {
         if (pm.currentTransaction().isActive()) {
            pm.currentTransaction().rollback();
         }
         pm.close();
      }
   }

   private Key getKeyForEmailAddress(String emailAddress)
   {
      return KeyFactory.createKey(Person.class.getSimpleName(), emailAddress);
   }

   private static PersistenceManager getPersistenceManager()
   {
      // PMF is a singleton class that returns an instance of PersistenceManagerFactory
      return PMF.get().getPersistenceManager();
   }

当持久化对象中有一个列表时,加载该列表是一个延迟操作。因此,如果在加载列表之前关闭
PersistenceManager
,则不会加载该列表

尝试使用:

public Person getProfileForCurrentUser()
{
    PersistenceManager pm = getPersistenceManager();
    try {
        Key k = getKeyForEmailAddress(getCurrentUserEmail());
        Person p = pm.getObjectById(Person.class, k);
        p.getLocationStamps().size();
        return p;
    } catch (JDOObjectNotFoundException e) {
        // Create a new profile if the new one isn't found
        return updateProfileForCurrentUser(new Person());
    } finally {
        pm.close();
    }
}

当持久化对象中有一个列表时,加载该列表是一个延迟操作。因此,如果在加载列表之前关闭
PersistenceManager
,则不会加载该列表

尝试使用:

public Person getProfileForCurrentUser()
{
    PersistenceManager pm = getPersistenceManager();
    try {
        Key k = getKeyForEmailAddress(getCurrentUserEmail());
        Person p = pm.getObjectById(Person.class, k);
        p.getLocationStamps().size();
        return p;
    } catch (JDOObjectNotFoundException e) {
        // Create a new profile if the new one isn't found
        return updateProfileForCurrentUser(new Person());
    } finally {
        pm.close();
    }
}

太好了。我以为我按照论坛帖子的指示消除了所有的延迟加载问题,但我显然也需要显式加载列表。太好了。我以为我按照论坛帖子的指示消除了所有延迟加载问题,但我显然也需要显式加载列表。