2013-10-15 74 views
0

我的模特有一些奇怪的行爲。NDB的put()有多可靠?

我有事件模型,它可以跟蹤事件。還有一個「Aggregate」模型,它存儲模型A的記錄彙總,按日期分組。

class Event(ndb.Model): 
    user = ndb.KeyProperty(kind=UserProfile) 
    date = ndb.DateTimeProperty(auto_now_add=True) 
    event_type = ndb.StringProperty() 
    is_aggregated = ndb.BooleanProperty(default=False) 

class Aggregate(ndb.Model): 
    user = ndb.KeyProperty(kind=UserProfile) 
    date = ndb.DateProperty() 
    aggregates = ndb.PickleProperty(default={}) 

Eventaggregate()方法,像這樣:

def aggregate(self): 
    if self.is_aggregated: 
     # already aggregated 
     return 

    # get an existing aggregate 
    agg = Aggregate.query(
     Aggregate.user == self.user, 
     Aggregate.date == self.date.date() 
    ).get() 
    if not agg: 
     # or create a new one 
     agg = Aggregate(
      user=self.user, 
      date=self.date.date() 
     ) 
     agg.put() 

    # update aggregate's count 
    if self.event_type not in agg.aggregates.keys(): 
     agg.aggregates[self.event_type] = 0 
    agg.aggregates[self.event_type] += 1 
    agg.put() 

    # mark this as aggregated 
    self.is_aggregated = True 
    self.put() 

現在,在我的處理程序,每一個新的Event時間被創建,我調用它的aggregate方法。 但與數字有一些差異。

例如,我有20條Event記錄與2013-10-10 00:00:002013-10-10 23:59:59event_type = "add"之間的date,個個都is_aggregated = True。這意味着aggregate方法每個都成功執行。

但是,當我查看與date = 2013-10-10相應的Aggregate記錄時,aggregates屬性不反映20 "add"事件。它只有16個。

什麼會導致這種差異? self.put()將如何成功但agg.put()不成功?

回答

3

我想你已經面臨eventual consistency功能。每次查詢Aggregate模型時,都可以從不同的數據中心進行檢索,這些數據中心可能包含略微不同的Aggregate版本。特別是如果您的事件模型創建得足夠快。

我會做出這樣:人工合成骨料模型的字符串ID基於用戶和日期,然後通過這個ID由Aggregate.get_by_id()得到它(我認爲用戶ID):

# get an existing aggregate 
agg_id = str(user.id) + '@' + self.date.date().strftime("%m/%d/%Y") 
agg = Aggregate.get_by_id(agg_id) 
if not agg: 
    # or create a new one 
    agg = Aggregate(key=ndb.Key(Aggregate, agg_id), 
        user=self.user, 
        date=self.date.date() 
    ) 
    #agg.put() #ALSO, this put is not needed because you has one below 
+0

謝謝,我會試試這個。有沒有辦法來驗證它是否解決了這個問題?此外,該文件指出實體將「最終一致」,但我查詢的記錄已經過去幾天了。 「最終」在這裏意味着多久? – john2x

+1

「最終一致」意味着當您創建新事件時,您可以獲得不反映先前事件更改的聚合(例如,「聚合」屬性不包含3項,而是包含2項)。所以你已經不是在更新一個新的Aggreate了,等等......所以,你永遠不會再看到「幾天前」的變化。 – Denisigo

+0

啊,對,是有道理的。謝謝。因此,如果我使用密鑰來獲取實體,它將確保我得到的實體更新?我問,因爲文檔只顯示使用祖先查詢/分組實現一致性。 – john2x