""" open/dulcinea/lib/item.py """ from dulcinea.base import DulcineaPersistent from dulcinea.common import format_date from dulcinea.partition import PartKeyed, Partition from dulcinea.timestamped import Timestamped, reverse_timestamp_sorted from durus.btree import BTree from qp.lib.spec import add_getters_and_setters, string, boolean, init class Item(DulcineaPersistent, PartKeyed, Timestamped): title_is = (string, None) approved_is = boolean def __init__(self): assert self.__class__ is not Item, "abstract class" PartKeyed.__init__(self) Timestamped.__init__(self) init(self, approved=False) def is_new(self): return self.key is None def is_expired(self): if self.part_key == 'expired': return True return False def absorb(self, other): assert self.__class__ is other.__class__ for key, value in other.__getstate__().items(): if key != 'key': setattr(self, key, value) def get_search_text(self): return ' '.join(self.get_search_text_fields()) def get_search_text_fields(self): return [self.get_title() or '', format_date(self.get_timestamp())] def is_approved(self): return self.approved def can_modify(self, user): return user.is_admin() add_getters_and_setters(Item) class ItemFolder(Partition): def __init__(self, value_spec=Item): Partition.__init__(self, value_spec=value_spec, part_key_spec=('active', 'expired')) init(self) self.parts['active'] = BTree() self.parts['expired'] = BTree() def get_all(self): return self.get_active() + self.get_expired() def get_active(self): return list(self.get_part('active').itervalues()) def get_expired(self): return list(self.get_part('expired').itervalues()) def get_recent_items(self, count=None, include_unapproved=False): """(count : int = None, include_unapproved : bool = False) -> [Item] Return the 'count' most recent items. If 'include_unapproved' is True, both un-approved and approved items are returned. The list returned is in reverse-chronological order by timestamp. """ return reverse_timestamp_sorted( [item for item in self.get_active() if item.is_approved() or include_unapproved])[:count] def get_to_oldest_date(self, oldest_date, **kwargs): if oldest_date is not None: return [item for item in self.get_recent_items(**kwargs) if item.get_timestamp() >= oldest_date] return self.get_recent_items(**kwargs) def partition_item_folder(item_folder, item_class): '''Convert a Keep-style ItemFolder and Items within into a two part Partition ''' from durus.persistent import PersistentObject from durus.btree import BTree def __setstate__(self, state): if 'mapping' in state: parts = BTree() parts['active'] = state['mapping'] parts['expired'] = BTree() state['parts'] = parts del state['mapping'] PersistentObject.__setstate__(self, state) item_folder.__class__.__setstate__ = __setstate__ item_folder.value_spec = item_class item_folder.part_key_spec = ('active', 'expired') item_folder._p_note_change() for item in item_folder.get_part('active').itervalues(): item.part_key = 'active'