2

我正在利用 NDB ComputedProperty 和祖先查询来计算与特定过滤器匹配的另一个模型的对象。ComputedProperty 看起来像这样:

class Goal(ndb.Model):
    various_attributes = various_properties
    @ndb.ComputedProperty
    def count_active_actions(self):
        return Action.query(ancestor=self.key).filter(
                Action.status=='active').count()

class Action(ndb.Model):
    status = ndb.StringProperty(choices=(
            'not started', 'active', 'completed', 'on hold'))
    various_attributes = various_properties
    @ndb.ComputedProperty(
    def count_active_tasks(self):
        return Task.query(ancestor=self.key).filter(
                Task.status=='active').count()

class Task(ndb.Model):
    status = ndb.StringProperty(choices=(
            'not started', 'active', 'completed', 'on hold'))
    various_attributes = various_properties

当我创建一个Goal对象时,我不存储任何东西作为它的父对象。请注意,Goal 上的 ComputedProperty 与 Action 上的类似。在编写目标时执行 goal.put() 时没有收到任何错误。

然而,当创建一个动作对象时,我将父对象存储为goal.key这样的:

action = Action(parent=goal.key, various_other_properties = various_other_values)
action.put()

编写动作时,ComputedProperty正在执行查询,并且由于尚未完全编写id动作,因此尚未分配 for 动作,因此是None

我收到的错误是:

BadValueError: Expected complete Key, got Key('Goal', '##########', 'Action', None)

考虑到我认为幕后发生的事情,这种行为是有道理的。但是,我假设我遗漏了一些东西或错误地解决了这个问题,因为在我看来,这似乎是一个常见的用例。

我想要的目标是让父对象的属性表示匹配某个条件的子对象的计数,并且将父对象的键作为其祖先。

有没有更好的方法来实现这一目标?还是有什么明显的我失踪了?

4

0 回答 0