[Checkins] SVN: z3c.batching/trunk/ * fixed bug in total calculation

Kim Nikolay fafhrd at datacom.kz
Tue Dec 4 00:07:49 EST 2007


Log message for revision 82115:
  * fixed bug in total calculation
  
  * added more method to IBatch
  
  

Changed:
  A   z3c.batching/trunk/CHANGES.txt
  A   z3c.batching/trunk/README.txt
  A   z3c.batching/trunk/setup.py
  A   z3c.batching/trunk/src/z3c/__init__.py
  U   z3c.batching/trunk/src/z3c/batching/README.txt
  U   z3c.batching/trunk/src/z3c/batching/__init__.py
  U   z3c.batching/trunk/src/z3c/batching/batch.py
  U   z3c.batching/trunk/src/z3c/batching/interfaces.py
  U   z3c.batching/trunk/src/z3c/batching/tests.py

-=-
Added: z3c.batching/trunk/CHANGES.txt
===================================================================
--- z3c.batching/trunk/CHANGES.txt	                        (rev 0)
+++ z3c.batching/trunk/CHANGES.txt	2007-12-04 05:07:48 UTC (rev 82115)
@@ -0,0 +1,8 @@
+=======
+CHANGES
+=======
+
+1.0.0 (2007-10-30)
+------------------
+
+- Initial release.

Added: z3c.batching/trunk/README.txt
===================================================================
--- z3c.batching/trunk/README.txt	                        (rev 0)
+++ z3c.batching/trunk/README.txt	2007-12-04 05:07:48 UTC (rev 82115)
@@ -0,0 +1 @@
+This package provides simple sequence batching.

