0001 """Unit tests for the copy module.""" 0002 0003 import sys 0004 import copy 0005 import copy_reg 0006 0007 import unittest 0008 from test import test_support 0009 0010 class TestCopy(unittest.TestCase): 0011 0012 # Attempt full line coverage of copy.py from top to bottom 0013 0014 def test_exceptions(self): 0015 self.assert_(copy.Error is copy.error) 0016 self.assert_(issubclass(copy.Error, Exception)) 0017 0018 # The copy() method 0019 0020 def test_copy_basic(self): 0021 x = 42 0022 y = copy.copy(x) 0023 self.assertEqual(x, y) 0024 0025 def test_copy_copy(self): 0026 class C(object): 0027 def __init__(self, foo): 0028 self.foo = foo 0029 def __copy__(self): 0030 return C(self.foo) 0031 x = C(42) 0032 y = copy.copy(x) 0033 self.assertEqual(y.__class__, x.__class__) 0034 self.assertEqual(y.foo, x.foo) 0035 0036 def test_copy_registry(self): 0037 class C(object): 0038 def __new__(cls, foo): 0039 obj = object.__new__(cls) 0040 obj.foo = foo 0041 return obj 0042 def pickle_C(obj): 0043 return (C, (obj.foo,)) 0044 x = C(42) 0045 self.assertRaises(TypeError, copy.copy, x) 0046 copy_reg.pickle(C, pickle_C, C) 0047 y = copy.copy(x) 0048 0049 def test_copy_reduce_ex(self): 0050 class C(object): 0051 def __reduce_ex__(self, proto): 0052 return "" 0053 def __reduce__(self): 0054 raise test_support.TestFailed, "shouldn't call this" 0055 x = C() 0056 y = copy.copy(x) 0057 self.assert_(y is x) 0058 0059 def test_copy_reduce(self): 0060 class C(object): 0061 def __reduce__(self): 0062 return "" 0063 x = C() 0064 y = copy.copy(x) 0065 self.assert_(y is x) 0066 0067 def test_copy_cant(self): 0068 class C(object): 0069 def __getattribute__(self, name): 0070 if name.startswith("__reduce"): 0071 raise AttributeError, name 0072 return object.__getattribute__(self, name) 0073 x = C() 0074 self.assertRaises(copy.Error, copy.copy, x) 0075 0076 # Type-specific _copy_xxx() methods 0077 0078 def test_copy_atomic(self): 0079 class Classic: 0080 pass 0081 class NewStyle(object): 0082 pass 0083 def f(): 0084 pass 0085 tests = [None, 42, 2L**100, 3.14, True, False, 1j, 0086 "hello", u"hello\u1234", f.func_code, 0087 NewStyle, xrange(10), Classic, max] 0088 for x in tests: 0089 self.assert_(copy.copy(x) is x, repr(x)) 0090 0091 def test_copy_list(self): 0092 x = [1, 2, 3] 0093 self.assertEqual(copy.copy(x), x) 0094 0095 def test_copy_tuple(self): 0096 x = (1, 2, 3) 0097 self.assertEqual(copy.copy(x), x) 0098 0099 def test_copy_dict(self): 0100 x = {"foo": 1, "bar": 2} 0101 self.assertEqual(copy.copy(x), x) 0102 0103 def test_copy_inst_vanilla(self): 0104 class C: 0105 def __init__(self, foo): 0106 self.foo = foo 0107 def __cmp__(self, other): 0108 return cmp(self.foo, other.foo) 0109 x = C(42) 0110 self.assertEqual(copy.copy(x), x) 0111 0112 def test_copy_inst_copy(self): 0113 class C: 0114 def __init__(self, foo): 0115 self.foo = foo 0116 def __copy__(self): 0117 return C(self.foo) 0118 def __cmp__(self, other): 0119 return cmp(self.foo, other.foo) 0120 x = C(42) 0121 self.assertEqual(copy.copy(x), x) 0122 0123 def test_copy_inst_getinitargs(self): 0124 class C: 0125 def __init__(self, foo): 0126 self.foo = foo 0127 def __getinitargs__(self): 0128 return (self.foo,) 0129 def __cmp__(self, other): 0130 return cmp(self.foo, other.foo) 0131 x = C(42) 0132 self.assertEqual(copy.copy(x), x) 0133 0134 def test_copy_inst_getstate(self): 0135 class C: 0136 def __init__(self, foo): 0137 self.foo = foo 0138 def __getstate__(self): 0139 return {"foo": self.foo} 0140 def __cmp__(self, other): 0141 return cmp(self.foo, other.foo) 0142 x = C(42) 0143 self.assertEqual(copy.copy(x), x) 0144 0145 def test_copy_inst_setstate(self): 0146 class C: 0147 def __init__(self, foo): 0148 self.foo = foo 0149 def __setstate__(self, state): 0150 self.foo = state["foo"] 0151 def __cmp__(self, other): 0152 return cmp(self.foo, other.foo) 0153 x = C(42) 0154 self.assertEqual(copy.copy(x), x) 0155 0156 def test_copy_inst_getstate_setstate(self): 0157 class C: 0158 def __init__(self, foo): 0159 self.foo = foo 0160 def __getstate__(self): 0161 return self.foo 0162 def __setstate__(self, state): 0163 self.foo = state 0164 def __cmp__(self, other): 0165 return cmp(self.foo, other.foo) 0166 x = C(42) 0167 self.assertEqual(copy.copy(x), x) 0168 0169 # The deepcopy() method 0170 0171 def test_deepcopy_basic(self): 0172 x = 42 0173 y = copy.deepcopy(x) 0174 self.assertEqual(y, x) 0175 0176 def test_deepcopy_memo(self): 0177 # Tests of reflexive objects are under type-specific sections below. 0178 # This tests only repetitions of objects. 0179 x = [] 0180 x = [x, x] 0181 y = copy.deepcopy(x) 0182 self.assertEqual(y, x) 0183 self.assert_(y is not x) 0184 self.assert_(y[0] is not x[0]) 0185 self.assert_(y[0] is y[1]) 0186 0187 def test_deepcopy_issubclass(self): 0188 # XXX Note: there's no way to test the TypeError coming out of 0189 # issubclass() -- this can only happen when an extension 0190 # module defines a "type" that doesn't formally inherit from 0191 # type. 0192 class Meta(type): 0193 pass 0194 class C: 0195 __metaclass__ = Meta 0196 self.assertEqual(copy.deepcopy(C), C) 0197 0198 def test_deepcopy_deepcopy(self): 0199 class C(object): 0200 def __init__(self, foo): 0201 self.foo = foo 0202 def __deepcopy__(self, memo=None): 0203 return C(self.foo) 0204 x = C(42) 0205 y = copy.deepcopy(x) 0206 self.assertEqual(y.__class__, x.__class__) 0207 self.assertEqual(y.foo, x.foo) 0208 0209 def test_deepcopy_registry(self): 0210 class C(object): 0211 def __new__(cls, foo): 0212 obj = object.__new__(cls) 0213 obj.foo = foo 0214 return obj 0215 def pickle_C(obj): 0216 return (C, (obj.foo,)) 0217 x = C(42) 0218 self.assertRaises(TypeError, copy.deepcopy, x) 0219 copy_reg.pickle(C, pickle_C, C) 0220 y = copy.deepcopy(x) 0221 0222 def test_deepcopy_reduce_ex(self): 0223 class C(object): 0224 def __reduce_ex__(self, proto): 0225 return "" 0226 def __reduce__(self): 0227 raise test_support.TestFailed, "shouldn't call this" 0228 x = C() 0229 y = copy.deepcopy(x) 0230 self.assert_(y is x) 0231 0232 def test_deepcopy_reduce(self): 0233 class C(object): 0234 def __reduce__(self): 0235 return "" 0236 x = C() 0237 y = copy.deepcopy(x) 0238 self.assert_(y is x) 0239 0240 def test_deepcopy_cant(self): 0241 class C(object): 0242 def __getattribute__(self, name): 0243 if name.startswith("__reduce"): 0244 raise AttributeError, name 0245 return object.__getattribute__(self, name) 0246 x = C() 0247 self.assertRaises(copy.Error, copy.deepcopy, x) 0248 0249 # Type-specific _deepcopy_xxx() methods 0250 0251 def test_deepcopy_atomic(self): 0252 class Classic: 0253 pass 0254 class NewStyle(object): 0255 pass 0256 def f(): 0257 pass 0258 tests = [None, 42, 2L**100, 3.14, True, False, 1j, 0259 "hello", u"hello\u1234", f.func_code, 0260 NewStyle, xrange(10), Classic, max] 0261 for x in tests: 0262 self.assert_(copy.deepcopy(x) is x, repr(x)) 0263 0264 def test_deepcopy_list(self): 0265 x = [[1, 2], 3] 0266 y = copy.deepcopy(x) 0267 self.assertEqual(y, x) 0268 self.assert_(x is not y) 0269 self.assert_(x[0] is not y[0]) 0270 0271 def test_deepcopy_reflexive_list(self): 0272 x = [] 0273 x.append(x) 0274 y = copy.deepcopy(x) 0275 self.assertRaises(RuntimeError, cmp, y, x) 0276 self.assert_(y is not x) 0277 self.assert_(y[0] is y) 0278 self.assertEqual(len(y), 1) 0279 0280 def test_deepcopy_tuple(self): 0281 x = ([1, 2], 3) 0282 y = copy.deepcopy(x) 0283 self.assertEqual(y, x) 0284 self.assert_(x is not y) 0285 self.assert_(x[0] is not y[0]) 0286 0287 def test_deepcopy_reflexive_tuple(self): 0288 x = ([],) 0289 x[0].append(x) 0290 y = copy.deepcopy(x) 0291 self.assertRaises(RuntimeError, cmp, y, x) 0292 self.assert_(y is not x) 0293 self.assert_(y[0] is not x[0]) 0294 self.assert_(y[0][0] is y) 0295 0296 def test_deepcopy_dict(self): 0297 x = {"foo": [1, 2], "bar": 3} 0298 y = copy.deepcopy(x) 0299 self.assertEqual(y, x) 0300 self.assert_(x is not y) 0301 self.assert_(x["foo"] is not y["foo"]) 0302 0303 def test_deepcopy_reflexive_dict(self): 0304 x = {} 0305 x['foo'] = x 0306 y = copy.deepcopy(x) 0307 self.assertRaises(RuntimeError, cmp, y, x) 0308 self.assert_(y is not x) 0309 self.assert_(y['foo'] is y) 0310 self.assertEqual(len(y), 1) 0311 0312 def test_deepcopy_keepalive(self): 0313 memo = {} 0314 x = 42 0315 y = copy.deepcopy(x, memo) 0316 self.assert_(memo[id(x)] is x) 0317 0318 def test_deepcopy_inst_vanilla(self): 0319 class C: 0320 def __init__(self, foo): 0321 self.foo = foo 0322 def __cmp__(self, other): 0323 return cmp(self.foo, other.foo) 0324 x = C([42]) 0325 y = copy.deepcopy(x) 0326 self.assertEqual(y, x) 0327 self.assert_(y.foo is not x.foo) 0328 0329 def test_deepcopy_inst_deepcopy(self): 0330 class C: 0331 def __init__(self, foo): 0332 self.foo = foo 0333 def __deepcopy__(self, memo): 0334 return C(copy.deepcopy(self.foo, memo)) 0335 def __cmp__(self, other): 0336 return cmp(self.foo, other.foo) 0337 x = C([42]) 0338 y = copy.deepcopy(x) 0339 self.assertEqual(y, x) 0340 self.assert_(y is not x) 0341 self.assert_(y.foo is not x.foo) 0342 0343 def test_deepcopy_inst_getinitargs(self): 0344 class C: 0345 def __init__(self, foo): 0346 self.foo = foo 0347 def __getinitargs__(self): 0348 return (self.foo,) 0349 def __cmp__(self, other): 0350 return cmp(self.foo, other.foo) 0351 x = C([42]) 0352 y = copy.deepcopy(x) 0353 self.assertEqual(y, x) 0354 self.assert_(y is not x) 0355 self.assert_(y.foo is not x.foo) 0356 0357 def test_deepcopy_inst_getstate(self): 0358 class C: 0359 def __init__(self, foo): 0360 self.foo = foo 0361 def __getstate__(self): 0362 return {"foo": self.foo} 0363 def __cmp__(self, other): 0364 return cmp(self.foo, other.foo) 0365 x = C([42]) 0366 y = copy.deepcopy(x) 0367 self.assertEqual(y, x) 0368 self.assert_(y is not x) 0369 self.assert_(y.foo is not x.foo) 0370 0371 def test_deepcopy_inst_setstate(self): 0372 class C: 0373 def __init__(self, foo): 0374 self.foo = foo 0375 def __setstate__(self, state): 0376 self.foo = state["foo"] 0377 def __cmp__(self, other): 0378 return cmp(self.foo, other.foo) 0379 x = C([42]) 0380 y = copy.deepcopy(x) 0381 self.assertEqual(y, x) 0382 self.assert_(y is not x) 0383 self.assert_(y.foo is not x.foo) 0384 0385 def test_deepcopy_inst_getstate_setstate(self): 0386 class C: 0387 def __init__(self, foo): 0388 self.foo = foo 0389 def __getstate__(self): 0390 return self.foo 0391 def __setstate__(self, state): 0392 self.foo = state 0393 def __cmp__(self, other): 0394 return cmp(self.foo, other.foo) 0395 x = C([42]) 0396 y = copy.deepcopy(x) 0397 self.assertEqual(y, x) 0398 self.assert_(y is not x) 0399 self.assert_(y.foo is not x.foo) 0400 0401 def test_deepcopy_reflexive_inst(self): 0402 class C: 0403 pass 0404 x = C() 0405 x.foo = x 0406 y = copy.deepcopy(x) 0407 self.assert_(y is not x) 0408 self.assert_(y.foo is y) 0409 0410 # _reconstruct() 0411 0412 def test_reconstruct_string(self): 0413 class C(object): 0414 def __reduce__(self): 0415 return "" 0416 x = C() 0417 y = copy.copy(x) 0418 self.assert_(y is x) 0419 y = copy.deepcopy(x) 0420 self.assert_(y is x) 0421 0422 def test_reconstruct_nostate(self): 0423 class C(object): 0424 def __reduce__(self): 0425 return (C, ()) 0426 x = C() 0427 x.foo = 42 0428 y = copy.copy(x) 0429 self.assert_(y.__class__ is x.__class__) 0430 y = copy.deepcopy(x) 0431 self.assert_(y.__class__ is x.__class__) 0432 0433 def test_reconstruct_state(self): 0434 class C(object): 0435 def __reduce__(self): 0436 return (C, (), self.__dict__) 0437 def __cmp__(self, other): 0438 return cmp(self.__dict__, other.__dict__) 0439 x = C() 0440 x.foo = [42] 0441 y = copy.copy(x) 0442 self.assertEqual(y, x) 0443 y = copy.deepcopy(x) 0444 self.assertEqual(y, x) 0445 self.assert_(y.foo is not x.foo) 0446 0447 def test_reconstruct_state_setstate(self): 0448 class C(object): 0449 def __reduce__(self): 0450 return (C, (), self.__dict__) 0451 def __setstate__(self, state): 0452 self.__dict__.update(state) 0453 def __cmp__(self, other): 0454 return cmp(self.__dict__, other.__dict__) 0455 x = C() 0456 x.foo = [42] 0457 y = copy.copy(x) 0458 self.assertEqual(y, x) 0459 y = copy.deepcopy(x) 0460 self.assertEqual(y, x) 0461 self.assert_(y.foo is not x.foo) 0462 0463 def test_reconstruct_reflexive(self): 0464 class C(object): 0465 pass 0466 x = C() 0467 x.foo = x 0468 y = copy.deepcopy(x) 0469 self.assert_(y is not x) 0470 self.assert_(y.foo is y) 0471 0472 # Additions for Python 2.3 and pickle protocol 2 0473 0474 def test_reduce_4tuple(self): 0475 class C(list): 0476 def __reduce__(self): 0477 return (C, (), self.__dict__, iter(self)) 0478 def __cmp__(self, other): 0479 return (cmp(list(self), list(other)) or 0480 cmp(self.__dict__, other.__dict__)) 0481 x = C([[1, 2], 3]) 0482 y = copy.copy(x) 0483 self.assertEqual(x, y) 0484 self.assert_(x is not y) 0485 self.assert_(x[0] is y[0]) 0486 y = copy.deepcopy(x) 0487 self.assertEqual(x, y) 0488 self.assert_(x is not y) 0489 self.assert_(x[0] is not y[0]) 0490 0491 def test_reduce_5tuple(self): 0492 class C(dict): 0493 def __reduce__(self): 0494 return (C, (), self.__dict__, None, self.iteritems()) 0495 def __cmp__(self, other): 0496 return (cmp(dict(self), list(dict)) or 0497 cmp(self.__dict__, other.__dict__)) 0498 x = C([("foo", [1, 2]), ("bar", 3)]) 0499 y = copy.copy(x) 0500 self.assertEqual(x, y) 0501 self.assert_(x is not y) 0502 self.assert_(x["foo"] is y["foo"]) 0503 y = copy.deepcopy(x) 0504 self.assertEqual(x, y) 0505 self.assert_(x is not y) 0506 self.assert_(x["foo"] is not y["foo"]) 0507 0508 def test_copy_slots(self): 0509 class C(object): 0510 __slots__ = ["foo"] 0511 x = C() 0512 x.foo = [42] 0513 y = copy.copy(x) 0514 self.assert_(x.foo is y.foo) 0515 0516 def test_deepcopy_slots(self): 0517 class C(object): 0518 __slots__ = ["foo"] 0519 x = C() 0520 x.foo = [42] 0521 y = copy.deepcopy(x) 0522 self.assertEqual(x.foo, y.foo) 0523 self.assert_(x.foo is not y.foo) 0524 0525 def test_copy_list_subclass(self): 0526 class C(list): 0527 pass 0528 x = C([[1, 2], 3]) 0529 x.foo = [4, 5] 0530 y = copy.copy(x) 0531 self.assertEqual(list(x), list(y)) 0532 self.assertEqual(x.foo, y.foo) 0533 self.assert_(x[0] is y[0]) 0534 self.assert_(x.foo is y.foo) 0535 0536 def test_deepcopy_list_subclass(self): 0537 class C(list): 0538 pass 0539 x = C([[1, 2], 3]) 0540 x.foo = [4, 5] 0541 y = copy.deepcopy(x) 0542 self.assertEqual(list(x), list(y)) 0543 self.assertEqual(x.foo, y.foo) 0544 self.assert_(x[0] is not y[0]) 0545 self.assert_(x.foo is not y.foo) 0546 0547 def test_copy_tuple_subclass(self): 0548 class C(tuple): 0549 pass 0550 x = C([1, 2, 3]) 0551 self.assertEqual(tuple(x), (1, 2, 3)) 0552 y = copy.copy(x) 0553 self.assertEqual(tuple(y), (1, 2, 3)) 0554 0555 def test_deepcopy_tuple_subclass(self): 0556 class C(tuple): 0557 pass 0558 x = C([[1, 2], 3]) 0559 self.assertEqual(tuple(x), ([1, 2], 3)) 0560 y = copy.deepcopy(x) 0561 self.assertEqual(tuple(y), ([1, 2], 3)) 0562 self.assert_(x is not y) 0563 self.assert_(x[0] is not y[0]) 0564 0565 def test_getstate_exc(self): 0566 class EvilState(object): 0567 def __getstate__(self): 0568 raise ValueError, "ain't got no stickin' state" 0569 self.assertRaises(ValueError, copy.copy, EvilState()) 0570 0571 def test_main(): 0572 test_support.run_unittest(TestCopy) 0573 0574 if __name__ == "__main__": 0575 test_main() 0576
Generated by PyXR 0.9.4