1import unittest.mock 2from test import support 3import builtins 4import contextlib 5import copy 6import io 7import os 8import pickle 9import shutil 10import subprocess 11import sys 12 13py_uuid = support.import_fresh_module('uuid', blocked=['_uuid']) 14c_uuid = support.import_fresh_module('uuid', fresh=['_uuid']) 15 16 17def importable(name): 18 try: 19 __import__(name) 20 return True 21 except: 22 return False 23 24 25class BaseTestUUID: 26 uuid = None 27 28 def test_UUID(self): 29 equal = self.assertEqual 30 ascending = [] 31 for (string, curly, hex, bytes, bytes_le, fields, integer, urn, 32 time, clock_seq, variant, version) in [ 33 ('00000000-0000-0000-0000-000000000000', 34 '{00000000-0000-0000-0000-000000000000}', 35 '00000000000000000000000000000000', 36 b'\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0', 37 b'\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0', 38 (0, 0, 0, 0, 0, 0), 39 0, 40 'urn:uuid:00000000-0000-0000-0000-000000000000', 41 0, 0, self.uuid.RESERVED_NCS, None), 42 ('00010203-0405-0607-0809-0a0b0c0d0e0f', 43 '{00010203-0405-0607-0809-0a0b0c0d0e0f}', 44 '000102030405060708090a0b0c0d0e0f', 45 b'\0\x01\x02\x03\x04\x05\x06\x07\x08\t\n\x0b\x0c\x0d\x0e\x0f', 46 b'\x03\x02\x01\0\x05\x04\x07\x06\x08\t\n\x0b\x0c\x0d\x0e\x0f', 47 (0x00010203, 0x0405, 0x0607, 8, 9, 0x0a0b0c0d0e0f), 48 0x000102030405060708090a0b0c0d0e0f, 49 'urn:uuid:00010203-0405-0607-0809-0a0b0c0d0e0f', 50 0x607040500010203, 0x809, self.uuid.RESERVED_NCS, None), 51 ('02d9e6d5-9467-382e-8f9b-9300a64ac3cd', 52 '{02d9e6d5-9467-382e-8f9b-9300a64ac3cd}', 53 '02d9e6d59467382e8f9b9300a64ac3cd', 54 b'\x02\xd9\xe6\xd5\x94\x67\x38\x2e\x8f\x9b\x93\x00\xa6\x4a\xc3\xcd', 55 b'\xd5\xe6\xd9\x02\x67\x94\x2e\x38\x8f\x9b\x93\x00\xa6\x4a\xc3\xcd', 56 (0x02d9e6d5, 0x9467, 0x382e, 0x8f, 0x9b, 0x9300a64ac3cd), 57 0x02d9e6d59467382e8f9b9300a64ac3cd, 58 'urn:uuid:02d9e6d5-9467-382e-8f9b-9300a64ac3cd', 59 0x82e946702d9e6d5, 0xf9b, self.uuid.RFC_4122, 3), 60 ('12345678-1234-5678-1234-567812345678', 61 '{12345678-1234-5678-1234-567812345678}', 62 '12345678123456781234567812345678', 63 b'\x12\x34\x56\x78'*4, 64 b'\x78\x56\x34\x12\x34\x12\x78\x56\x12\x34\x56\x78\x12\x34\x56\x78', 65 (0x12345678, 0x1234, 0x5678, 0x12, 0x34, 0x567812345678), 66 0x12345678123456781234567812345678, 67 'urn:uuid:12345678-1234-5678-1234-567812345678', 68 0x678123412345678, 0x1234, self.uuid.RESERVED_NCS, None), 69 ('6ba7b810-9dad-11d1-80b4-00c04fd430c8', 70 '{6ba7b810-9dad-11d1-80b4-00c04fd430c8}', 71 '6ba7b8109dad11d180b400c04fd430c8', 72 b'\x6b\xa7\xb8\x10\x9d\xad\x11\xd1\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 73 b'\x10\xb8\xa7\x6b\xad\x9d\xd1\x11\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 74 (0x6ba7b810, 0x9dad, 0x11d1, 0x80, 0xb4, 0x00c04fd430c8), 75 0x6ba7b8109dad11d180b400c04fd430c8, 76 'urn:uuid:6ba7b810-9dad-11d1-80b4-00c04fd430c8', 77 0x1d19dad6ba7b810, 0xb4, self.uuid.RFC_4122, 1), 78 ('6ba7b811-9dad-11d1-80b4-00c04fd430c8', 79 '{6ba7b811-9dad-11d1-80b4-00c04fd430c8}', 80 '6ba7b8119dad11d180b400c04fd430c8', 81 b'\x6b\xa7\xb8\x11\x9d\xad\x11\xd1\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 82 b'\x11\xb8\xa7\x6b\xad\x9d\xd1\x11\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 83 (0x6ba7b811, 0x9dad, 0x11d1, 0x80, 0xb4, 0x00c04fd430c8), 84 0x6ba7b8119dad11d180b400c04fd430c8, 85 'urn:uuid:6ba7b811-9dad-11d1-80b4-00c04fd430c8', 86 0x1d19dad6ba7b811, 0xb4, self.uuid.RFC_4122, 1), 87 ('6ba7b812-9dad-11d1-80b4-00c04fd430c8', 88 '{6ba7b812-9dad-11d1-80b4-00c04fd430c8}', 89 '6ba7b8129dad11d180b400c04fd430c8', 90 b'\x6b\xa7\xb8\x12\x9d\xad\x11\xd1\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 91 b'\x12\xb8\xa7\x6b\xad\x9d\xd1\x11\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 92 (0x6ba7b812, 0x9dad, 0x11d1, 0x80, 0xb4, 0x00c04fd430c8), 93 0x6ba7b8129dad11d180b400c04fd430c8, 94 'urn:uuid:6ba7b812-9dad-11d1-80b4-00c04fd430c8', 95 0x1d19dad6ba7b812, 0xb4, self.uuid.RFC_4122, 1), 96 ('6ba7b814-9dad-11d1-80b4-00c04fd430c8', 97 '{6ba7b814-9dad-11d1-80b4-00c04fd430c8}', 98 '6ba7b8149dad11d180b400c04fd430c8', 99 b'\x6b\xa7\xb8\x14\x9d\xad\x11\xd1\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 100 b'\x14\xb8\xa7\x6b\xad\x9d\xd1\x11\x80\xb4\x00\xc0\x4f\xd4\x30\xc8', 101 (0x6ba7b814, 0x9dad, 0x11d1, 0x80, 0xb4, 0x00c04fd430c8), 102 0x6ba7b8149dad11d180b400c04fd430c8, 103 'urn:uuid:6ba7b814-9dad-11d1-80b4-00c04fd430c8', 104 0x1d19dad6ba7b814, 0xb4, self.uuid.RFC_4122, 1), 105 ('7d444840-9dc0-11d1-b245-5ffdce74fad2', 106 '{7d444840-9dc0-11d1-b245-5ffdce74fad2}', 107 '7d4448409dc011d1b2455ffdce74fad2', 108 b'\x7d\x44\x48\x40\x9d\xc0\x11\xd1\xb2\x45\x5f\xfd\xce\x74\xfa\xd2', 109 b'\x40\x48\x44\x7d\xc0\x9d\xd1\x11\xb2\x45\x5f\xfd\xce\x74\xfa\xd2', 110 (0x7d444840, 0x9dc0, 0x11d1, 0xb2, 0x45, 0x5ffdce74fad2), 111 0x7d4448409dc011d1b2455ffdce74fad2, 112 'urn:uuid:7d444840-9dc0-11d1-b245-5ffdce74fad2', 113 0x1d19dc07d444840, 0x3245, self.uuid.RFC_4122, 1), 114 ('e902893a-9d22-3c7e-a7b8-d6e313b71d9f', 115 '{e902893a-9d22-3c7e-a7b8-d6e313b71d9f}', 116 'e902893a9d223c7ea7b8d6e313b71d9f', 117 b'\xe9\x02\x89\x3a\x9d\x22\x3c\x7e\xa7\xb8\xd6\xe3\x13\xb7\x1d\x9f', 118 b'\x3a\x89\x02\xe9\x22\x9d\x7e\x3c\xa7\xb8\xd6\xe3\x13\xb7\x1d\x9f', 119 (0xe902893a, 0x9d22, 0x3c7e, 0xa7, 0xb8, 0xd6e313b71d9f), 120 0xe902893a9d223c7ea7b8d6e313b71d9f, 121 'urn:uuid:e902893a-9d22-3c7e-a7b8-d6e313b71d9f', 122 0xc7e9d22e902893a, 0x27b8, self.uuid.RFC_4122, 3), 123 ('eb424026-6f54-4ef8-a4d0-bb658a1fc6cf', 124 '{eb424026-6f54-4ef8-a4d0-bb658a1fc6cf}', 125 'eb4240266f544ef8a4d0bb658a1fc6cf', 126 b'\xeb\x42\x40\x26\x6f\x54\x4e\xf8\xa4\xd0\xbb\x65\x8a\x1f\xc6\xcf', 127 b'\x26\x40\x42\xeb\x54\x6f\xf8\x4e\xa4\xd0\xbb\x65\x8a\x1f\xc6\xcf', 128 (0xeb424026, 0x6f54, 0x4ef8, 0xa4, 0xd0, 0xbb658a1fc6cf), 129 0xeb4240266f544ef8a4d0bb658a1fc6cf, 130 'urn:uuid:eb424026-6f54-4ef8-a4d0-bb658a1fc6cf', 131 0xef86f54eb424026, 0x24d0, self.uuid.RFC_4122, 4), 132 ('f81d4fae-7dec-11d0-a765-00a0c91e6bf6', 133 '{f81d4fae-7dec-11d0-a765-00a0c91e6bf6}', 134 'f81d4fae7dec11d0a76500a0c91e6bf6', 135 b'\xf8\x1d\x4f\xae\x7d\xec\x11\xd0\xa7\x65\x00\xa0\xc9\x1e\x6b\xf6', 136 b'\xae\x4f\x1d\xf8\xec\x7d\xd0\x11\xa7\x65\x00\xa0\xc9\x1e\x6b\xf6', 137 (0xf81d4fae, 0x7dec, 0x11d0, 0xa7, 0x65, 0x00a0c91e6bf6), 138 0xf81d4fae7dec11d0a76500a0c91e6bf6, 139 'urn:uuid:f81d4fae-7dec-11d0-a765-00a0c91e6bf6', 140 0x1d07decf81d4fae, 0x2765, self.uuid.RFC_4122, 1), 141 ('fffefdfc-fffe-fffe-fffe-fffefdfcfbfa', 142 '{fffefdfc-fffe-fffe-fffe-fffefdfcfbfa}', 143 'fffefdfcfffefffefffefffefdfcfbfa', 144 b'\xff\xfe\xfd\xfc\xff\xfe\xff\xfe\xff\xfe\xff\xfe\xfd\xfc\xfb\xfa', 145 b'\xfc\xfd\xfe\xff\xfe\xff\xfe\xff\xff\xfe\xff\xfe\xfd\xfc\xfb\xfa', 146 (0xfffefdfc, 0xfffe, 0xfffe, 0xff, 0xfe, 0xfffefdfcfbfa), 147 0xfffefdfcfffefffefffefffefdfcfbfa, 148 'urn:uuid:fffefdfc-fffe-fffe-fffe-fffefdfcfbfa', 149 0xffefffefffefdfc, 0x3ffe, self.uuid.RESERVED_FUTURE, None), 150 ('ffffffff-ffff-ffff-ffff-ffffffffffff', 151 '{ffffffff-ffff-ffff-ffff-ffffffffffff}', 152 'ffffffffffffffffffffffffffffffff', 153 b'\xff'*16, 154 b'\xff'*16, 155 (0xffffffff, 0xffff, 0xffff, 0xff, 0xff, 0xffffffffffff), 156 0xffffffffffffffffffffffffffffffff, 157 'urn:uuid:ffffffff-ffff-ffff-ffff-ffffffffffff', 158 0xfffffffffffffff, 0x3fff, self.uuid.RESERVED_FUTURE, None), 159 ]: 160 equivalents = [] 161 # Construct each UUID in several different ways. 162 for u in [self.uuid.UUID(string), self.uuid.UUID(curly), self.uuid.UUID(hex), 163 self.uuid.UUID(bytes=bytes), self.uuid.UUID(bytes_le=bytes_le), 164 self.uuid.UUID(fields=fields), self.uuid.UUID(int=integer), 165 self.uuid.UUID(urn)]: 166 # Test all conversions and properties of the UUID object. 167 equal(str(u), string) 168 equal(int(u), integer) 169 equal(u.bytes, bytes) 170 equal(u.bytes_le, bytes_le) 171 equal(u.fields, fields) 172 equal(u.time_low, fields[0]) 173 equal(u.time_mid, fields[1]) 174 equal(u.time_hi_version, fields[2]) 175 equal(u.clock_seq_hi_variant, fields[3]) 176 equal(u.clock_seq_low, fields[4]) 177 equal(u.node, fields[5]) 178 equal(u.hex, hex) 179 equal(u.int, integer) 180 equal(u.urn, urn) 181 equal(u.time, time) 182 equal(u.clock_seq, clock_seq) 183 equal(u.variant, variant) 184 equal(u.version, version) 185 equivalents.append(u) 186 187 # Different construction methods should give the same UUID. 188 for u in equivalents: 189 for v in equivalents: 190 equal(u, v) 191 192 # Bug 7380: "bytes" and "bytes_le" should give the same type. 193 equal(type(u.bytes), builtins.bytes) 194 equal(type(u.bytes_le), builtins.bytes) 195 196 ascending.append(u) 197 198 # Test comparison of UUIDs. 199 for i in range(len(ascending)): 200 for j in range(len(ascending)): 201 equal(i < j, ascending[i] < ascending[j]) 202 equal(i <= j, ascending[i] <= ascending[j]) 203 equal(i == j, ascending[i] == ascending[j]) 204 equal(i > j, ascending[i] > ascending[j]) 205 equal(i >= j, ascending[i] >= ascending[j]) 206 equal(i != j, ascending[i] != ascending[j]) 207 208 # Test sorting of UUIDs (above list is in ascending order). 209 resorted = ascending[:] 210 resorted.reverse() 211 resorted.sort() 212 equal(ascending, resorted) 213 214 def test_exceptions(self): 215 badvalue = lambda f: self.assertRaises(ValueError, f) 216 badtype = lambda f: self.assertRaises(TypeError, f) 217 218 # Badly formed hex strings. 219 badvalue(lambda: self.uuid.UUID('')) 220 badvalue(lambda: self.uuid.UUID('abc')) 221 badvalue(lambda: self.uuid.UUID('1234567812345678123456781234567')) 222 badvalue(lambda: self.uuid.UUID('123456781234567812345678123456789')) 223 badvalue(lambda: self.uuid.UUID('123456781234567812345678z2345678')) 224 225 # Badly formed bytes. 226 badvalue(lambda: self.uuid.UUID(bytes='abc')) 227 badvalue(lambda: self.uuid.UUID(bytes='\0'*15)) 228 badvalue(lambda: self.uuid.UUID(bytes='\0'*17)) 229 230 # Badly formed bytes_le. 231 badvalue(lambda: self.uuid.UUID(bytes_le='abc')) 232 badvalue(lambda: self.uuid.UUID(bytes_le='\0'*15)) 233 badvalue(lambda: self.uuid.UUID(bytes_le='\0'*17)) 234 235 # Badly formed fields. 236 badvalue(lambda: self.uuid.UUID(fields=(1,))) 237 badvalue(lambda: self.uuid.UUID(fields=(1, 2, 3, 4, 5))) 238 badvalue(lambda: self.uuid.UUID(fields=(1, 2, 3, 4, 5, 6, 7))) 239 240 # Field values out of range. 241 badvalue(lambda: self.uuid.UUID(fields=(-1, 0, 0, 0, 0, 0))) 242 badvalue(lambda: self.uuid.UUID(fields=(0x100000000, 0, 0, 0, 0, 0))) 243 badvalue(lambda: self.uuid.UUID(fields=(0, -1, 0, 0, 0, 0))) 244 badvalue(lambda: self.uuid.UUID(fields=(0, 0x10000, 0, 0, 0, 0))) 245 badvalue(lambda: self.uuid.UUID(fields=(0, 0, -1, 0, 0, 0))) 246 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0x10000, 0, 0, 0))) 247 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, -1, 0, 0))) 248 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, 0x100, 0, 0))) 249 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, 0, -1, 0))) 250 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, 0, 0x100, 0))) 251 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, 0, 0, -1))) 252 badvalue(lambda: self.uuid.UUID(fields=(0, 0, 0, 0, 0, 0x1000000000000))) 253 254 # Version number out of range. 255 badvalue(lambda: self.uuid.UUID('00'*16, version=0)) 256 badvalue(lambda: self.uuid.UUID('00'*16, version=6)) 257 258 # Integer value out of range. 259 badvalue(lambda: self.uuid.UUID(int=-1)) 260 badvalue(lambda: self.uuid.UUID(int=1<<128)) 261 262 # Must supply exactly one of hex, bytes, fields, int. 263 h, b, f, i = '00'*16, b'\0'*16, (0, 0, 0, 0, 0, 0), 0 264 self.uuid.UUID(h) 265 self.uuid.UUID(hex=h) 266 self.uuid.UUID(bytes=b) 267 self.uuid.UUID(bytes_le=b) 268 self.uuid.UUID(fields=f) 269 self.uuid.UUID(int=i) 270 271 # Wrong number of arguments (positional). 272 badtype(lambda: self.uuid.UUID()) 273 badtype(lambda: self.uuid.UUID(h, b)) 274 badtype(lambda: self.uuid.UUID(h, b, b)) 275 badtype(lambda: self.uuid.UUID(h, b, b, f)) 276 badtype(lambda: self.uuid.UUID(h, b, b, f, i)) 277 278 # Duplicate arguments. 279 for hh in [[], [('hex', h)]]: 280 for bb in [[], [('bytes', b)]]: 281 for bble in [[], [('bytes_le', b)]]: 282 for ii in [[], [('int', i)]]: 283 for ff in [[], [('fields', f)]]: 284 args = dict(hh + bb + bble + ii + ff) 285 if len(args) != 0: 286 badtype(lambda: self.uuid.UUID(h, **args)) 287 if len(args) != 1: 288 badtype(lambda: self.uuid.UUID(**args)) 289 290 # Immutability. 291 u = self.uuid.UUID(h) 292 badtype(lambda: setattr(u, 'hex', h)) 293 badtype(lambda: setattr(u, 'bytes', b)) 294 badtype(lambda: setattr(u, 'bytes_le', b)) 295 badtype(lambda: setattr(u, 'fields', f)) 296 badtype(lambda: setattr(u, 'int', i)) 297 badtype(lambda: setattr(u, 'time_low', 0)) 298 badtype(lambda: setattr(u, 'time_mid', 0)) 299 badtype(lambda: setattr(u, 'time_hi_version', 0)) 300 badtype(lambda: setattr(u, 'time_hi_version', 0)) 301 badtype(lambda: setattr(u, 'clock_seq_hi_variant', 0)) 302 badtype(lambda: setattr(u, 'clock_seq_low', 0)) 303 badtype(lambda: setattr(u, 'node', 0)) 304 305 # Comparison with a non-UUID object 306 badtype(lambda: u < object()) 307 badtype(lambda: u > object()) 308 309 def test_getnode(self): 310 node1 = self.uuid.getnode() 311 self.assertTrue(0 < node1 < (1 << 48), '%012x' % node1) 312 313 # Test it again to ensure consistency. 314 node2 = self.uuid.getnode() 315 self.assertEqual(node1, node2, '%012x != %012x' % (node1, node2)) 316 317 def test_pickle_roundtrip(self): 318 def check(actual, expected): 319 self.assertEqual(actual, expected) 320 self.assertEqual(actual.is_safe, expected.is_safe) 321 322 with support.swap_item(sys.modules, 'uuid', self.uuid): 323 for is_safe in self.uuid.SafeUUID: 324 u = self.uuid.UUID('d82579ce6642a0de7ddf490a7aec7aa5', 325 is_safe=is_safe) 326 check(copy.copy(u), u) 327 check(copy.deepcopy(u), u) 328 for proto in range(pickle.HIGHEST_PROTOCOL + 1): 329 with self.subTest(protocol=proto): 330 check(pickle.loads(pickle.dumps(u, proto)), u) 331 332 def test_unpickle_previous_python_versions(self): 333 def check(actual, expected): 334 self.assertEqual(actual, expected) 335 self.assertEqual(actual.is_safe, expected.is_safe) 336 337 pickled_uuids = [ 338 # Python 2.7, protocol 0 339 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 340 b'tR(dS\'int\'\nL287307832597519156748809049798316161701L\nsb.', 341 # Python 2.7, protocol 1 342 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 343 b'tR}U\x03intL287307832597519156748809049798316161701L\nsb.', 344 # Python 2.7, protocol 2 345 b'\x80\x02cuuid\nUUID\n)\x81}U\x03int\x8a\x11\xa5z\xecz\nI\xdf}' 346 b'\xde\xa0Bf\xcey%\xd8\x00sb.', 347 # Python 3.6, protocol 0 348 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 349 b'tR(dVint\nL287307832597519156748809049798316161701L\nsb.', 350 # Python 3.6, protocol 1 351 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 352 b'tR}X\x03\x00\x00\x00intL287307832597519156748809049798316161701L' 353 b'\nsb.', 354 # Python 3.6, protocol 2 355 b'\x80\x02cuuid\nUUID\n)\x81}X\x03\x00\x00\x00int\x8a\x11\xa5z\xec' 356 b'z\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00sb.', 357 # Python 3.6, protocol 3 358 b'\x80\x03cuuid\nUUID\n)\x81}X\x03\x00\x00\x00int\x8a\x11\xa5z\xec' 359 b'z\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00sb.', 360 # Python 3.6, protocol 4 361 b'\x80\x04\x95+\x00\x00\x00\x00\x00\x00\x00\x8c\x04uuid\x8c\x04UUI' 362 b'D\x93)\x81}\x8c\x03int\x8a\x11\xa5z\xecz\nI\xdf}\xde\xa0Bf\xcey%' 363 b'\xd8\x00sb.', 364 # Python 3.7, protocol 0 365 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 366 b'tR(dVint\nL287307832597519156748809049798316161701L\nsVis_safe\n' 367 b'cuuid\nSafeUUID\n(NtRsb.', 368 # Python 3.7, protocol 1 369 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 370 b'tR}(X\x03\x00\x00\x00intL287307832597519156748809049798316161701' 371 b'L\nX\x07\x00\x00\x00is_safecuuid\nSafeUUID\n(NtRub.', 372 # Python 3.7, protocol 2 373 b'\x80\x02cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 374 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 375 b'id\nSafeUUID\nN\x85Rub.', 376 # Python 3.7, protocol 3 377 b'\x80\x03cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 378 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 379 b'id\nSafeUUID\nN\x85Rub.', 380 # Python 3.7, protocol 4 381 b'\x80\x04\x95F\x00\x00\x00\x00\x00\x00\x00\x8c\x04uuid\x94\x8c' 382 b'\x04UUID\x93)\x81}(\x8c\x03int\x8a\x11\xa5z\xecz\nI\xdf}\xde\xa0' 383 b'Bf\xcey%\xd8\x00\x8c\x07is_safeh\x00\x8c\x08SafeUUID\x93N\x85Rub' 384 b'.', 385 ] 386 pickled_uuids_safe = [ 387 # Python 3.7, protocol 0 388 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 389 b'tR(dVint\nL287307832597519156748809049798316161701L\nsVis_safe\n' 390 b'cuuid\nSafeUUID\n(I0\ntRsb.', 391 # Python 3.7, protocol 1 392 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 393 b'tR}(X\x03\x00\x00\x00intL287307832597519156748809049798316161701' 394 b'L\nX\x07\x00\x00\x00is_safecuuid\nSafeUUID\n(K\x00tRub.', 395 # Python 3.7, protocol 2 396 b'\x80\x02cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 397 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 398 b'id\nSafeUUID\nK\x00\x85Rub.', 399 # Python 3.7, protocol 3 400 b'\x80\x03cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 401 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 402 b'id\nSafeUUID\nK\x00\x85Rub.', 403 # Python 3.7, protocol 4 404 b'\x80\x04\x95G\x00\x00\x00\x00\x00\x00\x00\x8c\x04uuid\x94\x8c' 405 b'\x04UUID\x93)\x81}(\x8c\x03int\x8a\x11\xa5z\xecz\nI\xdf}\xde\xa0' 406 b'Bf\xcey%\xd8\x00\x8c\x07is_safeh\x00\x8c\x08SafeUUID\x93K\x00' 407 b'\x85Rub.', 408 ] 409 pickled_uuids_unsafe = [ 410 # Python 3.7, protocol 0 411 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 412 b'tR(dVint\nL287307832597519156748809049798316161701L\nsVis_safe\n' 413 b'cuuid\nSafeUUID\n(I-1\ntRsb.', 414 # Python 3.7, protocol 1 415 b'ccopy_reg\n_reconstructor\n(cuuid\nUUID\nc__builtin__\nobject\nN' 416 b'tR}(X\x03\x00\x00\x00intL287307832597519156748809049798316161701' 417 b'L\nX\x07\x00\x00\x00is_safecuuid\nSafeUUID\n(J\xff\xff\xff\xfftR' 418 b'ub.', 419 # Python 3.7, protocol 2 420 b'\x80\x02cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 421 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 422 b'id\nSafeUUID\nJ\xff\xff\xff\xff\x85Rub.', 423 # Python 3.7, protocol 3 424 b'\x80\x03cuuid\nUUID\n)\x81}(X\x03\x00\x00\x00int\x8a\x11\xa5z' 425 b'\xecz\nI\xdf}\xde\xa0Bf\xcey%\xd8\x00X\x07\x00\x00\x00is_safecuu' 426 b'id\nSafeUUID\nJ\xff\xff\xff\xff\x85Rub.', 427 # Python 3.7, protocol 4 428 b'\x80\x04\x95J\x00\x00\x00\x00\x00\x00\x00\x8c\x04uuid\x94\x8c' 429 b'\x04UUID\x93)\x81}(\x8c\x03int\x8a\x11\xa5z\xecz\nI\xdf}\xde\xa0' 430 b'Bf\xcey%\xd8\x00\x8c\x07is_safeh\x00\x8c\x08SafeUUID\x93J\xff' 431 b'\xff\xff\xff\x85Rub.', 432 ] 433 434 u = self.uuid.UUID('d82579ce6642a0de7ddf490a7aec7aa5') 435 u_safe = self.uuid.UUID('d82579ce6642a0de7ddf490a7aec7aa5', 436 is_safe=self.uuid.SafeUUID.safe) 437 u_unsafe = self.uuid.UUID('d82579ce6642a0de7ddf490a7aec7aa5', 438 is_safe=self.uuid.SafeUUID.unsafe) 439 440 with support.swap_item(sys.modules, 'uuid', self.uuid): 441 for pickled in pickled_uuids: 442 # is_safe was added in 3.7. When unpickling values from older 443 # versions, is_safe will be missing, so it should be set to 444 # SafeUUID.unknown. 445 check(pickle.loads(pickled), u) 446 for pickled in pickled_uuids_safe: 447 check(pickle.loads(pickled), u_safe) 448 for pickled in pickled_uuids_unsafe: 449 check(pickle.loads(pickled), u_unsafe) 450 451 # bpo-32502: UUID1 requires a 48-bit identifier, but hardware identifiers 452 # need not necessarily be 48 bits (e.g., EUI-64). 453 def test_uuid1_eui64(self): 454 # Confirm that uuid.getnode ignores hardware addresses larger than 48 455 # bits. Mock out each platform's *_getnode helper functions to return 456 # something just larger than 48 bits to test. This will cause 457 # uuid.getnode to fall back on uuid._random_getnode, which will 458 # generate a valid value. 459 too_large_getter = lambda: 1 << 48 460 with unittest.mock.patch.multiple( 461 self.uuid, 462 _node=None, # Ignore any cached node value. 463 _NODE_GETTERS_WIN32=[too_large_getter], 464 _NODE_GETTERS_UNIX=[too_large_getter], 465 ): 466 node = self.uuid.getnode() 467 self.assertTrue(0 < node < (1 << 48), '%012x' % node) 468 469 # Confirm that uuid1 can use the generated node, i.e., the that 470 # uuid.getnode fell back on uuid._random_getnode() rather than using 471 # the value from too_large_getter above. 472 try: 473 self.uuid.uuid1(node=node) 474 except ValueError as e: 475 self.fail('uuid1 was given an invalid node ID') 476 477 def test_uuid1(self): 478 equal = self.assertEqual 479 480 # Make sure uuid1() generates UUIDs that are actually version 1. 481 for u in [self.uuid.uuid1() for i in range(10)]: 482 equal(u.variant, self.uuid.RFC_4122) 483 equal(u.version, 1) 484 self.assertIn(u.is_safe, {self.uuid.SafeUUID.safe, 485 self.uuid.SafeUUID.unsafe, 486 self.uuid.SafeUUID.unknown}) 487 488 # Make sure the generated UUIDs are actually unique. 489 uuids = {} 490 for u in [self.uuid.uuid1() for i in range(1000)]: 491 uuids[u] = 1 492 equal(len(uuids.keys()), 1000) 493 494 # Make sure the supplied node ID appears in the UUID. 495 u = self.uuid.uuid1(0) 496 equal(u.node, 0) 497 u = self.uuid.uuid1(0x123456789abc) 498 equal(u.node, 0x123456789abc) 499 u = self.uuid.uuid1(0xffffffffffff) 500 equal(u.node, 0xffffffffffff) 501 502 # Make sure the supplied clock sequence appears in the UUID. 503 u = self.uuid.uuid1(0x123456789abc, 0) 504 equal(u.node, 0x123456789abc) 505 equal(((u.clock_seq_hi_variant & 0x3f) << 8) | u.clock_seq_low, 0) 506 u = self.uuid.uuid1(0x123456789abc, 0x1234) 507 equal(u.node, 0x123456789abc) 508 equal(((u.clock_seq_hi_variant & 0x3f) << 8) | 509 u.clock_seq_low, 0x1234) 510 u = self.uuid.uuid1(0x123456789abc, 0x3fff) 511 equal(u.node, 0x123456789abc) 512 equal(((u.clock_seq_hi_variant & 0x3f) << 8) | 513 u.clock_seq_low, 0x3fff) 514 515 # bpo-29925: On Mac OS X Tiger, self.uuid.uuid1().is_safe returns 516 # self.uuid.SafeUUID.unknown 517 @support.requires_mac_ver(10, 5) 518 @unittest.skipUnless(os.name == 'posix', 'POSIX-only test') 519 def test_uuid1_safe(self): 520 if not self.uuid._has_uuid_generate_time_safe: 521 self.skipTest('requires uuid_generate_time_safe(3)') 522 523 u = self.uuid.uuid1() 524 # uuid_generate_time_safe() may return 0 or -1 but what it returns is 525 # dependent on the underlying platform support. At least it cannot be 526 # unknown (unless I suppose the platform is buggy). 527 self.assertNotEqual(u.is_safe, self.uuid.SafeUUID.unknown) 528 529 @contextlib.contextmanager 530 def mock_generate_time_safe(self, safe_value): 531 """ 532 Mock uuid._generate_time_safe() to return a given *safe_value*. 533 """ 534 if os.name != 'posix': 535 self.skipTest('POSIX-only test') 536 self.uuid._load_system_functions() 537 f = self.uuid._generate_time_safe 538 if f is None: 539 self.skipTest('need uuid._generate_time_safe') 540 with unittest.mock.patch.object(self.uuid, '_generate_time_safe', 541 lambda: (f()[0], safe_value)): 542 yield 543 544 @unittest.skipUnless(os.name == 'posix', 'POSIX-only test') 545 def test_uuid1_unknown(self): 546 # Even if the platform has uuid_generate_time_safe(), let's mock it to 547 # be uuid_generate_time() and ensure the safety is unknown. 548 with self.mock_generate_time_safe(None): 549 u = self.uuid.uuid1() 550 self.assertEqual(u.is_safe, self.uuid.SafeUUID.unknown) 551 552 @unittest.skipUnless(os.name == 'posix', 'POSIX-only test') 553 def test_uuid1_is_safe(self): 554 with self.mock_generate_time_safe(0): 555 u = self.uuid.uuid1() 556 self.assertEqual(u.is_safe, self.uuid.SafeUUID.safe) 557 558 @unittest.skipUnless(os.name == 'posix', 'POSIX-only test') 559 def test_uuid1_is_unsafe(self): 560 with self.mock_generate_time_safe(-1): 561 u = self.uuid.uuid1() 562 self.assertEqual(u.is_safe, self.uuid.SafeUUID.unsafe) 563 564 @unittest.skipUnless(os.name == 'posix', 'POSIX-only test') 565 def test_uuid1_bogus_return_value(self): 566 with self.mock_generate_time_safe(3): 567 u = self.uuid.uuid1() 568 self.assertEqual(u.is_safe, self.uuid.SafeUUID.unknown) 569 570 def test_uuid3(self): 571 equal = self.assertEqual 572 573 # Test some known version-3 UUIDs. 574 for u, v in [(self.uuid.uuid3(self.uuid.NAMESPACE_DNS, 'python.org'), 575 '6fa459ea-ee8a-3ca4-894e-db77e160355e'), 576 (self.uuid.uuid3(self.uuid.NAMESPACE_URL, 'http://python.org/'), 577 '9fe8e8c4-aaa8-32a9-a55c-4535a88b748d'), 578 (self.uuid.uuid3(self.uuid.NAMESPACE_OID, '1.3.6.1'), 579 'dd1a1cef-13d5-368a-ad82-eca71acd4cd1'), 580 (self.uuid.uuid3(self.uuid.NAMESPACE_X500, 'c=ca'), 581 '658d3002-db6b-3040-a1d1-8ddd7d189a4d'), 582 ]: 583 equal(u.variant, self.uuid.RFC_4122) 584 equal(u.version, 3) 585 equal(u, self.uuid.UUID(v)) 586 equal(str(u), v) 587 588 def test_uuid4(self): 589 equal = self.assertEqual 590 591 # Make sure uuid4() generates UUIDs that are actually version 4. 592 for u in [self.uuid.uuid4() for i in range(10)]: 593 equal(u.variant, self.uuid.RFC_4122) 594 equal(u.version, 4) 595 596 # Make sure the generated UUIDs are actually unique. 597 uuids = {} 598 for u in [self.uuid.uuid4() for i in range(1000)]: 599 uuids[u] = 1 600 equal(len(uuids.keys()), 1000) 601 602 def test_uuid5(self): 603 equal = self.assertEqual 604 605 # Test some known version-5 UUIDs. 606 for u, v in [(self.uuid.uuid5(self.uuid.NAMESPACE_DNS, 'python.org'), 607 '886313e1-3b8a-5372-9b90-0c9aee199e5d'), 608 (self.uuid.uuid5(self.uuid.NAMESPACE_URL, 'http://python.org/'), 609 '4c565f0d-3f5a-5890-b41b-20cf47701c5e'), 610 (self.uuid.uuid5(self.uuid.NAMESPACE_OID, '1.3.6.1'), 611 '1447fa61-5277-5fef-a9b3-fbc6e44f4af3'), 612 (self.uuid.uuid5(self.uuid.NAMESPACE_X500, 'c=ca'), 613 'cc957dd1-a972-5349-98cd-874190002798'), 614 ]: 615 equal(u.variant, self.uuid.RFC_4122) 616 equal(u.version, 5) 617 equal(u, self.uuid.UUID(v)) 618 equal(str(u), v) 619 620 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 621 def testIssue8621(self): 622 # On at least some versions of OSX self.uuid.uuid4 generates 623 # the same sequence of UUIDs in the parent and any 624 # children started using fork. 625 fds = os.pipe() 626 pid = os.fork() 627 if pid == 0: 628 os.close(fds[0]) 629 value = self.uuid.uuid4() 630 os.write(fds[1], value.hex.encode('latin-1')) 631 os._exit(0) 632 633 else: 634 os.close(fds[1]) 635 self.addCleanup(os.close, fds[0]) 636 parent_value = self.uuid.uuid4().hex 637 os.waitpid(pid, 0) 638 child_value = os.read(fds[0], 100).decode('latin-1') 639 640 self.assertNotEqual(parent_value, child_value) 641 642 643class TestUUIDWithoutExtModule(BaseTestUUID, unittest.TestCase): 644 uuid = py_uuid 645 646@unittest.skipUnless(c_uuid, 'requires the C _uuid module') 647class TestUUIDWithExtModule(BaseTestUUID, unittest.TestCase): 648 uuid = c_uuid 649 650 651class BaseTestInternals: 652 uuid = None 653 654 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 655 def test_find_mac(self): 656 data = ''' 657fake hwaddr 658cscotun0 Link encap:UNSPEC HWaddr 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00 659eth0 Link encap:Ethernet HWaddr 12:34:56:78:90:ab 660''' 661 662 popen = unittest.mock.MagicMock() 663 popen.stdout = io.BytesIO(data.encode()) 664 665 with unittest.mock.patch.object(shutil, 'which', 666 return_value='/sbin/ifconfig'): 667 with unittest.mock.patch.object(subprocess, 'Popen', 668 return_value=popen): 669 mac = self.uuid._find_mac( 670 command='ifconfig', 671 args='', 672 hw_identifiers=[b'hwaddr'], 673 get_index=lambda x: x + 1, 674 ) 675 676 self.assertEqual(mac, 0x1234567890ab) 677 678 def check_node(self, node, requires=None): 679 if requires and node is None: 680 self.skipTest('requires ' + requires) 681 hex = '%012x' % node 682 if support.verbose >= 2: 683 print(hex, end=' ') 684 self.assertTrue(0 < node < (1 << 48), 685 "%s is not an RFC 4122 node ID" % hex) 686 687 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 688 def test_ifconfig_getnode(self): 689 node = self.uuid._ifconfig_getnode() 690 self.check_node(node, 'ifconfig') 691 692 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 693 def test_ip_getnode(self): 694 node = self.uuid._ip_getnode() 695 self.check_node(node, 'ip') 696 697 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 698 def test_arp_getnode(self): 699 node = self.uuid._arp_getnode() 700 self.check_node(node, 'arp') 701 702 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 703 def test_lanscan_getnode(self): 704 node = self.uuid._lanscan_getnode() 705 self.check_node(node, 'lanscan') 706 707 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 708 def test_netstat_getnode(self): 709 node = self.uuid._netstat_getnode() 710 self.check_node(node, 'netstat') 711 712 @unittest.skipUnless(os.name == 'nt', 'requires Windows') 713 def test_ipconfig_getnode(self): 714 node = self.uuid._ipconfig_getnode() 715 self.check_node(node, 'ipconfig') 716 717 @unittest.skipUnless(importable('win32wnet'), 'requires win32wnet') 718 @unittest.skipUnless(importable('netbios'), 'requires netbios') 719 def test_netbios_getnode(self): 720 node = self.uuid._netbios_getnode() 721 self.check_node(node) 722 723 def test_random_getnode(self): 724 node = self.uuid._random_getnode() 725 # The multicast bit, i.e. the least significant bit of first octet, 726 # must be set for randomly generated MAC addresses. See RFC 4122, 727 # $4.1.6. 728 self.assertTrue(node & (1 << 40), '%012x' % node) 729 self.check_node(node) 730 731 node2 = self.uuid._random_getnode() 732 self.assertNotEqual(node2, node, '%012x' % node) 733 734 @unittest.skipUnless(os.name == 'posix', 'requires Posix') 735 def test_unix_getnode(self): 736 if not importable('_uuid') and not importable('ctypes'): 737 self.skipTest("neither _uuid extension nor ctypes available") 738 try: # Issues 1481, 3581: _uuid_generate_time() might be None. 739 node = self.uuid._unix_getnode() 740 except TypeError: 741 self.skipTest('requires uuid_generate_time') 742 self.check_node(node, 'unix') 743 744 @unittest.skipUnless(os.name == 'nt', 'requires Windows') 745 @unittest.skipUnless(importable('ctypes'), 'requires ctypes') 746 def test_windll_getnode(self): 747 node = self.uuid._windll_getnode() 748 self.check_node(node) 749 750 751class TestInternalsWithoutExtModule(BaseTestInternals, unittest.TestCase): 752 uuid = py_uuid 753 754@unittest.skipUnless(c_uuid, 'requires the C _uuid module') 755class TestInternalsWithExtModule(BaseTestInternals, unittest.TestCase): 756 uuid = c_uuid 757 758 759if __name__ == '__main__': 760 unittest.main() 761