Added: z3c.batching/trunk/setup.py
===================================================================
--- z3c.batching/trunk/setup.py	                        (rev 0)
+++ z3c.batching/trunk/setup.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -0,0 +1,62 @@
+##############################################################################
+#
+# Copyright (c) 2007 Zope Corporation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL).  A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Setup for z3c.batching package
+
+$Id$
+"""
+import os
+from setuptools import setup, find_packages
+
+def read(*rnames):
+    return open(os.path.join(os.path.dirname(__file__), *rnames)).read()
+
+setup(name='z3c.batching',
+      version = '1.0.0',
+      author='Zope Corporation and Contributors',
+      author_email='zope3-dev at zope.org',
+      description='Batching',
+      long_description=(
+          read('README.txt')
+          + '\n\n' +
+          'Detailed Dcoumentation\n' +
+          '======================\n'
+          + '\n\n' +
+          read('src', 'z3c', 'batching', 'README.txt')
+          + '\n\n' +
+          read('CHANGES.txt')
+          ),
+      keywords = "zope3 batching",
+      classifiers = [
+          'Development Status :: 5 - Production/Stable',
+          'Environment :: Web Environment',
+          'Intended Audience :: Developers',
+          'License :: OSI Approved :: Zope Public License',
+          'Programming Language :: Python',
+          'Natural Language :: English',
+          'Operating System :: OS Independent',
+          'Topic :: Internet :: WWW/HTTP',
+          'Framework :: Zope3'],
+      url='http://cheeseshop.python.org/pypi/z3c.batching',
+      license='ZPL 2.1',
+      packages=find_packages('src'),
+      package_dir = {'': 'src'},
+      namespace_packages=['z3c'],
+      install_requires = ['setuptools',
+                          'zope.component',
+                          'zope.interface',
+                          'zope.schema',
+                          ],
+      include_package_data = True,
+      zip_safe = False,
+      )


Property changes on: z3c.batching/trunk/setup.py
___________________________________________________________________
Name: svn:keywords
   + Id

Added: z3c.batching/trunk/src/z3c/__init__.py
===================================================================
--- z3c.batching/trunk/src/z3c/__init__.py	                        (rev 0)
+++ z3c.batching/trunk/src/z3c/__init__.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -0,0 +1,6 @@
+try:
+    # Declare this a namespace package if pkg_resources is available.
+    import pkg_resources
+    pkg_resources.declare_namespace('z3c')
+except ImportError:
+    pass


Property changes on: z3c.batching/trunk/src/z3c/__init__.py
___________________________________________________________________
Name: svn:keywords
   + Id

Modified: z3c.batching/trunk/src/z3c/batching/README.txt
===================================================================
--- z3c.batching/trunk/src/z3c/batching/README.txt	2007-12-03 23:47:38 UTC (rev 82114)
+++ z3c.batching/trunk/src/z3c/batching/README.txt	2007-12-04 05:07:48 UTC (rev 82115)
@@ -6,13 +6,40 @@
 large sequence into smaller batches. Let's start by creating a simple list,
 which will be our full sequence:
 
-   >>> sequence = ['one', 'two', 'three', 'four', 'five', 'six', 'seven',
-   ...             'eight', 'nine', 'ten', 'eleven', 'twelve', 'thirteen']
+Batch on empty root
 
+  >>> from z3c.batching.batch import Batch
+  >>> batch = Batch([], size=3)
+  >>> len(batch)
+  0
+  >>> batch.firstElement
+  Traceback (most recent call last):
+  ...
+  IndexError: ...
+
+  >>> batch.lastElement
+  Traceback (most recent call last):
+  ...
+  IndexError: ...
+
+  >>> batch[0]
+  Traceback (most recent call last):
+  ...
+  IndexError: ...
+
+  >>> batch.next is None
+  True
+
+  >>> batch.previous is None
+  True
+
+
+  >>> sequence = ['one', 'two', 'three', 'four', 'five', 'six', 'seven',
+  ...             'eight', 'nine', 'ten', 'eleven', 'twelve', 'thirteen']
+
 We can now create a batch for this sequence. Let's make our batch size 3:
 
-  >>> from z3c import batching
-  >>> batch = batching.Batch(sequence, size=3)
+  >>> batch = Batch(sequence, size=3)
 
 The first argument to the batch is always the full sequence. If no start
 element is specified, the batch starts at the first element:
@@ -22,14 +49,14 @@
 
 The start index is commonly specified in the constructor though:
 
-  >>> batch = batching.Batch(sequence, start=6, size=3)
+  >>> batch = Batch(sequence, start=6, size=3)
   >>> list(batch)
   ['seven', 'eight', 'nine']
 
 Note that the start is an index and starts at zero. If the start index is
 greater than the largest index of the sequence, an index error is raised:
 
-  >>> batching.Batch(sequence, start=15, size=3)
+  >>> Batch(sequence, start=15, size=3)
   Traceback (most recent call last):
   ...
   IndexError: start index key out of range
@@ -43,7 +70,7 @@
 Note that the length returns the true size of the batch, not the size we asked
 for:
 
-  >>> len(batching.Batch(sequence, start=12, size=3))
+  >>> len(Batch(sequence, start=12, size=3))
   1
 
 You can also get an element by index, which is relative to the batch:
@@ -72,6 +99,23 @@
   >>> iterator.next()
   'nine'
 
+Batch also implement some of IReadSequence interface
+
+  >>> 'eight' in batch
+  True
+
+  >>> 'ten' in batch
+  False
+
+  >>> batch == Batch(sequence, start=6, size=3)
+  True
+
+  >>> batch != Batch(sequence, start=6, size=3)
+  False
+
+  >>> batch != Batch(sequence, start=3, size=3)
+  True
+
 Besides all of those common API methods, there are several properties that were
 designed to make your life simpler. The start and size are specified:
 
@@ -100,7 +144,7 @@
 
 If the current batch is the last one, the next batch is None:
 
-  >>> batching.Batch(sequence, start=12, size=3).next is None
+  >>> Batch(sequence, start=12, size=3).next is None
   True
 
 The previous batch shows the previous batch:
@@ -110,7 +154,7 @@
 
 If the current batch is the first one, the previous batch is None:
 
-  >>> batching.Batch(sequence, start=0, size=3).previous is None
+  >>> Batch(sequence, start=0, size=3).previous is None
   True
 
 The final two properties deal with the elements within the batch. They ask for
@@ -121,3 +165,32 @@
 
   >>> batch.lastElement
   'nine'
+
+
+Total batches
+
+  >>> batch = Batch(sequence[:-1], size=3)
+  >>> batch.total
+  4
+
+We can get access to all batches
+
+  >>> len(batch.batches)
+  4
+
+  >>> batch.batches[0]
+  <Batch start=0, size=3>
+
+  >>> batch.batches[3]
+  <Batch start=9, size=3>
+
+  >>> batch.batches[4]
+  Traceback (most recent call last):
+  ...
+  IndexError: ...
+
+  >>> batch.batches[-1]
+  <Batch start=9, size=3>
+
+  >>> batch.batches[-2]
+  <Batch start=6, size=3>

Modified: z3c.batching/trunk/src/z3c/batching/__init__.py
===================================================================
--- z3c.batching/trunk/src/z3c/batching/__init__.py	2007-12-03 23:47:38 UTC (rev 82114)
+++ z3c.batching/trunk/src/z3c/batching/__init__.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -1,3 +1 @@
 # Make a package
-
-from z3c.batching.batch import Batch

Modified: z3c.batching/trunk/src/z3c/batching/batch.py
===================================================================
--- z3c.batching/trunk/src/z3c/batching/batch.py	2007-12-03 23:47:38 UTC (rev 82114)
+++ z3c.batching/trunk/src/z3c/batching/batch.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -16,8 +16,10 @@
 $Id$
 """
 __docformat__ = 'restructuredtext'
