[Checkins] SVN: z3c.iplocation/trunk/ Implemented update concept. The new update method allows to update the

Roger Ineichen roger at projekt01.ch
Sat May 10 18:57:40 EDT 2008


Log message for revision 86621:
  Implemented update concept. The new update method allows to update the 
  iplocation data based on a file upload or a file path. Added tests and 
  update to new coverage recipe.

Changed:
  _U  z3c.iplocation/trunk/
  U   z3c.iplocation/trunk/CHANGES.txt
  U   z3c.iplocation/trunk/buildout.cfg
  U   z3c.iplocation/trunk/src/z3c/iplocation/README.txt
  U   z3c.iplocation/trunk/src/z3c/iplocation/locator.py

-=-

Property changes on: z3c.iplocation/trunk
___________________________________________________________________
Name: svn:ignore
   - bin
.installed.cfg
develop-eggs
parts

   + bin
.installed.cfg
develop-eggs
parts
coverage


Modified: z3c.iplocation/trunk/CHANGES.txt
===================================================================
--- z3c.iplocation/trunk/CHANGES.txt	2008-05-10 19:54:33 UTC (rev 86620)
+++ z3c.iplocation/trunk/CHANGES.txt	2008-05-10 22:57:38 UTC (rev 86621)
@@ -5,4 +5,7 @@
 Unreleased
 ----------
 
+- Implemented update concept. The new update method allows to update the 
+  iplocation data based on a file upload or a file path. Added tests
+
 - Initial Release

Modified: z3c.iplocation/trunk/buildout.cfg
===================================================================
--- z3c.iplocation/trunk/buildout.cfg	2008-05-10 19:54:33 UTC (rev 86620)
+++ z3c.iplocation/trunk/buildout.cfg	2008-05-10 22:57:38 UTC (rev 86621)
@@ -1,6 +1,6 @@
 [buildout]
 develop = . 
-parts = test checker coverage
+parts = test checker coverage-test coverage-report
 
 [test]
 recipe = zc.recipe.testrunner
@@ -10,6 +10,15 @@
 recipe = lovely.recipe:importchecker
 path = src/z3c/iplocation
 
-[coverage]
+
+[coverage-test]
+recipe = zc.recipe.testrunner
+eggs = z3c.iplocation [test]
+defaults = ['--coverage', '../../coverage']
+
+
+[coverage-report]
 recipe = zc.recipe.egg
 eggs = z3c.coverage
+scripts = coverage=coverage-report
+arguments = ('coverage', 'coverage/report')

Modified: z3c.iplocation/trunk/src/z3c/iplocation/README.txt
===================================================================
--- z3c.iplocation/trunk/src/z3c/iplocation/README.txt	2008-05-10 19:54:33 UTC (rev 86620)
+++ z3c.iplocation/trunk/src/z3c/iplocation/README.txt	2008-05-10 22:57:38 UTC (rev 86621)
@@ -219,6 +219,59 @@
   21.0
 
 
+update
+------
+
+An existing IPLocator can get updated with new data. If we do this, we will 
+remove all existing data. Take care if you are using custom added data which
+are not in the original ipligence data file.
+
+Let's get the existing maxLocator and update them with the lite data file.
+
+  >>> file = open(os.path.join(dirpath, 'ipligence-lite-demo.txt'), 'r')
+  >>> maxLocator.update(file)
+  Traceback (most recent call last):
+  ...
+  ValueError: Must use a ipligence location class.
+
+As you can see, you must use a location class for update the data:
+
+  >>> maxLocator.update(file, ipligence.MaxLocation)
+  Traceback (most recent call last):
+  ...
+  ValueError: Wrong ipligence location class used or skipped the wrong amount of skipLines.
+
+But you have to use the right ipligence location class:
+
+  >>> file = open(os.path.join(dirpath, 'ipligence-lite-demo.txt'), 'r')
+  >>> maxLocator.update(file, ipligence.LiteLocation)
+
+Now we must get the lite location as result for the given IP:
+
+  >>> liteLocator.get('24.225.10.88')
+  <LiteLocation 24.225.0.0-24.225.255.255 u'UNITED STATES'>
+
+Since we skip first 5 lines by default in the update method, let's check
+the amount of locations which must be 42:
+
+  >>> len(liteLocator._locations)
+  42
+
+reset
+-----
+
+The locator offers also a reset method which will remove all existing data and
+can setup a clean empty locator. This method is used on initialization and 
+before the data get updated like shown in the sample above. 
+
+  >>> liteLocator.reset()
+
+After the reset, the locator is empty and doesn't return any location:
+
+  >>> liteLocator.get('24.225.10.88') is None
+  True
+
+
 Converting IPs to Decimals
 --------------------------
 

Modified: z3c.iplocation/trunk/src/z3c/iplocation/locator.py
===================================================================
--- z3c.iplocation/trunk/src/z3c/iplocation/locator.py	2008-05-10 19:54:33 UTC (rev 86620)
+++ z3c.iplocation/trunk/src/z3c/iplocation/locator.py	2008-05-10 22:57:38 UTC (rev 86621)
@@ -16,9 +16,13 @@
 $Id$
 """
 __docformat__ = "reStructuredText"
+
+import csv
+import StringIO
 import persistent
 import zope.app.intid
 import zope.interface
+import zope.location
 from BTrees import IOBTree, IFBTree, OIBTree
 from zc.catalog import index
 from zope.app.container import contained
@@ -66,11 +70,34 @@
 
     def __init__(self):
         super(IPLocator, self).__init__()
+        self.reset()
+
+    def reset(self):
         self._locations = OIBTree.OITreeSet()
         self._ids = zope.app.intid.IntIds()
         self._ipFrom = index.ValueIndex()
         self._ipTo = index.ValueIndex()
 
+    def update(self, file, klass=None, skipLines=5):
+        self.reset()
+        counter = 0
+        if klass is None:
+            raise ValueError("Must use a ipligence location class.")
+        try:
+            # probably we've got file upload data from a form
+            if isinstance(file, str):
+                reader = csv.reader(StringIO.StringIO(file))
+            else:
+                reader = csv.reader(file)
+            for row in reader:
+                counter += 1
+                if skipLines < counter:
+                    loc = klass(*row)
+                    self.add(loc, loc.decimalFrom, loc.decimalTo)
+        except TypeError:
+            raise ValueError("Wrong ipligence location class used or skipped "
+                             "the wrong amount of skipLines.")
+
     def get(self, ip, default=None):
         """See interfaces.IIPLocator"""
         ip = getDecimal(ip)
@@ -92,6 +119,8 @@
         if location in self._locations.keys():
             return
         self._locations.insert(location)
+        # give em a location and prevent to run into NotYet errors in IIntIds
+        zope.location.locate(location, self)
         uid = self._ids.register(location)
         self._ipFrom.index_doc(uid, fromDecimal or getDecimal(location.ipFrom))
         self._ipTo.index_doc(uid, toDecimal or getDecimal(location.ipTo))



More information about the Checkins mailing list