[Zope-Checkins] CVS: ZODB3/ZODB - ConflictResolution.py:1.14.2.1

Jeremy Hylton jeremy@zope.com
Mon, 28 Oct 2002 11:04:45 -0500


Update of /cvs-repository/ZODB3/ZODB
In directory cvs.zope.org:/tmp/cvs-serv25054/ZODB

Modified Files:
      Tag: ZODB3-3_1-branch
	ConflictResolution.py 
Log Message:
Revert change that removed blanket try/except for conflict resolution.

There are a lot of exceptions that can occur when you try to load
objects from the database for conflict resolution.  Reports from the
field are that unexpected errors were causing transactions to fail
hard instead of raising conflict error.

Concrete example:
Traceback (most recent call last):
  File "/home/zope/opt/Python_2_1_3/lib/python2.1/site-packages/ZEO/StorageServe
r.py", line 494, in store
    self.txn)
  File "/home/zope/opt/Python_2_1_3/lib/python2.1/site-packages/Standby/primary.
py", line 131, in store
    r = self._storage.store(oid, serial, data, version, t)
  File "/home/zope/opt/Python_2_1_3/lib/python2.1/site-packages/ZODB/FileStorage
.py", line 702, in store
    data=self.tryToResolveConflict(oid, oserial, serial, data)
  File "/home/zope/opt/Python_2_1_3/lib/python2.1/site-packages/ZODB/ConflictRes
olution.py", line 95, in tryToResolveConflict
    newstate = unpickler.load()
ImportError: No module named DateTime.DateTime

The solution is to restore the blanket try/except with a log call if
the error isn't a ConflictError.  I'd like to do a more careful
analysis of what exceptions can be raised and narrow down the
try/except, but that's too much change to do right now.


=== ZODB3/ZODB/ConflictResolution.py 1.14 => 1.14.2.1 ===
--- ZODB3/ZODB/ConflictResolution.py:1.14	Fri Sep 27 14:35:09 2002
+++ ZODB3/ZODB/ConflictResolution.py	Mon Oct 28 11:04:45 2002
@@ -116,6 +116,15 @@
         return file.getvalue(1)
     except ConflictError:
         return 0
+    except:
+        # If anything else went wrong, catch it here and avoid passing an
+        # arbitrary exception back to the client.  The error here will mask
+        # the original ConflictError.  A client can recover from a
+        # ConflictError, but not necessarily from other errors.  But log
+        # the error so that any problems can be fixed.
+        zLOG.LOG("Conflict Resolution", zLOG.ERROR,
+                 "Unexpected error", error=sys.exc_info())
+        return 0
 
 class ConflictResolvingStorage:
     "Mix-in class that provides conflict resolution handling for storages"