Google Cloud Datastore:如何查询所有不同的 Parent/Ancestor?

Google Cloud Datastore: how to query all distinct Parent/Ancestor?

我有一个名为 Order 的数据存储类型,它有一个 ancestor/parent User.

我想使用 GQL 查询订单的所有不同祖先(用户),但以下查询不起作用。

SELECT DISTINCT User FROM Order

查询的响应是:

No entities matched this query.

Make sure there are either simple or composite indexes for the properties you are searching. Learn more

由于parent也是key的一部分,我也试过:

SELECT DISTINCT __key__ FROM Order

但是错误响应说:

GQL query error: Group by is not supported for the property: key

您应该注意,数据存储祖先并不是在实体 kind 级别建立的:您不能真正说 Order kind 有一个 User 种类 作为祖先。

祖先是在 实体 级别建立的 - 只有在实体创建级别指定了祖先时,实体才有祖先,否则它没有祖先。同样,祖先实体的种类无关紧要,同一种类的不同实体可以有不同种类的祖先或根本没有祖先。

考虑到这一点,听起来您的每个 Order 实体都有一个 User 实体作为祖先。

血统关系的存在将所有相关实体置于同一个实体组中。所有没有祖先的实体都被放入它们自己的实体组中(它们是实体组 roots/leaders)。

在你的例子中,Order 个实体被放置在它们各自的 User 个实体的实体组中。

进行祖先查询时(即指定特定祖先或后代实体),查询结果将仅限于该特定实体组的范围。这允许以事务方式进行此类查询,并获得高度一致的结果。

有关祖先查询语法的示例,请参阅 HAS ANCESTOR and HAS DESCENDANT clauses in google cloud datastore

缺点是您不能跨多个实体组进行祖先查询。在您的情况下,您正在查询 User 个实体,它们位于不同的实体组中。即使你将所有 User 实体放在同一个组中(通过为它们指定一个共同的祖先键)你仍然无法得到你想要的东西,因为你正在寻找不同的祖先 Order,这是一个 "descendant condition" - 一个 Order 只能有一个 User 作为祖先。

这让我们找到了问题的根本原因:您正在使用实体祖先来模拟实体关系。这不是祖先的设计目的,它是为强一致性而设计的。我知道,这听起来很混乱。

您可以做的是忘记数据存储的祖先,使用普通键属性为您的关系建模,没有任何限制。另见

我会在 User 类型中添加一个 order_count 属性,在 Order 类型中添加一个 user 键 属性。每当创建订单时,我都会创建一个 Order 实体,并将其 user 属性 设置为相应的 User 实体键,然后我会增加 order_countUser 实体的 属性。然后,为了得到你想要的,你只需要查询 User 具有非零 order_count.

的实体