Fixed _pickle.Unpickler to handle empty persistent IDs correctly.

This commit is contained in:
Alexandre Vassalotti 2013-11-30 13:52:35 -08:00
parent 1a83070d9e
commit 896414fedf
3 changed files with 26 additions and 19 deletions

View File

@ -1499,30 +1499,34 @@ class AbstractPersistentPicklerTests(unittest.TestCase):
if isinstance(object, int) and object % 2 == 0:
self.id_count += 1
return str(object)
elif object == "test_false_value":
self.false_count += 1
return ""
else:
return None
def persistent_load(self, oid):
self.load_count += 1
object = int(oid)
assert object % 2 == 0
return object
if not oid:
self.load_false_count += 1
return "test_false_value"
else:
self.load_count += 1
object = int(oid)
assert object % 2 == 0
return object
def test_persistence(self):
self.id_count = 0
self.load_count = 0
L = list(range(10))
self.assertEqual(self.loads(self.dumps(L)), L)
self.assertEqual(self.id_count, 5)
self.assertEqual(self.load_count, 5)
def test_bin_persistence(self):
self.id_count = 0
self.load_count = 0
L = list(range(10))
self.assertEqual(self.loads(self.dumps(L, 1)), L)
self.assertEqual(self.id_count, 5)
self.assertEqual(self.load_count, 5)
L = list(range(10)) + ["test_false_value"]
for proto in protocols:
self.id_count = 0
self.false_count = 0
self.load_false_count = 0
self.load_count = 0
self.assertEqual(self.loads(self.dumps(L, proto)), L)
self.assertEqual(self.id_count, 5)
self.assertEqual(self.false_count, 1)
self.assertEqual(self.load_count, 5)
self.assertEqual(self.load_false_count, 1)
class AbstractPicklerUnpicklerObjectTests(unittest.TestCase):

View File

@ -21,6 +21,9 @@ Library
- Issue #19088: Fixed incorrect caching of the copyreg module in
object.__reduce__() and object.__reduce_ex__().
- Fixed _pickle.Unpickler to not fail when loading empty strings as
persistent IDs.
- Issue #11508: Fixed uuid.getnode() and uuid.uuid1() on environment with
virtual interface. Original patch by Kent Frazier.

View File

@ -4665,7 +4665,7 @@ load_persid(UnpicklerObject *self)
if (self->pers_func) {
if ((len = _Unpickler_Readline(self, &s)) < 0)
return -1;
if (len < 2)
if (len < 1)
return bad_readline();
pid = PyBytes_FromStringAndSize(s, len - 1);