我剛剛從CRM應用程序中用sqlalchemy回想了一個非常討厭的模式。所有的表格都有一個刪除的列,我想自動過濾所有標記爲已刪除的實體和關係。以下是我想出了:自動過濾SQLAlchemy查詢的正確方法?
class CustomizableQuery(Query):
"""An overridden sqlalchemy.orm.query.Query to filter entities
Filters itself by BinaryExpressions
found in :attr:`CONDITIONS`
"""
CONDITIONS = []
def __init__(self, mapper, session=None):
super(CustomizableQuery, self).__init__(mapper, session)
for cond in self.CONDITIONS:
self._add_criterion(cond)
def _add_criterion(self, criterion):
criterion = self._adapt_clause(criterion, False, True)
if self._criterion is not None:
self._criterion = self._criterion & criterion
else:
self._criterion = criterion
而且它使用的是這樣的:
class UndeletedContactQuery(CustomizableQuery):
CONDITIONS = [contacts.c.deleted != True]
def by_email(self, email_address):
return EmailInfo.query.by_module_and_address('Contacts', email_address).contact
def by_username(self, uname):
return self.filter_by(twod_username_c=uname).one()
class Contact(object):
query = session.query_property(UndeletedContactQuery)
Contact.query.by_email('[email protected]')
EmailInfo是被映射到連接表的電子郵件和其他模塊,他們是之間的階級相關。
下面是一個映射的例子:
contacts_map = mapper(Contact, join(contacts, contacts_cstm), {
'_emails': dynamic_loader(EmailInfo,
foreign_keys=[email_join.c.bean_id],
primaryjoin=contacts.c.id==email_join.c.bean_id,
query_class=EmailInfoQuery),
})
class EmailInfoQuery(CustomizableQuery):
CONDITIONS = [email_join.c.deleted != True]
# More methods here
這給了我什麼,我想,我已經過濾掉所有被刪除的聯繫人。我也可以用這個作爲query_class說法在我的製圖員dynamic_loader - 但是...
- 有沒有更好的方式來做到這一點,我不是一個compicated類的內部打交道了真的很開心就像我一樣查詢。
- 有沒有人以不同的方式解決這個問題,他們可以分享?
非常好,我不知道! – 2009-05-28 13:13:45