如何用持久层建模朋友系统?

时间:2009-04-21 13:21:09

标签: java google-app-engine jpa persistence

您好我正在尝试为Google应用引擎提供新的Java支持,我正在尝试为所有对象创建一个持久层。我正在尝试模拟朋友连接,但遇到了问题。我使用JPA来持久化对象并使用JPA注释定义我的持久性对象。

我的想法是做以下事情:

用户对象:

@Entity
public class User  {

@Column(name="user_id")
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY) 
@Extension(vendorName="datanucleus", key="gae.encoded-pk", value="true") 
private String id;

@OneToMany(cascade={CascadeType.ALL},mappedBy="invitee")
private List<Connection> IncConnections;

@OneToMany(cascade={CascadeType.ALL},mappedBy="initiator")
private List<Connection> OutConnections;
}

@Entity
public class Connection {

@Column(name="connection_id")
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY) 
@Extension(vendorName="datanucleus", key="gae.encoded-pk", value="true") 
private String id;

@ManyToOne(cascade={CascadeType.ALL})
User initiator;

@ManyToOne(cascade={CascadeType.ALL})
User invitee;
}

但是当我尝试这个时,我得到错误: App Engine ORM不支持多个父密钥提供程序字段

那么有没有人知道如何在不使用多个父键的情况下为朋友系统建模?

希望有人可以提供帮助!

3 个答案:

答案 0 :(得分:2)

一般情况下,您必须自己与GAE保持任何关系。 GAE为此提供的最佳工具记录在Unowned Relationships部分。特别是,我认为关于“多对多”关系的部分是相关的。

从示例中,您似乎仍然需要自己完成维护参照完整性的大部分工作。由于这些可能位于不同的实体组中,因此您可能还需要大量代码来处理可能已损坏的关系。

答案 1 :(得分:2)

Using Objectify

class User { 
   @Id Long userId; 
   String email; 
} 

class UserFriendMap { 
   @Id Long id; 
   @Parent OKey<User> parent; 
   Set<OKey<User>> friend; // 5000 max
} 

答案 2 :(得分:1)

我从来没有真正使用谷歌应用引擎进行项目,但你需要了解它的持久性的第一件事是它不是一个关系数据库。我相信它使用了一个关键值存储。

因此,在使用应用引擎时,您需要以不同的方式考虑持久性。

来自文档:

App Engine实施不支持JPA接口的以下功能:

  • 拥有多对多的关系,以及无主的关系。您可以使用显式Key值实现无主关系,但不会在API中强制执行类型检查。
  • “加入”查询。在父类型上执行查询时,不能在过滤器中使用子实体的字段。请注意,您可以使用密钥直接在查询中测试父级关系字段。
  • 聚合查询(分组依据,拥有,总和,平均值,最大值,分钟数)
  • 多态查询。您无法执行类的查询以获取子类的实例。每个类在数据存储区中由单独的实体类型表示。

http://code.google.com/appengine/docs/java/datastore/usingjpa.html