+
 import zope.interface
 from zope.schema.fieldproperty import FieldProperty
+from zope.interface.common.sequence import IFiniteSequence
 
 from z3c.batching import interfaces
 
@@ -29,26 +31,42 @@
     size = FieldProperty(interfaces.IBatch['size'])
     end = FieldProperty(interfaces.IBatch['end'])
 
-    def __init__(self, list, start=0, size=20):
-        self._list = list
+    def __init__(self, sequence, start=0, size=20, batches=None):
+        self.sequence = sequence
+
+        length = len(sequence)
+        self._length = length
+
         # See interfaces.IBatch
         self.start = start
-        if len(list) == 0:
+        if length == 0:
             self.start = -1
-        elif start >= len(list):
+        elif start >= length:
             raise IndexError('start index key out of range')
+
         # See interfaces.IBatch
         self.size = size
         self._trueSize = size
-        if start + size >= len(list):
-            self._trueSize = len(list) - start
+
+        if start + size >= length:
+            self._trueSize = length - start
+
         # See interfaces.IBatch
-        if len(list) == 0:
+        if length == 0:
             self.end = -1
         else:
             self.end = start + self._trueSize - 1
 
+        if batches is None:
+            batches = Batches(self)
+
+        self.batches = batches
+
     @property
+    def index(self):
+        return self.start / self.size
+
+    @property
     def number(self):
         """See interfaces.IBatch"""
         return self.start / self.size + 1
@@ -56,48 +74,91 @@
     @property
     def total(self):
         """See interfaces.IBatch"""
-        return len(self._list) / self.size + 1
+        total = self._length / self.size
+        if self._length % self.size:
+            total += 1
+        return total
 
     @property
     def next(self):
-        """See interfaces.IBatch"""
-        start = self.start + self.size
-        if start >= len(self._list):
+        try:
+            return self.batches[self.index + 1]
+        except IndexError:
             return None
-        return Batch(self._list, start, self.size)
 
     @property
     def previous(self):
-        """See interfaces.IBatch"""
-        start = self.start - self.size
-        if start < 0:
-            return None
-        return Batch(self._list, start, self.size)
+        idx = self.index - 1
+        if idx >= 0:
+            return self.batches[idx]
+        return None
 
     @property
     def firstElement(self):
         """See interfaces.IBatch"""
-        return self._list[self.start]
+        return self.sequence[self.start]
 
     @property
     def lastElement(self):
         """See interfaces.IBatch"""
-        return self._list[self.end]
+        return self.sequence[self.end]
 
     def __getitem__(self, key):
         """See zope.interface.common.sequence.IMinimalSequence"""
         if key >= self._trueSize:
             raise IndexError('batch index out of range')
