这是Datastore的这个父子结构
+ Entity:Place,ID:1 {'name':'Derp Region','type':'region'}
|
+---+ Entity:Place,ID:1a {'name':'Derpina Province','type','province'}
|
+---+ Entity:Place,ID:1b {'name':'Banana Province','type','province'}
|
+---+ Entity:Place,ID:1c {'name':'Potato Province','type','province'}
当尝试获取 Derp Region 的子项时,它在返回的数据中包含Derp Region
,如下所示:
Derp Region
Derpina Province
Banana Province
Potato Province
不应该是这种情况。这是因为它们具有相同的Entity
类型吗?
广告代码
DatastoreService datastore = DatastoreServiceFactory.getDatastoreService();
Entity place = new Entity( "Place" , "1" );
place.setProperty( "name" , "Derp Region" );
place.setProperty( "type" , "region" );
datastore.put( place );
Key parentKey = KeyFactory.createKey( "Place" , "1" );
Entity placeA = new Entity( "Place" , "1a" , parentKey );
placeA.setProperty( "name" , "Derpina Province" );
placeA.setProperty( "type" , "province" );
datastore.put( placeA );
Entity placeB = new Entity( "Place" , "1b" , parentKey );
placeB.setProperty( "name" , "Banana Province" );
placeB.setProperty( "type" , "province" );
datastore.put( placeB );
Entity placeC = new Entity( "Place" , "1c" , parentKey );
placeC.setProperty( "name" , "Potato Province" );
placeC.setProperty( "type" , "province" );
datastore.put( placeC );
查询代码
DatastoreService datastore = DatastoreServiceFactory.getDatastoreService();
Key parentKey = KeyFactory.createKey("Place", "1" );
Query placeQuery = new Query( "Place" ).setAncestor( parentKey ).addSort( "name" , SortDirection.ASCENDING );
PreparedQuery preparedQuery = datastore.prepare( placeQuery );
for( Entity result : preparedQuery.asIterable() )
{
resp.getWriter().println( result.getProperty( "name" ) );
}
有没有办法让所有子实体不包含相同类型的父实体?
答案 0 :(得分:0)
'祖先查询'不是儿童查询' - 虽然它很相似。将实体组视为树,将云数据存储视为密钥树文档数据库(而不仅仅是键值或文档数据库)。
祖先查询是指"让我看到这棵树中符合这些条件的每个实体"。 "这棵树"是由parentKey
指定的那个,你的条件是" Kind = Place"。一旦理解了这个概念,这种类型的查询与"子查询的区别就越清楚了。
通常,这可以忽略,因为parentKey
不符合Kind条件。这是第一个解决方案:使父级和子级实体具有不同的种类 - 例如PlaceRegion
和PlaceProvince
,或者如果类型不与父Place
和{{1}相关联}
第二种解决方案是通过索引。添加一个名为PlaceChild
的整数字段,并根据树中的级别为其分配值。 1 =根/父,2 =直系子。创建包含此level
字段的复合索引,现在您可以使用条件level
发出查询以执行子查询。
第三个解决方案只是按level = 2
= key
进行过滤,并弃置父级。