# HG changeset patch # User Paul Boddie # Date 1370295425 -7200 # Node ID ffd4c114650370cddbda81aad21931ecf7e1e785 # Parent 965d1f6ff37ae7611b78092ec527e85674ba3259 Added support for removing items from stores; made the __len__ method return the number of items, not the next item number; added a keys method to expose the item numbers being used. diff -r 965d1f6ff37a -r ffd4c1146503 ItemSupport.py --- a/ItemSupport.py Fri May 31 02:07:53 2013 +0200 +++ b/ItemSupport.py Mon Jun 03 23:37:05 2013 +0200 @@ -41,11 +41,17 @@ self.write_next(next) return next + def get_keys(self): + + "Return the item keys." + + return [int(filename) for filename in os.listdir(self.path) if filename.isdigit()] + def deduce_next(self): "Deduce the next item number from the existing item files." - return max([int(filename) for filename in os.listdir(self.path) if filename.isdigit()] or [-1]) + 1 + return max(self.get_keys() or [-1]) + 1 def read_next(self): @@ -93,6 +99,12 @@ finally: f.close() + def remove_item(self, number): + + "Remove the item with the given item 'number'." + + os.remove(self.get_item_path(number)) + def get_item_path(self, number): "Get the path for the given item 'number'." @@ -122,15 +134,10 @@ def __len__(self): """ - Return the number of the next item (which should also be the number of - items). + Return the number of items. """ - self.writelock.acquire() - try: - return self.get_next() - finally: - self.writelock.release() + return len(self.keys()) def __iter__(self): @@ -138,6 +145,16 @@ return ItemIterator(self) + def keys(self): + + "Return a list of keys for items in the store." + + self.readlock.acquire() + try: + return self.get_keys() + finally: + self.readlock.release() + def __getitem__(self, number): "Return the item with the given 'number'." @@ -151,6 +168,32 @@ finally: self.readlock.release() + def __delitem__(self, number): + + "Remove the item with the given 'number' from the store." + + self.writelock.acquire() + try: + try: + self.remove_item(number) + except (IOError, OSError): + raise IndexError, number + finally: + self.writelock.release() + + def next(self): + + """ + Return the number of the next item (which should also be the number of + items if none have been deleted). + """ + + self.writelock.acquire() + try: + return self.get_next() + finally: + self.writelock.release() + class ItemIterator: "An iterator over items in a store." @@ -163,9 +206,9 @@ def reset(self): if self.direction == 1: self._next = 0 - self.final = len(self.store) + self.final = self.store.next() else: - self._next = len(self.store) - 1 + self._next = self.store.next() - 1 self.final = 0 def more(self): diff -r 965d1f6ff37a -r ffd4c1146503 MoinSupport.py --- a/MoinSupport.py Fri May 31 02:07:53 2013 +0200 +++ b/MoinSupport.py Mon Jun 03 23:37:05 2013 +0200 @@ -1026,6 +1026,16 @@ user = self.page.request.user return user and user.may.read(self.page.page_name) + def can_delete(self): + + """ + Return whether the user associated with the request can delete the + page owning this store. + """ + + user = self.page.request.user + return user and user.may.delete(self.page.page_name) + # High-level methods. def append(self, item): @@ -1039,10 +1049,7 @@ def __len__(self): - """ - Return the number of the next item (which should also be the number of - items). - """ + "Return the number of items in the store." if not self.can_read(): return 0 @@ -1058,4 +1065,13 @@ return ItemDirectoryStore.__getitem__(self, number) + def __delitem__(self, number): + + "Remove the item with the given 'number'." + + if not self.can_delete(): + return + + return ItemDirectoryStore.__delitem__(self, number) + # vim: tabstop=4 expandtab shiftwidth=4