我有很多课程(例如联系人)我也想跟踪更改历史记录。以下是我的出发点。我想这是一个常见的用例,所以希望能够在这里获得有关最佳实践的指导。这是一个使用多重继承的好地方,那会是什么样的?
from datetime import date
class ContactHistory(object):
def __init__(self, contact, change_action, change_user_id, change_source):
self.name = contact.name
self.phone = contact.phone
self.email = contact.email
self.change_action = change_action
self.change_user_id = change_user_id
self.change_source = change_source
self.change_date = date.today()
def __repr__(self):
return '%s, %s, %s, %s, %s, %s, %s' % (self.name, self.email, self.phone, self.change_action, self.change_user_id, self.change_source, self.change_date)
class Contact(object):
def __init__(self, name, phone, email, change_user_id, change_source):
self.name = name
self.phone = phone
self.email = email
self.history = []
self.history.append(ContactHistory(self, 'created', change_user_id, change_source))
def update_phone(self, phone, change_user_id, change_source):
self.phone = phone
self.history.append(ContactHistory(self, 'phone updated', change_user_id, change_source))
def get_history(self):
return self.history
contact = Contact('Bill', '214-555-1212', 'me', 'admin page')
contact.update('972-555-1212', 'me', 'contact management page')
print contact.get_history()
答案 0 :(得分:1)
这是您使用继承来解决此问题的一种方法。 ChangeableObject
可以由任何需要更改的对象继承,该对象只描述用于为历史创建浅层克隆的参数:
from collections import namedtuple
Change = namedtuple("Change", ("old", "new", "action"))
class History(object):
def __init__(self):
self.history = []
def save_change(self, old, new, action):
change = Change(old, new, action)
self.history.append(change)
def get_history(self):
return self.history
class ChangeableObject(object):
def __init__(self, make_history=True):
if make_history:
self.history = History()
self.history.save_change(None, self, "created")
self.cloneable_attributes = ()
@classmethod
def get_clone(cls, obj):
attrs = {attr: getattr(obj, attr) for attr in obj.cloneable_attributes}
return cls(make_history=False, **attrs)
def view_history(self):
return self.history.get_history()
class Contact(ChangeableObject):
def __init__(self, name, phone, email, make_history=True):
super(Contact, self).__init__(make_history=make_history)
self.name = name
self.phone = phone
self.email = email
self.cloneable_attributes = ("name", "phone", "email")
def update_phone(self, phone):
clone = self.get_clone(self)
self.phone = phone
self.history.save_change(clone, self, "phone updated")
def __repr__(self):
return "{} {} {}".format(self.name, self.phone, self.email)
使用示例代码:
c = Contact("me", "123-123-123", "foo@example.com")
c.update_phone("456-456-456")
print c
for i, hist in enumerate(c.view_history()):
print "{}. {}".format(i, hist)
输出:
me 456-456-456 foo@example.com
0. Change(old=None, new=me 456-456-456 foo@example.com, action='created')
1. Change(old=me 123-123-123 foo@example.com, new=me 456-456-456 foo@example.com, action='phone updated')