0
我想了解如何在常見使用場景下使用ReferenceProperty
。
在典型的應用程序中,我們始終顯示引用實體的列。我應該使用ReferenceProperty預取還是複製引用實體的列?
例如,考慮採購訂單應用程序。
class POCategory(db.Model):
name = db.StringProperty()
class POSubCategory(db.Model):
category = db.ReferenceProperty(POCategory, collection_name='sub_categories')
name = db.StringProperty()
class PurchaseOrder(db.Model):
total_amount = db.FloatProperty()
class PurchaseOrderLineItem(db.Model):
category = db.ReferenceProperty(POCategory, collection_name='po_line_items')
sub_category = db.ReferenceProperty(POSubCategory, collection_name = 'po_line_items')
amount = db.FloatProperty()
這是我們通常在典型應用中顯示的內容。
+---------------+---------------+--------+ | Category | Sub Category | Amount | +---------------+---------------+--------+ | Blue Category | Water | $12.00 | | Red Category | Fire | $20.00 | +---------------+---------------+--------+ | Purchase Order Total | $22.00 | +---------------+---------------+--------+
我應該使用的ReferenceProperty預取此避免N + 1選擇的問題?
或
在我的採購訂單行項目中重複類別和子類別名稱,如下所示?
class PurchaseOrderLineItem(db.Model):
category = db.ReferenceProperty(POCategory, collection_name='po_line_items')
category_name = db.StringProperty()
sub_category = db.ReferenceProperty(POSubCategory, collection_name = 'po_line_items')
sub_category_name = db.StringProperty()
amount = db.FloatProperty()
很明顯,類別和子類別的名稱是可編輯的。
所以當有人更新name
屬性時,我將不得不查詢並遍歷所有引用的PurchaseOrderLineItem
實體並更新我的重複name
屬性。
#----------------------------------------
# BAD DESIGN
#----------------------------------------
po_category.name = 'New Category Name'
# build list of line items to be updated
update_list = []
for child_line_item in po_category.po_line_items:
child_line_item.category_name = po_entity.name
update_list.append(child_line_item)
db.put(po_category, update_list)
我知道這是不是一個良好的可擴展的解決方案,因爲隨着時間的推移,我們將有很多行項目的更新。 RDBMS的思維方式很難擺脫。
那麼任何人都可以請教我如何思考這些典型的場景?
謝謝!
是的NDB比DB有更好的API設計,我只需要做ReferenceProperty預取技術來執行「SQL-JOIN-like」操作。不要繞過它。謝謝您的回答。 – stun 2013-04-28 16:40:57