-        return self._list[self.start+key]
+        return self.sequence[self.start+key]
 
     def __iter__(self):
         """See zope.interface.common.sequence.IMinimalSequence"""
-        return iter(self._list[self.start:self.end+1])
+        return iter(self.sequence[self.start: self.end+1])
 
     def __len__(self):
         """See zope.interface.common.sequence.IFiniteSequence"""
         return self._trueSize
 
+    def __contains__(self, item):
+        for i in self:
+            if item == i:
+                return True
+        else:
+            return False
+
+    def __eq__(self, other):
+        return ((self.size, self.start, self.sequence) ==
+                (other.size, other.start, other.sequence))
+
+    def __ne__(self, other):
+        return not self.__eq__(other)
+
     def __repr__(self):
         return '<%s start=%i, size=%i>' % (
             self.__class__.__name__, self.start, self.size)
+
+
+class Batches(object):
+    zope.interface.implements(IFiniteSequence)
+    
+    def __init__(self, batch):
+        self.size = batch.size
+        self.total = batch.total
+        self.sequence = batch.sequence
+        
+        self._batches = {batch.index: batch}
+
+    def __len__(self):
+        return self.total
+
+    def __getitem__(self, key):
+        if key not in self._batches:
+            if key < 0:
+                key = self.total + key
+
+            batch = Batch(
+                self.sequence, key*self.size, self.size, self)
+            self._batches[batch.index] = batch
+
+        try:
+            return self._batches[key]
+        except KeyError:
+            raise IndexError(key)

Modified: z3c.batching/trunk/src/z3c/batching/interfaces.py
===================================================================
--- z3c.batching/trunk/src/z3c/batching/interfaces.py	2007-12-03 23:47:38 UTC (rev 82114)
+++ z3c.batching/trunk/src/z3c/batching/interfaces.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -27,6 +27,10 @@
     other values are calculated.
     """
 
+    sequence = zope.interface.Attribute('Sequence')
+
+    batches = zope.interface.Attribute('Batches')
+
     start = zope.schema.Int(
         title=u'Start Index',
         description=(u'The index of the sequence at which the batch starts. '
@@ -50,6 +54,13 @@
         readonly=True,
         required=True)
 
+    index = zope.schema.Int(
+        title=u'Current Batch Index',
+        description=u'The index of the batch in relation to all batches.',
+        min=0,
+        readonly=True,
+        required=True)
+
     number = zope.schema.Int(
         title=u'Current Batch Number',
         description=u'The number of the batch in relation to all batches.',
@@ -91,3 +102,12 @@
 
     def __iter__():
         """Creates an iterator for the contents of the batch."""
+
+    def __contains__(item):
+        """ `x.__contains__(item)` <==> `item in x` """
+
+    def __eq__(other):
+        """`x.__eq__(other)` <==> `x == other`"""
+
+    def __ne__(other):
+        """`x.__ne__(other)` <==> `x != other`"""

Modified: z3c.batching/trunk/src/z3c/batching/tests.py
===================================================================
--- z3c.batching/trunk/src/z3c/batching/tests.py	2007-12-03 23:47:38 UTC (rev 82114)
+++ z3c.batching/trunk/src/z3c/batching/tests.py	2007-12-04 05:07:48 UTC (rev 82115)
@@ -17,16 +17,13 @@
 """
 __docformat__ = "reStructuredText"
 
-import doctest
-import unittest
-from zope.testing.doctestunit import DocFileSuite
+import doctest, unittest
 
+
 def test_suite():
+
     return unittest.TestSuite((
-        DocFileSuite(
-            'README.txt',
-            optionflags=doctest.NORMALIZE_WHITESPACE|doctest.ELLIPSIS),
+        doctest.DocFileSuite(
+                'README.txt',
+                optionflags=doctest.NORMALIZE_WHITESPACE|doctest.ELLIPSIS),
         ))
-
-if __name__ == '__main__':
-    unittest.main(defaultTest='test_suite')



More information about the Checkins mailing list