/thirdparty/breakpad/third_party/protobuf/protobuf/python/google/protobuf/internal/reflection_test.py
Python | 1590 lines | 1519 code | 6 blank | 65 comment | 0 complexity | f6a12b3dfbdfb99bf9f89eaad6a8c3f9 MD5 | raw file
1#! /usr/bin/python 2# -*- coding: utf-8 -*- 3# 4# Protocol Buffers - Google's data interchange format 5# Copyright 2008 Google Inc. All rights reserved. 6# http://code.google.com/p/protobuf/ 7# 8# Redistribution and use in source and binary forms, with or without 9# modification, are permitted provided that the following conditions are 10# met: 11# 12# * Redistributions of source code must retain the above copyright 13# notice, this list of conditions and the following disclaimer. 14# * Redistributions in binary form must reproduce the above 15# copyright notice, this list of conditions and the following disclaimer 16# in the documentation and/or other materials provided with the 17# distribution. 18# * Neither the name of Google Inc. nor the names of its 19# contributors may be used to endorse or promote products derived from 20# this software without specific prior written permission. 21# 22# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 23# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 24# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 25# A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 26# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 27# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 28# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29# DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30# THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 32# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33 34"""Unittest for reflection.py, which also indirectly tests the output of the 35pure-Python protocol compiler. 36""" 37 38__author__ = 'robinson@google.com (Will Robinson)' 39 40import operator 41import struct 42 43import unittest 44from google.protobuf import unittest_import_pb2 45from google.protobuf import unittest_mset_pb2 46from google.protobuf import unittest_pb2 47from google.protobuf import descriptor_pb2 48from google.protobuf import descriptor 49from google.protobuf import message 50from google.protobuf import reflection 51from google.protobuf.internal import api_implementation 52from google.protobuf.internal import more_extensions_pb2 53from google.protobuf.internal import more_messages_pb2 54from google.protobuf.internal import wire_format 55from google.protobuf.internal import test_util 56from google.protobuf.internal import decoder 57 58 59class _MiniDecoder(object): 60 """Decodes a stream of values from a string. 61 62 Once upon a time we actually had a class called decoder.Decoder. Then we 63 got rid of it during a redesign that made decoding much, much faster overall. 64 But a couple tests in this file used it to check that the serialized form of 65 a message was correct. So, this class implements just the methods that were 66 used by said tests, so that we don't have to rewrite the tests. 67 """ 68 69 def __init__(self, bytes): 70 self._bytes = bytes 71 self._pos = 0 72 73 def ReadVarint(self): 74 result, self._pos = decoder._DecodeVarint(self._bytes, self._pos) 75 return result 76 77 ReadInt32 = ReadVarint 78 ReadInt64 = ReadVarint 79 ReadUInt32 = ReadVarint 80 ReadUInt64 = ReadVarint 81 82 def ReadSInt64(self): 83 return wire_format.ZigZagDecode(self.ReadVarint()) 84 85 ReadSInt32 = ReadSInt64 86 87 def ReadFieldNumberAndWireType(self): 88 return wire_format.UnpackTag(self.ReadVarint()) 89 90 def ReadFloat(self): 91 result = struct.unpack("<f", self._bytes[self._pos:self._pos+4])[0] 92 self._pos += 4 93 return result 94 95 def ReadDouble(self): 96 result = struct.unpack("<d", self._bytes[self._pos:self._pos+8])[0] 97 self._pos += 8 98 return result 99 100 def EndOfStream(self): 101 return self._pos == len(self._bytes) 102 103 104class ReflectionTest(unittest.TestCase): 105 106 def assertListsEqual(self, values, others): 107 self.assertEqual(len(values), len(others)) 108 for i in range(len(values)): 109 self.assertEqual(values[i], others[i]) 110 111 def testScalarConstructor(self): 112 # Constructor with only scalar types should succeed. 113 proto = unittest_pb2.TestAllTypes( 114 optional_int32=24, 115 optional_double=54.321, 116 optional_string='optional_string') 117 118 self.assertEqual(24, proto.optional_int32) 119 self.assertEqual(54.321, proto.optional_double) 120 self.assertEqual('optional_string', proto.optional_string) 121 122 def testRepeatedScalarConstructor(self): 123 # Constructor with only repeated scalar types should succeed. 124 proto = unittest_pb2.TestAllTypes( 125 repeated_int32=[1, 2, 3, 4], 126 repeated_double=[1.23, 54.321], 127 repeated_bool=[True, False, False], 128 repeated_string=["optional_string"]) 129 130 self.assertEquals([1, 2, 3, 4], list(proto.repeated_int32)) 131 self.assertEquals([1.23, 54.321], list(proto.repeated_double)) 132 self.assertEquals([True, False, False], list(proto.repeated_bool)) 133 self.assertEquals(["optional_string"], list(proto.repeated_string)) 134 135 def testRepeatedCompositeConstructor(self): 136 # Constructor with only repeated composite types should succeed. 137 proto = unittest_pb2.TestAllTypes( 138 repeated_nested_message=[ 139 unittest_pb2.TestAllTypes.NestedMessage( 140 bb=unittest_pb2.TestAllTypes.FOO), 141 unittest_pb2.TestAllTypes.NestedMessage( 142 bb=unittest_pb2.TestAllTypes.BAR)], 143 repeated_foreign_message=[ 144 unittest_pb2.ForeignMessage(c=-43), 145 unittest_pb2.ForeignMessage(c=45324), 146 unittest_pb2.ForeignMessage(c=12)], 147 repeatedgroup=[ 148 unittest_pb2.TestAllTypes.RepeatedGroup(), 149 unittest_pb2.TestAllTypes.RepeatedGroup(a=1), 150 unittest_pb2.TestAllTypes.RepeatedGroup(a=2)]) 151 152 self.assertEquals( 153 [unittest_pb2.TestAllTypes.NestedMessage( 154 bb=unittest_pb2.TestAllTypes.FOO), 155 unittest_pb2.TestAllTypes.NestedMessage( 156 bb=unittest_pb2.TestAllTypes.BAR)], 157 list(proto.repeated_nested_message)) 158 self.assertEquals( 159 [unittest_pb2.ForeignMessage(c=-43), 160 unittest_pb2.ForeignMessage(c=45324), 161 unittest_pb2.ForeignMessage(c=12)], 162 list(proto.repeated_foreign_message)) 163 self.assertEquals( 164 [unittest_pb2.TestAllTypes.RepeatedGroup(), 165 unittest_pb2.TestAllTypes.RepeatedGroup(a=1), 166 unittest_pb2.TestAllTypes.RepeatedGroup(a=2)], 167 list(proto.repeatedgroup)) 168 169 def testMixedConstructor(self): 170 # Constructor with only mixed types should succeed. 171 proto = unittest_pb2.TestAllTypes( 172 optional_int32=24, 173 optional_string='optional_string', 174 repeated_double=[1.23, 54.321], 175 repeated_bool=[True, False, False], 176 repeated_nested_message=[ 177 unittest_pb2.TestAllTypes.NestedMessage( 178 bb=unittest_pb2.TestAllTypes.FOO), 179 unittest_pb2.TestAllTypes.NestedMessage( 180 bb=unittest_pb2.TestAllTypes.BAR)], 181 repeated_foreign_message=[ 182 unittest_pb2.ForeignMessage(c=-43), 183 unittest_pb2.ForeignMessage(c=45324), 184 unittest_pb2.ForeignMessage(c=12)]) 185 186 self.assertEqual(24, proto.optional_int32) 187 self.assertEqual('optional_string', proto.optional_string) 188 self.assertEquals([1.23, 54.321], list(proto.repeated_double)) 189 self.assertEquals([True, False, False], list(proto.repeated_bool)) 190 self.assertEquals( 191 [unittest_pb2.TestAllTypes.NestedMessage( 192 bb=unittest_pb2.TestAllTypes.FOO), 193 unittest_pb2.TestAllTypes.NestedMessage( 194 bb=unittest_pb2.TestAllTypes.BAR)], 195 list(proto.repeated_nested_message)) 196 self.assertEquals( 197 [unittest_pb2.ForeignMessage(c=-43), 198 unittest_pb2.ForeignMessage(c=45324), 199 unittest_pb2.ForeignMessage(c=12)], 200 list(proto.repeated_foreign_message)) 201 202 def testConstructorTypeError(self): 203 self.assertRaises( 204 TypeError, unittest_pb2.TestAllTypes, optional_int32="foo") 205 self.assertRaises( 206 TypeError, unittest_pb2.TestAllTypes, optional_string=1234) 207 self.assertRaises( 208 TypeError, unittest_pb2.TestAllTypes, optional_nested_message=1234) 209 self.assertRaises( 210 TypeError, unittest_pb2.TestAllTypes, repeated_int32=1234) 211 self.assertRaises( 212 TypeError, unittest_pb2.TestAllTypes, repeated_int32=["foo"]) 213 self.assertRaises( 214 TypeError, unittest_pb2.TestAllTypes, repeated_string=1234) 215 self.assertRaises( 216 TypeError, unittest_pb2.TestAllTypes, repeated_string=[1234]) 217 self.assertRaises( 218 TypeError, unittest_pb2.TestAllTypes, repeated_nested_message=1234) 219 self.assertRaises( 220 TypeError, unittest_pb2.TestAllTypes, repeated_nested_message=[1234]) 221 222 def testConstructorInvalidatesCachedByteSize(self): 223 message = unittest_pb2.TestAllTypes(optional_int32 = 12) 224 self.assertEquals(2, message.ByteSize()) 225 226 message = unittest_pb2.TestAllTypes( 227 optional_nested_message = unittest_pb2.TestAllTypes.NestedMessage()) 228 self.assertEquals(3, message.ByteSize()) 229 230 message = unittest_pb2.TestAllTypes(repeated_int32 = [12]) 231 self.assertEquals(3, message.ByteSize()) 232 233 message = unittest_pb2.TestAllTypes( 234 repeated_nested_message = [unittest_pb2.TestAllTypes.NestedMessage()]) 235 self.assertEquals(3, message.ByteSize()) 236 237 def testSimpleHasBits(self): 238 # Test a scalar. 239 proto = unittest_pb2.TestAllTypes() 240 self.assertTrue(not proto.HasField('optional_int32')) 241 self.assertEqual(0, proto.optional_int32) 242 # HasField() shouldn't be true if all we've done is 243 # read the default value. 244 self.assertTrue(not proto.HasField('optional_int32')) 245 proto.optional_int32 = 1 246 # Setting a value however *should* set the "has" bit. 247 self.assertTrue(proto.HasField('optional_int32')) 248 proto.ClearField('optional_int32') 249 # And clearing that value should unset the "has" bit. 250 self.assertTrue(not proto.HasField('optional_int32')) 251 252 def testHasBitsWithSinglyNestedScalar(self): 253 # Helper used to test foreign messages and groups. 254 # 255 # composite_field_name should be the name of a non-repeated 256 # composite (i.e., foreign or group) field in TestAllTypes, 257 # and scalar_field_name should be the name of an integer-valued 258 # scalar field within that composite. 259 # 260 # I never thought I'd miss C++ macros and templates so much. :( 261 # This helper is semantically just: 262 # 263 # assert proto.composite_field.scalar_field == 0 264 # assert not proto.composite_field.HasField('scalar_field') 265 # assert not proto.HasField('composite_field') 266 # 267 # proto.composite_field.scalar_field = 10 268 # old_composite_field = proto.composite_field 269 # 270 # assert proto.composite_field.scalar_field == 10 271 # assert proto.composite_field.HasField('scalar_field') 272 # assert proto.HasField('composite_field') 273 # 274 # proto.ClearField('composite_field') 275 # 276 # assert not proto.composite_field.HasField('scalar_field') 277 # assert not proto.HasField('composite_field') 278 # assert proto.composite_field.scalar_field == 0 279 # 280 # # Now ensure that ClearField('composite_field') disconnected 281 # # the old field object from the object tree... 282 # assert old_composite_field is not proto.composite_field 283 # old_composite_field.scalar_field = 20 284 # assert not proto.composite_field.HasField('scalar_field') 285 # assert not proto.HasField('composite_field') 286 def TestCompositeHasBits(composite_field_name, scalar_field_name): 287 proto = unittest_pb2.TestAllTypes() 288 # First, check that we can get the scalar value, and see that it's the 289 # default (0), but that proto.HasField('omposite') and 290 # proto.composite.HasField('scalar') will still return False. 291 composite_field = getattr(proto, composite_field_name) 292 original_scalar_value = getattr(composite_field, scalar_field_name) 293 self.assertEqual(0, original_scalar_value) 294 # Assert that the composite object does not "have" the scalar. 295 self.assertTrue(not composite_field.HasField(scalar_field_name)) 296 # Assert that proto does not "have" the composite field. 297 self.assertTrue(not proto.HasField(composite_field_name)) 298 299 # Now set the scalar within the composite field. Ensure that the setting 300 # is reflected, and that proto.HasField('composite') and 301 # proto.composite.HasField('scalar') now both return True. 302 new_val = 20 303 setattr(composite_field, scalar_field_name, new_val) 304 self.assertEqual(new_val, getattr(composite_field, scalar_field_name)) 305 # Hold on to a reference to the current composite_field object. 306 old_composite_field = composite_field 307 # Assert that the has methods now return true. 308 self.assertTrue(composite_field.HasField(scalar_field_name)) 309 self.assertTrue(proto.HasField(composite_field_name)) 310 311 # Now call the clear method... 312 proto.ClearField(composite_field_name) 313 314 # ...and ensure that the "has" bits are all back to False... 315 composite_field = getattr(proto, composite_field_name) 316 self.assertTrue(not composite_field.HasField(scalar_field_name)) 317 self.assertTrue(not proto.HasField(composite_field_name)) 318 # ...and ensure that the scalar field has returned to its default. 319 self.assertEqual(0, getattr(composite_field, scalar_field_name)) 320 321 # Finally, ensure that modifications to the old composite field object 322 # don't have any effect on the parent. Possible only with the pure-python 323 # implementation of the API. 324 # 325 # (NOTE that when we clear the composite field in the parent, we actually 326 # don't recursively clear down the tree. Instead, we just disconnect the 327 # cleared composite from the tree.) 328 if api_implementation.Type() != 'python': 329 return 330 self.assertTrue(old_composite_field is not composite_field) 331 setattr(old_composite_field, scalar_field_name, new_val) 332 self.assertTrue(not composite_field.HasField(scalar_field_name)) 333 self.assertTrue(not proto.HasField(composite_field_name)) 334 self.assertEqual(0, getattr(composite_field, scalar_field_name)) 335 336 # Test simple, single-level nesting when we set a scalar. 337 TestCompositeHasBits('optionalgroup', 'a') 338 TestCompositeHasBits('optional_nested_message', 'bb') 339 TestCompositeHasBits('optional_foreign_message', 'c') 340 TestCompositeHasBits('optional_import_message', 'd') 341 342 def testReferencesToNestedMessage(self): 343 proto = unittest_pb2.TestAllTypes() 344 nested = proto.optional_nested_message 345 del proto 346 # A previous version had a bug where this would raise an exception when 347 # hitting a now-dead weak reference. 348 nested.bb = 23 349 350 def testDisconnectingNestedMessageBeforeSettingField(self): 351 if api_implementation.Type() != 'python': 352 return 353 proto = unittest_pb2.TestAllTypes() 354 nested = proto.optional_nested_message 355 proto.ClearField('optional_nested_message') # Should disconnect from parent 356 self.assertTrue(nested is not proto.optional_nested_message) 357 nested.bb = 23 358 self.assertTrue(not proto.HasField('optional_nested_message')) 359 self.assertEqual(0, proto.optional_nested_message.bb) 360 361 def testHasBitsWhenModifyingRepeatedFields(self): 362 # Test nesting when we add an element to a repeated field in a submessage. 363 proto = unittest_pb2.TestNestedMessageHasBits() 364 proto.optional_nested_message.nestedmessage_repeated_int32.append(5) 365 self.assertEqual( 366 [5], proto.optional_nested_message.nestedmessage_repeated_int32) 367 self.assertTrue(proto.HasField('optional_nested_message')) 368 369 # Do the same test, but with a repeated composite field within the 370 # submessage. 371 proto.ClearField('optional_nested_message') 372 self.assertTrue(not proto.HasField('optional_nested_message')) 373 proto.optional_nested_message.nestedmessage_repeated_foreignmessage.add() 374 self.assertTrue(proto.HasField('optional_nested_message')) 375 376 def testHasBitsForManyLevelsOfNesting(self): 377 # Test nesting many levels deep. 378 recursive_proto = unittest_pb2.TestMutualRecursionA() 379 self.assertTrue(not recursive_proto.HasField('bb')) 380 self.assertEqual(0, recursive_proto.bb.a.bb.a.bb.optional_int32) 381 self.assertTrue(not recursive_proto.HasField('bb')) 382 recursive_proto.bb.a.bb.a.bb.optional_int32 = 5 383 self.assertEqual(5, recursive_proto.bb.a.bb.a.bb.optional_int32) 384 self.assertTrue(recursive_proto.HasField('bb')) 385 self.assertTrue(recursive_proto.bb.HasField('a')) 386 self.assertTrue(recursive_proto.bb.a.HasField('bb')) 387 self.assertTrue(recursive_proto.bb.a.bb.HasField('a')) 388 self.assertTrue(recursive_proto.bb.a.bb.a.HasField('bb')) 389 self.assertTrue(not recursive_proto.bb.a.bb.a.bb.HasField('a')) 390 self.assertTrue(recursive_proto.bb.a.bb.a.bb.HasField('optional_int32')) 391 392 def testSingularListFields(self): 393 proto = unittest_pb2.TestAllTypes() 394 proto.optional_fixed32 = 1 395 proto.optional_int32 = 5 396 proto.optional_string = 'foo' 397 # Access sub-message but don't set it yet. 398 nested_message = proto.optional_nested_message 399 self.assertEqual( 400 [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 5), 401 (proto.DESCRIPTOR.fields_by_name['optional_fixed32'], 1), 402 (proto.DESCRIPTOR.fields_by_name['optional_string' ], 'foo') ], 403 proto.ListFields()) 404 405 proto.optional_nested_message.bb = 123 406 self.assertEqual( 407 [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 5), 408 (proto.DESCRIPTOR.fields_by_name['optional_fixed32'], 1), 409 (proto.DESCRIPTOR.fields_by_name['optional_string' ], 'foo'), 410 (proto.DESCRIPTOR.fields_by_name['optional_nested_message' ], 411 nested_message) ], 412 proto.ListFields()) 413 414 def testRepeatedListFields(self): 415 proto = unittest_pb2.TestAllTypes() 416 proto.repeated_fixed32.append(1) 417 proto.repeated_int32.append(5) 418 proto.repeated_int32.append(11) 419 proto.repeated_string.extend(['foo', 'bar']) 420 proto.repeated_string.extend([]) 421 proto.repeated_string.append('baz') 422 proto.repeated_string.extend(str(x) for x in xrange(2)) 423 proto.optional_int32 = 21 424 proto.repeated_bool # Access but don't set anything; should not be listed. 425 self.assertEqual( 426 [ (proto.DESCRIPTOR.fields_by_name['optional_int32' ], 21), 427 (proto.DESCRIPTOR.fields_by_name['repeated_int32' ], [5, 11]), 428 (proto.DESCRIPTOR.fields_by_name['repeated_fixed32'], [1]), 429 (proto.DESCRIPTOR.fields_by_name['repeated_string' ], 430 ['foo', 'bar', 'baz', '0', '1']) ], 431 proto.ListFields()) 432 433 def testSingularListExtensions(self): 434 proto = unittest_pb2.TestAllExtensions() 435 proto.Extensions[unittest_pb2.optional_fixed32_extension] = 1 436 proto.Extensions[unittest_pb2.optional_int32_extension ] = 5 437 proto.Extensions[unittest_pb2.optional_string_extension ] = 'foo' 438 self.assertEqual( 439 [ (unittest_pb2.optional_int32_extension , 5), 440 (unittest_pb2.optional_fixed32_extension, 1), 441 (unittest_pb2.optional_string_extension , 'foo') ], 442 proto.ListFields()) 443 444 def testRepeatedListExtensions(self): 445 proto = unittest_pb2.TestAllExtensions() 446 proto.Extensions[unittest_pb2.repeated_fixed32_extension].append(1) 447 proto.Extensions[unittest_pb2.repeated_int32_extension ].append(5) 448 proto.Extensions[unittest_pb2.repeated_int32_extension ].append(11) 449 proto.Extensions[unittest_pb2.repeated_string_extension ].append('foo') 450 proto.Extensions[unittest_pb2.repeated_string_extension ].append('bar') 451 proto.Extensions[unittest_pb2.repeated_string_extension ].append('baz') 452 proto.Extensions[unittest_pb2.optional_int32_extension ] = 21 453 self.assertEqual( 454 [ (unittest_pb2.optional_int32_extension , 21), 455 (unittest_pb2.repeated_int32_extension , [5, 11]), 456 (unittest_pb2.repeated_fixed32_extension, [1]), 457 (unittest_pb2.repeated_string_extension , ['foo', 'bar', 'baz']) ], 458 proto.ListFields()) 459 460 def testListFieldsAndExtensions(self): 461 proto = unittest_pb2.TestFieldOrderings() 462 test_util.SetAllFieldsAndExtensions(proto) 463 unittest_pb2.my_extension_int 464 self.assertEqual( 465 [ (proto.DESCRIPTOR.fields_by_name['my_int' ], 1), 466 (unittest_pb2.my_extension_int , 23), 467 (proto.DESCRIPTOR.fields_by_name['my_string'], 'foo'), 468 (unittest_pb2.my_extension_string , 'bar'), 469 (proto.DESCRIPTOR.fields_by_name['my_float' ], 1.0) ], 470 proto.ListFields()) 471 472 def testDefaultValues(self): 473 proto = unittest_pb2.TestAllTypes() 474 self.assertEqual(0, proto.optional_int32) 475 self.assertEqual(0, proto.optional_int64) 476 self.assertEqual(0, proto.optional_uint32) 477 self.assertEqual(0, proto.optional_uint64) 478 self.assertEqual(0, proto.optional_sint32) 479 self.assertEqual(0, proto.optional_sint64) 480 self.assertEqual(0, proto.optional_fixed32) 481 self.assertEqual(0, proto.optional_fixed64) 482 self.assertEqual(0, proto.optional_sfixed32) 483 self.assertEqual(0, proto.optional_sfixed64) 484 self.assertEqual(0.0, proto.optional_float) 485 self.assertEqual(0.0, proto.optional_double) 486 self.assertEqual(False, proto.optional_bool) 487 self.assertEqual('', proto.optional_string) 488 self.assertEqual('', proto.optional_bytes) 489 490 self.assertEqual(41, proto.default_int32) 491 self.assertEqual(42, proto.default_int64) 492 self.assertEqual(43, proto.default_uint32) 493 self.assertEqual(44, proto.default_uint64) 494 self.assertEqual(-45, proto.default_sint32) 495 self.assertEqual(46, proto.default_sint64) 496 self.assertEqual(47, proto.default_fixed32) 497 self.assertEqual(48, proto.default_fixed64) 498 self.assertEqual(49, proto.default_sfixed32) 499 self.assertEqual(-50, proto.default_sfixed64) 500 self.assertEqual(51.5, proto.default_float) 501 self.assertEqual(52e3, proto.default_double) 502 self.assertEqual(True, proto.default_bool) 503 self.assertEqual('hello', proto.default_string) 504 self.assertEqual('world', proto.default_bytes) 505 self.assertEqual(unittest_pb2.TestAllTypes.BAR, proto.default_nested_enum) 506 self.assertEqual(unittest_pb2.FOREIGN_BAR, proto.default_foreign_enum) 507 self.assertEqual(unittest_import_pb2.IMPORT_BAR, 508 proto.default_import_enum) 509 510 proto = unittest_pb2.TestExtremeDefaultValues() 511 self.assertEqual(u'\u1234', proto.utf8_string) 512 513 def testHasFieldWithUnknownFieldName(self): 514 proto = unittest_pb2.TestAllTypes() 515 self.assertRaises(ValueError, proto.HasField, 'nonexistent_field') 516 517 def testClearFieldWithUnknownFieldName(self): 518 proto = unittest_pb2.TestAllTypes() 519 self.assertRaises(ValueError, proto.ClearField, 'nonexistent_field') 520 521 def testDisallowedAssignments(self): 522 # It's illegal to assign values directly to repeated fields 523 # or to nonrepeated composite fields. Ensure that this fails. 524 proto = unittest_pb2.TestAllTypes() 525 # Repeated fields. 526 self.assertRaises(AttributeError, setattr, proto, 'repeated_int32', 10) 527 # Lists shouldn't work, either. 528 self.assertRaises(AttributeError, setattr, proto, 'repeated_int32', [10]) 529 # Composite fields. 530 self.assertRaises(AttributeError, setattr, proto, 531 'optional_nested_message', 23) 532 # Assignment to a repeated nested message field without specifying 533 # the index in the array of nested messages. 534 self.assertRaises(AttributeError, setattr, proto.repeated_nested_message, 535 'bb', 34) 536 # Assignment to an attribute of a repeated field. 537 self.assertRaises(AttributeError, setattr, proto.repeated_float, 538 'some_attribute', 34) 539 # proto.nonexistent_field = 23 should fail as well. 540 self.assertRaises(AttributeError, setattr, proto, 'nonexistent_field', 23) 541 542 def testSingleScalarTypeSafety(self): 543 proto = unittest_pb2.TestAllTypes() 544 self.assertRaises(TypeError, setattr, proto, 'optional_int32', 1.1) 545 self.assertRaises(TypeError, setattr, proto, 'optional_int32', 'foo') 546 self.assertRaises(TypeError, setattr, proto, 'optional_string', 10) 547 self.assertRaises(TypeError, setattr, proto, 'optional_bytes', 10) 548 549 def testSingleScalarBoundsChecking(self): 550 def TestMinAndMaxIntegers(field_name, expected_min, expected_max): 551 pb = unittest_pb2.TestAllTypes() 552 setattr(pb, field_name, expected_min) 553 self.assertEqual(expected_min, getattr(pb, field_name)) 554 setattr(pb, field_name, expected_max) 555 self.assertEqual(expected_max, getattr(pb, field_name)) 556 self.assertRaises(ValueError, setattr, pb, field_name, expected_min - 1) 557 self.assertRaises(ValueError, setattr, pb, field_name, expected_max + 1) 558 559 TestMinAndMaxIntegers('optional_int32', -(1 << 31), (1 << 31) - 1) 560 TestMinAndMaxIntegers('optional_uint32', 0, 0xffffffff) 561 TestMinAndMaxIntegers('optional_int64', -(1 << 63), (1 << 63) - 1) 562 TestMinAndMaxIntegers('optional_uint64', 0, 0xffffffffffffffff) 563 564 pb = unittest_pb2.TestAllTypes() 565 pb.optional_nested_enum = 1 566 self.assertEqual(1, pb.optional_nested_enum) 567 568 # Invalid enum values. 569 pb.optional_nested_enum = 0 570 self.assertEqual(0, pb.optional_nested_enum) 571 572 bytes_size_before = pb.ByteSize() 573 574 pb.optional_nested_enum = 4 575 self.assertEqual(4, pb.optional_nested_enum) 576 577 pb.optional_nested_enum = 0 578 self.assertEqual(0, pb.optional_nested_enum) 579 580 # Make sure that setting the same enum field doesn't just add unknown 581 # fields (but overwrites them). 582 self.assertEqual(bytes_size_before, pb.ByteSize()) 583 584 # Is the invalid value preserved after serialization? 585 serialized = pb.SerializeToString() 586 pb2 = unittest_pb2.TestAllTypes() 587 pb2.ParseFromString(serialized) 588 self.assertEqual(0, pb2.optional_nested_enum) 589 self.assertEqual(pb, pb2) 590 591 def testRepeatedScalarTypeSafety(self): 592 proto = unittest_pb2.TestAllTypes() 593 self.assertRaises(TypeError, proto.repeated_int32.append, 1.1) 594 self.assertRaises(TypeError, proto.repeated_int32.append, 'foo') 595 self.assertRaises(TypeError, proto.repeated_string, 10) 596 self.assertRaises(TypeError, proto.repeated_bytes, 10) 597 598 proto.repeated_int32.append(10) 599 proto.repeated_int32[0] = 23 600 self.assertRaises(IndexError, proto.repeated_int32.__setitem__, 500, 23) 601 self.assertRaises(TypeError, proto.repeated_int32.__setitem__, 0, 'abc') 602 603 # Repeated enums tests. 604 #proto.repeated_nested_enum.append(0) 605 606 def testSingleScalarGettersAndSetters(self): 607 proto = unittest_pb2.TestAllTypes() 608 self.assertEqual(0, proto.optional_int32) 609 proto.optional_int32 = 1 610 self.assertEqual(1, proto.optional_int32) 611 612 proto.optional_uint64 = 0xffffffffffff 613 self.assertEqual(0xffffffffffff, proto.optional_uint64) 614 proto.optional_uint64 = 0xffffffffffffffff 615 self.assertEqual(0xffffffffffffffff, proto.optional_uint64) 616 # TODO(robinson): Test all other scalar field types. 617 618 def testSingleScalarClearField(self): 619 proto = unittest_pb2.TestAllTypes() 620 # Should be allowed to clear something that's not there (a no-op). 621 proto.ClearField('optional_int32') 622 proto.optional_int32 = 1 623 self.assertTrue(proto.HasField('optional_int32')) 624 proto.ClearField('optional_int32') 625 self.assertEqual(0, proto.optional_int32) 626 self.assertTrue(not proto.HasField('optional_int32')) 627 # TODO(robinson): Test all other scalar field types. 628 629 def testEnums(self): 630 proto = unittest_pb2.TestAllTypes() 631 self.assertEqual(1, proto.FOO) 632 self.assertEqual(1, unittest_pb2.TestAllTypes.FOO) 633 self.assertEqual(2, proto.BAR) 634 self.assertEqual(2, unittest_pb2.TestAllTypes.BAR) 635 self.assertEqual(3, proto.BAZ) 636 self.assertEqual(3, unittest_pb2.TestAllTypes.BAZ) 637 638 def testRepeatedScalars(self): 639 proto = unittest_pb2.TestAllTypes() 640 641 self.assertTrue(not proto.repeated_int32) 642 self.assertEqual(0, len(proto.repeated_int32)) 643 proto.repeated_int32.append(5) 644 proto.repeated_int32.append(10) 645 proto.repeated_int32.append(15) 646 self.assertTrue(proto.repeated_int32) 647 self.assertEqual(3, len(proto.repeated_int32)) 648 649 self.assertEqual([5, 10, 15], proto.repeated_int32) 650 651 # Test single retrieval. 652 self.assertEqual(5, proto.repeated_int32[0]) 653 self.assertEqual(15, proto.repeated_int32[-1]) 654 # Test out-of-bounds indices. 655 self.assertRaises(IndexError, proto.repeated_int32.__getitem__, 1234) 656 self.assertRaises(IndexError, proto.repeated_int32.__getitem__, -1234) 657 # Test incorrect types passed to __getitem__. 658 self.assertRaises(TypeError, proto.repeated_int32.__getitem__, 'foo') 659 self.assertRaises(TypeError, proto.repeated_int32.__getitem__, None) 660 661 # Test single assignment. 662 proto.repeated_int32[1] = 20 663 self.assertEqual([5, 20, 15], proto.repeated_int32) 664 665 # Test insertion. 666 proto.repeated_int32.insert(1, 25) 667 self.assertEqual([5, 25, 20, 15], proto.repeated_int32) 668 669 # Test slice retrieval. 670 proto.repeated_int32.append(30) 671 self.assertEqual([25, 20, 15], proto.repeated_int32[1:4]) 672 self.assertEqual([5, 25, 20, 15, 30], proto.repeated_int32[:]) 673 674 # Test slice assignment with an iterator 675 proto.repeated_int32[1:4] = (i for i in xrange(3)) 676 self.assertEqual([5, 0, 1, 2, 30], proto.repeated_int32) 677 678 # Test slice assignment. 679 proto.repeated_int32[1:4] = [35, 40, 45] 680 self.assertEqual([5, 35, 40, 45, 30], proto.repeated_int32) 681 682 # Test that we can use the field as an iterator. 683 result = [] 684 for i in proto.repeated_int32: 685 result.append(i) 686 self.assertEqual([5, 35, 40, 45, 30], result) 687 688 # Test single deletion. 689 del proto.repeated_int32[2] 690 self.assertEqual([5, 35, 45, 30], proto.repeated_int32) 691 692 # Test slice deletion. 693 del proto.repeated_int32[2:] 694 self.assertEqual([5, 35], proto.repeated_int32) 695 696 # Test extending. 697 proto.repeated_int32.extend([3, 13]) 698 self.assertEqual([5, 35, 3, 13], proto.repeated_int32) 699 700 # Test clearing. 701 proto.ClearField('repeated_int32') 702 self.assertTrue(not proto.repeated_int32) 703 self.assertEqual(0, len(proto.repeated_int32)) 704 705 proto.repeated_int32.append(1) 706 self.assertEqual(1, proto.repeated_int32[-1]) 707 # Test assignment to a negative index. 708 proto.repeated_int32[-1] = 2 709 self.assertEqual(2, proto.repeated_int32[-1]) 710 711 # Test deletion at negative indices. 712 proto.repeated_int32[:] = [0, 1, 2, 3] 713 del proto.repeated_int32[-1] 714 self.assertEqual([0, 1, 2], proto.repeated_int32) 715 716 del proto.repeated_int32[-2] 717 self.assertEqual([0, 2], proto.repeated_int32) 718 719 self.assertRaises(IndexError, proto.repeated_int32.__delitem__, -3) 720 self.assertRaises(IndexError, proto.repeated_int32.__delitem__, 300) 721 722 del proto.repeated_int32[-2:-1] 723 self.assertEqual([2], proto.repeated_int32) 724 725 del proto.repeated_int32[100:10000] 726 self.assertEqual([2], proto.repeated_int32) 727 728 def testRepeatedScalarsRemove(self): 729 proto = unittest_pb2.TestAllTypes() 730 731 self.assertTrue(not proto.repeated_int32) 732 self.assertEqual(0, len(proto.repeated_int32)) 733 proto.repeated_int32.append(5) 734 proto.repeated_int32.append(10) 735 proto.repeated_int32.append(5) 736 proto.repeated_int32.append(5) 737 738 self.assertEqual(4, len(proto.repeated_int32)) 739 proto.repeated_int32.remove(5) 740 self.assertEqual(3, len(proto.repeated_int32)) 741 self.assertEqual(10, proto.repeated_int32[0]) 742 self.assertEqual(5, proto.repeated_int32[1]) 743 self.assertEqual(5, proto.repeated_int32[2]) 744 745 proto.repeated_int32.remove(5) 746 self.assertEqual(2, len(proto.repeated_int32)) 747 self.assertEqual(10, proto.repeated_int32[0]) 748 self.assertEqual(5, proto.repeated_int32[1]) 749 750 proto.repeated_int32.remove(10) 751 self.assertEqual(1, len(proto.repeated_int32)) 752 self.assertEqual(5, proto.repeated_int32[0]) 753 754 # Remove a non-existent element. 755 self.assertRaises(ValueError, proto.repeated_int32.remove, 123) 756 757 def testRepeatedComposites(self): 758 proto = unittest_pb2.TestAllTypes() 759 self.assertTrue(not proto.repeated_nested_message) 760 self.assertEqual(0, len(proto.repeated_nested_message)) 761 m0 = proto.repeated_nested_message.add() 762 m1 = proto.repeated_nested_message.add() 763 self.assertTrue(proto.repeated_nested_message) 764 self.assertEqual(2, len(proto.repeated_nested_message)) 765 self.assertListsEqual([m0, m1], proto.repeated_nested_message) 766 self.assertTrue(isinstance(m0, unittest_pb2.TestAllTypes.NestedMessage)) 767 768 # Test out-of-bounds indices. 769 self.assertRaises(IndexError, proto.repeated_nested_message.__getitem__, 770 1234) 771 self.assertRaises(IndexError, proto.repeated_nested_message.__getitem__, 772 -1234) 773 774 # Test incorrect types passed to __getitem__. 775 self.assertRaises(TypeError, proto.repeated_nested_message.__getitem__, 776 'foo') 777 self.assertRaises(TypeError, proto.repeated_nested_message.__getitem__, 778 None) 779 780 # Test slice retrieval. 781 m2 = proto.repeated_nested_message.add() 782 m3 = proto.repeated_nested_message.add() 783 m4 = proto.repeated_nested_message.add() 784 self.assertListsEqual( 785 [m1, m2, m3], proto.repeated_nested_message[1:4]) 786 self.assertListsEqual( 787 [m0, m1, m2, m3, m4], proto.repeated_nested_message[:]) 788 self.assertListsEqual( 789 [m0, m1], proto.repeated_nested_message[:2]) 790 self.assertListsEqual( 791 [m2, m3, m4], proto.repeated_nested_message[2:]) 792 self.assertEqual( 793 m0, proto.repeated_nested_message[0]) 794 self.assertListsEqual( 795 [m0], proto.repeated_nested_message[:1]) 796 797 # Test that we can use the field as an iterator. 798 result = [] 799 for i in proto.repeated_nested_message: 800 result.append(i) 801 self.assertListsEqual([m0, m1, m2, m3, m4], result) 802 803 # Test single deletion. 804 del proto.repeated_nested_message[2] 805 self.assertListsEqual([m0, m1, m3, m4], proto.repeated_nested_message) 806 807 # Test slice deletion. 808 del proto.repeated_nested_message[2:] 809 self.assertListsEqual([m0, m1], proto.repeated_nested_message) 810 811 # Test extending. 812 n1 = unittest_pb2.TestAllTypes.NestedMessage(bb=1) 813 n2 = unittest_pb2.TestAllTypes.NestedMessage(bb=2) 814 proto.repeated_nested_message.extend([n1,n2]) 815 self.assertEqual(4, len(proto.repeated_nested_message)) 816 self.assertEqual(n1, proto.repeated_nested_message[2]) 817 self.assertEqual(n2, proto.repeated_nested_message[3]) 818 819 # Test clearing. 820 proto.ClearField('repeated_nested_message') 821 self.assertTrue(not proto.repeated_nested_message) 822 self.assertEqual(0, len(proto.repeated_nested_message)) 823 824 # Test constructing an element while adding it. 825 proto.repeated_nested_message.add(bb=23) 826 self.assertEqual(1, len(proto.repeated_nested_message)) 827 self.assertEqual(23, proto.repeated_nested_message[0].bb) 828 829 def testHandWrittenReflection(self): 830 # Hand written extensions are only supported by the pure-Python 831 # implementation of the API. 832 if api_implementation.Type() != 'python': 833 return 834 835 FieldDescriptor = descriptor.FieldDescriptor 836 foo_field_descriptor = FieldDescriptor( 837 name='foo_field', full_name='MyProto.foo_field', 838 index=0, number=1, type=FieldDescriptor.TYPE_INT64, 839 cpp_type=FieldDescriptor.CPPTYPE_INT64, 840 label=FieldDescriptor.LABEL_OPTIONAL, default_value=0, 841 containing_type=None, message_type=None, enum_type=None, 842 is_extension=False, extension_scope=None, 843 options=descriptor_pb2.FieldOptions()) 844 mydescriptor = descriptor.Descriptor( 845 name='MyProto', full_name='MyProto', filename='ignored', 846 containing_type=None, nested_types=[], enum_types=[], 847 fields=[foo_field_descriptor], extensions=[], 848 options=descriptor_pb2.MessageOptions()) 849 class MyProtoClass(message.Message): 850 DESCRIPTOR = mydescriptor 851 __metaclass__ = reflection.GeneratedProtocolMessageType 852 myproto_instance = MyProtoClass() 853 self.assertEqual(0, myproto_instance.foo_field) 854 self.assertTrue(not myproto_instance.HasField('foo_field')) 855 myproto_instance.foo_field = 23 856 self.assertEqual(23, myproto_instance.foo_field) 857 self.assertTrue(myproto_instance.HasField('foo_field')) 858 859 def testTopLevelExtensionsForOptionalScalar(self): 860 extendee_proto = unittest_pb2.TestAllExtensions() 861 extension = unittest_pb2.optional_int32_extension 862 self.assertTrue(not extendee_proto.HasExtension(extension)) 863 self.assertEqual(0, extendee_proto.Extensions[extension]) 864 # As with normal scalar fields, just doing a read doesn't actually set the 865 # "has" bit. 866 self.assertTrue(not extendee_proto.HasExtension(extension)) 867 # Actually set the thing. 868 extendee_proto.Extensions[extension] = 23 869 self.assertEqual(23, extendee_proto.Extensions[extension]) 870 self.assertTrue(extendee_proto.HasExtension(extension)) 871 # Ensure that clearing works as well. 872 extendee_proto.ClearExtension(extension) 873 self.assertEqual(0, extendee_proto.Extensions[extension]) 874 self.assertTrue(not extendee_proto.HasExtension(extension)) 875 876 def testTopLevelExtensionsForRepeatedScalar(self): 877 extendee_proto = unittest_pb2.TestAllExtensions() 878 extension = unittest_pb2.repeated_string_extension 879 self.assertEqual(0, len(extendee_proto.Extensions[extension])) 880 extendee_proto.Extensions[extension].append('foo') 881 self.assertEqual(['foo'], extendee_proto.Extensions[extension]) 882 string_list = extendee_proto.Extensions[extension] 883 extendee_proto.ClearExtension(extension) 884 self.assertEqual(0, len(extendee_proto.Extensions[extension])) 885 self.assertTrue(string_list is not extendee_proto.Extensions[extension]) 886 # Shouldn't be allowed to do Extensions[extension] = 'a' 887 self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions, 888 extension, 'a') 889 890 def testTopLevelExtensionsForOptionalMessage(self): 891 extendee_proto = unittest_pb2.TestAllExtensions() 892 extension = unittest_pb2.optional_foreign_message_extension 893 self.assertTrue(not extendee_proto.HasExtension(extension)) 894 self.assertEqual(0, extendee_proto.Extensions[extension].c) 895 # As with normal (non-extension) fields, merely reading from the 896 # thing shouldn't set the "has" bit. 897 self.assertTrue(not extendee_proto.HasExtension(extension)) 898 extendee_proto.Extensions[extension].c = 23 899 self.assertEqual(23, extendee_proto.Extensions[extension].c) 900 self.assertTrue(extendee_proto.HasExtension(extension)) 901 # Save a reference here. 902 foreign_message = extendee_proto.Extensions[extension] 903 extendee_proto.ClearExtension(extension) 904 self.assertTrue(foreign_message is not extendee_proto.Extensions[extension]) 905 # Setting a field on foreign_message now shouldn't set 906 # any "has" bits on extendee_proto. 907 foreign_message.c = 42 908 self.assertEqual(42, foreign_message.c) 909 self.assertTrue(foreign_message.HasField('c')) 910 self.assertTrue(not extendee_proto.HasExtension(extension)) 911 # Shouldn't be allowed to do Extensions[extension] = 'a' 912 self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions, 913 extension, 'a') 914 915 def testTopLevelExtensionsForRepeatedMessage(self): 916 extendee_proto = unittest_pb2.TestAllExtensions() 917 extension = unittest_pb2.repeatedgroup_extension 918 self.assertEqual(0, len(extendee_proto.Extensions[extension])) 919 group = extendee_proto.Extensions[extension].add() 920 group.a = 23 921 self.assertEqual(23, extendee_proto.Extensions[extension][0].a) 922 group.a = 42 923 self.assertEqual(42, extendee_proto.Extensions[extension][0].a) 924 group_list = extendee_proto.Extensions[extension] 925 extendee_proto.ClearExtension(extension) 926 self.assertEqual(0, len(extendee_proto.Extensions[extension])) 927 self.assertTrue(group_list is not extendee_proto.Extensions[extension]) 928 # Shouldn't be allowed to do Extensions[extension] = 'a' 929 self.assertRaises(TypeError, operator.setitem, extendee_proto.Extensions, 930 extension, 'a') 931 932 def testNestedExtensions(self): 933 extendee_proto = unittest_pb2.TestAllExtensions() 934 extension = unittest_pb2.TestRequired.single 935 936 # We just test the non-repeated case. 937 self.assertTrue(not extendee_proto.HasExtension(extension)) 938 required = extendee_proto.Extensions[extension] 939 self.assertEqual(0, required.a) 940 self.assertTrue(not extendee_proto.HasExtension(extension)) 941 required.a = 23 942 self.assertEqual(23, extendee_proto.Extensions[extension].a) 943 self.assertTrue(extendee_proto.HasExtension(extension)) 944 extendee_proto.ClearExtension(extension) 945 self.assertTrue(required is not extendee_proto.Extensions[extension]) 946 self.assertTrue(not extendee_proto.HasExtension(extension)) 947 948 # If message A directly contains message B, and 949 # a.HasField('b') is currently False, then mutating any 950 # extension in B should change a.HasField('b') to True 951 # (and so on up the object tree). 952 def testHasBitsForAncestorsOfExtendedMessage(self): 953 # Optional scalar extension. 954 toplevel = more_extensions_pb2.TopLevelMessage() 955 self.assertTrue(not toplevel.HasField('submessage')) 956 self.assertEqual(0, toplevel.submessage.Extensions[ 957 more_extensions_pb2.optional_int_extension]) 958 self.assertTrue(not toplevel.HasField('submessage')) 959 toplevel.submessage.Extensions[ 960 more_extensions_pb2.optional_int_extension] = 23 961 self.assertEqual(23, toplevel.submessage.Extensions[ 962 more_extensions_pb2.optional_int_extension]) 963 self.assertTrue(toplevel.HasField('submessage')) 964 965 # Repeated scalar extension. 966 toplevel = more_extensions_pb2.TopLevelMessage() 967 self.assertTrue(not toplevel.HasField('submessage')) 968 self.assertEqual([], toplevel.submessage.Extensions[ 969 more_extensions_pb2.repeated_int_extension]) 970 self.assertTrue(not toplevel.HasField('submessage')) 971 toplevel.submessage.Extensions[ 972 more_extensions_pb2.repeated_int_extension].append(23) 973 self.assertEqual([23], toplevel.submessage.Extensions[ 974 more_extensions_pb2.repeated_int_extension]) 975 self.assertTrue(toplevel.HasField('submessage')) 976 977 # Optional message extension. 978 toplevel = more_extensions_pb2.TopLevelMessage() 979 self.assertTrue(not toplevel.HasField('submessage')) 980 self.assertEqual(0, toplevel.submessage.Extensions[ 981 more_extensions_pb2.optional_message_extension].foreign_message_int) 982 self.assertTrue(not toplevel.HasField('submessage')) 983 toplevel.submessage.Extensions[ 984 more_extensions_pb2.optional_message_extension].foreign_message_int = 23 985 self.assertEqual(23, toplevel.submessage.Extensions[ 986 more_extensions_pb2.optional_message_extension].foreign_message_int) 987 self.assertTrue(toplevel.HasField('submessage')) 988 989 # Repeated message extension. 990 toplevel = more_extensions_pb2.TopLevelMessage() 991 self.assertTrue(not toplevel.HasField('submessage')) 992 self.assertEqual(0, len(toplevel.submessage.Extensions[ 993 more_extensions_pb2.repeated_message_extension])) 994 self.assertTrue(not toplevel.HasField('submessage')) 995 foreign = toplevel.submessage.Extensions[ 996 more_extensions_pb2.repeated_message_extension].add() 997 self.assertEqual(foreign, toplevel.submessage.Extensions[ 998 more_extensions_pb2.repeated_message_extension][0]) 999 self.assertTrue(toplevel.HasField('submessage')) 1000 1001 def testDisconnectionAfterClearingEmptyMessage(self): 1002 toplevel = more_extensions_pb2.TopLevelMessage() 1003 extendee_proto = toplevel.submessage 1004 extension = more_extensions_pb2.optional_message_extension 1005 extension_proto = extendee_proto.Extensions[extension] 1006 extendee_proto.ClearExtension(extension) 1007 extension_proto.foreign_message_int = 23 1008 1009 self.assertTrue(extension_proto is not extendee_proto.Extensions[extension]) 1010 1011 def testExtensionFailureModes(self): 1012 extendee_proto = unittest_pb2.TestAllExtensions() 1013 1014 # Try non-extension-handle arguments to HasExtension, 1015 # ClearExtension(), and Extensions[]... 1016 self.assertRaises(KeyError, extendee_proto.HasExtension, 1234) 1017 self.assertRaises(KeyError, extendee_proto.ClearExtension, 1234) 1018 self.assertRaises(KeyError, extendee_proto.Extensions.__getitem__, 1234) 1019 self.assertRaises(KeyError, extendee_proto.Extensions.__setitem__, 1234, 5) 1020 1021 # Try something that *is* an extension handle, just not for 1022 # this message... 1023 unknown_handle = more_extensions_pb2.optional_int_extension 1024 self.assertRaises(KeyError, extendee_proto.HasExtension, 1025 unknown_handle) 1026 self.assertRaises(KeyError, extendee_proto.ClearExtension, 1027 unknown_handle) 1028 self.assertRaises(KeyError, extendee_proto.Extensions.__getitem__, 1029 unknown_handle) 1030 self.assertRaises(KeyError, extendee_proto.Extensions.__setitem__, 1031 unknown_handle, 5) 1032 1033 # Try call HasExtension() with a valid handle, but for a 1034 # *repeated* field. (Just as with non-extension repeated 1035 # fields, Has*() isn't supported for extension repeated fields). 1036 self.assertRaises(KeyError, extendee_proto.HasExtension, 1037 unittest_pb2.repeated_string_extension) 1038 1039 def testStaticParseFrom(self): 1040 proto1 = unittest_pb2.TestAllTypes() 1041 test_util.SetAllFields(proto1) 1042 1043 string1 = proto1.SerializeToString() 1044 proto2 = unittest_pb2.TestAllTypes.FromString(string1) 1045 1046 # Messages should be equal. 1047 self.assertEqual(proto2, proto1) 1048 1049 def testMergeFromSingularField(self): 1050 # Test merge with just a singular field. 1051 proto1 = unittest_pb2.TestAllTypes() 1052 proto1.optional_int32 = 1 1053 1054 proto2 = unittest_pb2.TestAllTypes() 1055 # This shouldn't get overwritten. 1056 proto2.optional_string = 'value' 1057 1058 proto2.MergeFrom(proto1) 1059 self.assertEqual(1, proto2.optional_int32) 1060 self.assertEqual('value', proto2.optional_string) 1061 1062 def testMergeFromRepeatedField(self): 1063 # Test merge with just a repeated field. 1064 proto1 = unittest_pb2.TestAllTypes() 1065 proto1.repeated_int32.append(1) 1066 proto1.repeated_int32.append(2) 1067 1068 proto2 = unittest_pb2.TestAllTypes() 1069 proto2.repeated_int32.append(0) 1070 proto2.MergeFrom(proto1) 1071 1072 self.assertEqual(0, proto2.repeated_int32[0]) 1073 self.assertEqual(1, proto2.repeated_int32[1]) 1074 self.assertEqual(2, proto2.repeated_int32[2]) 1075 1076 def testMergeFromOptionalGroup(self): 1077 # Test merge with an optional group. 1078 proto1 = unittest_pb2.TestAllTypes() 1079 proto1.optionalgroup.a = 12 1080 proto2 = unittest_pb2.TestAllTypes() 1081 proto2.MergeFrom(proto1) 1082 self.assertEqual(12, proto2.optionalgroup.a) 1083 1084 def testMergeFromRepeatedNestedMessage(self): 1085 # Test merge with a repeated nested message. 1086 proto1 = unittest_pb2.TestAllTypes() 1087 m = proto1.repeated_nested_message.add() 1088 m.bb = 123 1089 m = proto1.repeated_nested_message.add() 1090 m.bb = 321 1091 1092 proto2 = unittest_pb2.TestAllTypes() 1093 m = proto2.repeated_nested_message.add() 1094 m.bb = 999 1095 proto2.MergeFrom(proto1) 1096 self.assertEqual(999, proto2.repeated_nested_message[0].bb) 1097 self.assertEqual(123, proto2.repeated_nested_message[1].bb) 1098 self.assertEqual(321, proto2.repeated_nested_message[2].bb) 1099 1100 proto3 = unittest_pb2.TestAllTypes() 1101 proto3.repeated_nested_message.MergeFrom(proto2.repeated_nested_message) 1102 self.assertEqual(999, proto3.repeated_nested_message[0].bb) 1103 self.assertEqual(123, proto3.repeated_nested_message[1].bb) 1104 self.assertEqual(321, proto3.repeated_nested_message[2].bb) 1105 1106 def testMergeFromAllFields(self): 1107 # With all fields set. 1108 proto1 = unittest_pb2.TestAllTypes() 1109 test_util.SetAllFields(proto1) 1110 proto2 = unittest_pb2.TestAllTypes() 1111 proto2.MergeFrom(proto1) 1112 1113 # Messages should be equal. 1114 self.assertEqual(proto2, proto1) 1115 1116 # Serialized string should be equal too. 1117 string1 = proto1.SerializeToString() 1118 string2 = proto2.SerializeToString() 1119 self.assertEqual(string1, string2) 1120 1121 def testMergeFromExtensionsSingular(self): 1122 proto1 = unittest_pb2.TestAllExtensions() 1123 proto1.Extensions[unittest_pb2.optional_int32_extension] = 1 1124 1125 proto2 = unittest_pb2.TestAllExtensions() 1126 proto2.MergeFrom(proto1) 1127 self.assertEqual( 1128 1, proto2.Extensions[unittest_pb2.optional_int32_extension]) 1129 1130 def testMergeFromExtensionsRepeated(self): 1131 proto1 = unittest_pb2.TestAllExtensions() 1132 proto1.Extensions[unittest_pb2.repeated_int32_extension].append(1) 1133 proto1.Extensions[unittest_pb2.repeated_int32_extension].append(2) 1134 1135 proto2 = unittest_pb2.TestAllExtensions() 1136 proto2.Extensions[unittest_pb2.repeated_int32_extension].append(0) 1137 proto2.MergeFrom(proto1) 1138 self.assertEqual( 1139 3, len(proto2.Extensions[unittest_pb2.repeated_int32_extension])) 1140 self.assertEqual( 1141 0, proto2.Extensions[unittest_pb2.repeated_int32_extension][0]) 1142 self.assertEqual( 1143 1, proto2.Extensions[unittest_pb2.repeated_int32_extension][1]) 1144 self.assertEqual( 1145 2, proto2.Extensions[unittest_pb2.repeated_int32_extension][2]) 1146 1147 def testMergeFromExtensionsNestedMessage(self): 1148 proto1 = unittest_pb2.TestAllExtensions() 1149 ext1 = proto1.Extensions[ 1150 unittest_pb2.repeated_nested_message_extension] 1151 m = ext1.add() 1152 m.bb = 222 1153 m = ext1.add() 1154 m.bb = 333 1155 1156 proto2 = unittest_pb2.TestAllExtensions() 1157 ext2 = proto2.Extensions[ 1158 unittest_pb2.repeated_nested_message_extension] 1159 m = ext2.add() 1160 m.bb = 111 1161 1162 proto2.MergeFrom(proto1) 1163 ext2 = proto2.Extensions[ 1164 unittest_pb2.repeated_nested_message_extension] 1165 self.assertEqual(3, len(ext2)) 1166 self.assertEqual(111, ext2[0].bb) 1167 self.assertEqual(222, ext2[1].bb) 1168 self.assertEqual(333, ext2[2].bb) 1169 1170 def testMergeFromBug(self): 1171 message1 = unittest_pb2.TestAllTypes() 1172 message2 = unittest_pb2.TestAllTypes() 1173 1174 # Cause optional_nested_message to be instantiated within message1, even 1175 # though it is not considered to be "present". 1176 message1.optional_nested_message 1177 self.assertFalse(message1.HasField('optional_nested_message')) 1178 1179 # Merge into message2. This should not instantiate the field is message2. 1180 message2.MergeFrom(message1) 1181 self.assertFalse(message2.HasField('optional_nested_message')) 1182 1183 def testCopyFromSingularField(self): 1184 # Test copy with just a singular field. 1185 proto1 = unittest_pb2.TestAllTypes() 1186 proto1.optional_int32 = 1 1187 proto1.optional_string = 'important-text' 1188 1189 proto2 = unittest_pb2.TestAllTypes() 1190 proto2.optional_string = 'value' 1191 1192 proto2.CopyFrom(proto1) 1193 self.assertEqual(1, proto2.optional_int32) 1194 self.assertEqual('important-text', proto2.optional_string) 1195 1196 def testCopyFromRepeatedField(self): 1197 # Test copy with a repeated field. 1198 proto1 = unittest_pb2.TestAllTypes() 1199 proto1.repeated_int32.append(1) 1200 proto1.repeated_int32.append(2) 1201 1202 proto2 = unittest_pb2.TestAllTypes() 1203 proto2.repeated_int32.append(0) 1204 proto2.CopyFrom(proto1) 1205 1206 self.assertEqual(1, proto2.repeated_int32[0]) 1207 self.assertEqual(2, proto2.repeated_int32[1]) 1208 1209 def testCopyFromAllFields(self): 1210 # With all fields set. 1211 proto1 = unittest_pb2.TestAllTypes() 1212 test_util.SetAllFields(proto1) 1213 proto2 = unittest_pb2.TestAllTypes() 1214 proto2.CopyFrom(proto1) 1215 1216 # Messages should be equal. 1217 self.assertEqual(proto2, proto1) 1218 1219 # Serialized string should be equal too. 1220 string1 = proto1.SerializeToString() 1221 string2 = proto2.SerializeToString() 1222 self.assertEqual(string1, string2) 1223 1224 def testCopyFromSelf(self): 1225 proto1 = unittest_pb2.TestAllTypes() 1226 proto1.repeated_int32.append(1) 1227 proto1.optional_int32 = 2 1228 proto1.optional_string = 'important-text' 1229 1230 proto1.CopyFrom(proto1) 1231 self.assertEqual(1, proto1.repeated_int32[0]) 1232 self.assertEqual(2, proto1.optional_int32) 1233 self.assertEqual('important-text', proto1.optional_string) 1234 1235 def testCopyFromBadType(self): 1236 # The python implementation doesn't raise an exception in this 1237 # case. In theory it should. 1238 if api_implementation.Type() == 'python': 1239 return 1240 proto1 = unittest_pb2.TestAllTypes() 1241 proto2 = unittest_pb2.TestAllExtensions() 1242 self.assertRaises(TypeError, proto1.CopyFrom, proto2) 1243 1244 def testClear(self): 1245 proto = unittest_pb2.TestAllTypes() 1246 test_util.SetAllFields(proto) 1247 # Clear the message. 1248 proto.Clear() 1249 self.assertEquals(proto.ByteSize(), 0) 1250 empty_proto = unittest_pb2.TestAllTypes() 1251 self.assertEquals(proto, empty_proto) 1252 1253 # Test if extensions which were set are cleared. 1254 proto = unittest_pb2.TestAllExtensions() 1255 test_util.SetAllExtensions(proto) 1256 # Clear the message. 1257 proto.Clear() 1258 self.assertEquals(proto.ByteSize(), 0) 1259 empty_proto = unittest_pb2.TestAllExtensions() 1260 self.assertEquals(proto, empty_proto) 1261 1262 def assertInitialized(self, proto): 1263 self.assertTrue(proto.IsInitialized()) 1264 # Neither method should raise an exception. 1265 proto.SerializeToString() 1266 proto.SerializePartialToString() 1267 1268 def assertNotInitialized(self, proto): 1269 self.assertFalse(proto.IsInitialized()) 1270 self.assertRaises(message.EncodeError, proto.SerializeToString) 1271 # "Partial" serialization doesn't care if message is uninitialized. 1272 proto.SerializePartialToString() 1273 1274 def testIsInitialized(self): 1275 # Trivial cases - all optional fields and extensions. 1276 proto = unittest_pb2.TestAllTypes() 1277 self.assertInitialized(proto) 1278 proto = unittest_pb2.TestAllExtensions() 1279 self.assertInitialized(proto) 1280 1281 # The case of uninitialized required fields. 1282 proto = unittest_pb2.TestRequired() 1283 self.assertNotInitialized(proto) 1284 proto.a = proto.b = proto.c = 2 1285 self.assertInitialized(proto) 1286 1287 # The case of uninitialized submessage. 1288 proto = unittest_pb2.TestRequiredForeign() 1289 self.assertInitialized(proto) 1290 proto.optional_message.a = 1 1291 self.assertNotInitialized(proto) 1292 proto.optional_message.b = 0 1293 proto.optional_message.c = 0 1294 self.assertInitialized(proto) 1295 1296 # Uninitialized repeated submessage. 1297 message1 = proto.repeated_message.add() 1298 self.assertNotInitialized(proto) 1299 message1.a = message1.b = message1.c = 0 1300 self.assertInitialized(proto) 1301 1302 # Uninitialized repeated group in an extension. 1303 proto = unittest_pb2.TestAllExtensions() 1304 extension = unittest_pb2.TestRequired.multi 1305 message1 = proto.Extensions[extension].add() 1306 message2 = proto.Extensions[extension].add() 1307 self.assertNotInitialized(proto) 1308 message1.a = 1 1309 message1.b = 1 1310 message1.c = 1 1311 self.assertNotInitialized(proto) 1312 message2.a = 2 1313 message2.b = 2 1314 message2.c = 2 1315 self.assertInitialized(proto) 1316 1317 # Uninitialized nonrepeated message in an extension. 1318 proto = unittest_pb2.TestAllExtensions() 1319 extension = unittest_pb2.TestRequired.single 1320 proto.Extensions[extension].a = 1 1321 self.assertNotInitialized(proto) 1322 proto.Extensions[extension].b = 2 1323 proto.Extensions[extension].c = 3 1324 self.assertInitialized(proto) 1325 1326 # Try passing an errors list. 1327 errors = [] 1328 proto = unittest_pb2.TestRequired() 1329 self.assertFalse(proto.IsInitialized(errors)) 1330 self.assertEqual(errors, ['a', 'b', 'c']) 1331 1332 def testStringUTF8Encoding(self): 1333 proto = unittest_pb2.TestAllTypes() 1334 1335 # Assignment of a unicode object to a field of type 'bytes' is not allowed. 1336 self.assertRaises(TypeError, 1337 setattr, proto, 'optional_bytes', u'unicode object') 1338 1339 # Check that the default value is of python's 'unicode' type. 1340 self.assertEqual(type(proto.optional_string), unicode) 1341 1342 proto.optional_string = unicode('Testing') 1343 self.assertEqual(proto.optional_string, str('Testing')) 1344 1345 # Assign a value of type 'str' which can be encoded in UTF-8. 1346 proto.optional_string = str('Testing') 1347 self.assertEqual(proto.optional_string, unicode('Testing')) 1348 1349 if api_implementation.Type() == 'python': 1350 # Values of type 'str' are also accepted as long as they can be 1351 # encoded in UTF-8. 1352 self.assertEqual(type(proto.optional_string), str) 1353 1354 # Try to assign a 'str' value which contains bytes that aren't 7-bit ASCII. 1355 self.assertRaises(ValueError, 1356 setattr, proto, 'optional_string', str('a\x80a')) 1357 # Assign a 'str' object which contains a UTF-8 encoded string. 1358 self.assertRaises(ValueError, 1359 setattr, proto, 'optional_string', '????') 1360 # No exception thrown. 1361 proto.optional_string = 'abc' 1362 1363 def testStringUTF8Serialization(self): 1364 proto = unittest_mset_pb2.TestMessageSet() 1365 extension_message = unittest_mset_pb2.TestMessageSetExtension2 1366 extension = extension_message.message_set_extension 1367 1368 test_utf8 = u'????' 1369 test_utf8_bytes = test_utf8.encode('utf-8') 1370 1371 # 'Test' in another language, using UTF-8 charset. 1372 proto.Extensions[extension].str = test_utf8 1373 1374 # Serialize using the MessageSet wire format (this is specified in the 1375 # .proto file). 1376 serialized = proto.SerializeToString() 1377 1378 # Check byte size. 1379 self.assertEqual(proto.ByteSize(), len(serialized)) 1380 1381 raw = unittest_mset_pb2.RawMessageSet() 1382 raw.MergeFromString(serialized) 1383 1384 message2 = unittest_mset_pb2.TestMessageSetExtension2() 1385 1386 self.assertEqual(1, len(raw.item)) 1387 # Check that the type_id is the same as the tag ID in the .proto file. 1388 self.assertEqual(raw.item[0].type_id, 1547769) 1389 1390 # Check the actual bytes on the wire. 1391 self.assertTrue( 1392 raw.item[0].message.endswith(test_utf8_bytes)) 1393 message2.MergeFromString(raw.item[0].message) 1394 1395 self.assertEqual(type(message2.str), unicode) 1396 self.assertEqual(message2.str, test_utf8) 1397 1398 # The pure Python API throws an exception on MergeFromString(), 1399 # if any of the string fields of the message can't be UTF-8 decoded. 1400 # The C++ implementation of the API has no way to check that on 1401 # MergeFromString and thus has no way to throw the exception. 1402 # 1403 # The pure Python API always returns objects of type 'unicode' (UTF-8 1404 # encoded), or 'str' (in 7 bit ASCII). 1405 bytes = raw.item[0].message.replace( 1406 test_utf8_bytes, len(test_utf8_bytes) * '\xff') 1407 1408 unicode_decode_failed = False 1409 try: 1410 message2.MergeFromString(bytes) 1411 except UnicodeDecodeError, e: 1412 unicode_decode_failed = True 1413 string_field = message2.str 1414 self.assertTrue(unicode_decode_failed or type(string_field) == str) 1415 1416 def testEmptyNestedMessage(self): 1417 proto = unittest_pb2.TestAllTypes() 1418 proto.optional_nested_message.MergeFrom( 1419 unittest_pb2.TestAllTypes.NestedMessage()) 1420 self.assertTrue(proto.HasField('optional_nested_message')) 1421 1422 proto = unittest_pb2.TestAllTypes() 1423 proto.optional_nested_message.CopyFrom( 1424 unittest_pb2.TestAllTypes.NestedMessage()) 1425 self.assertTrue(proto.HasField('optional_nested_message')) 1426 1427 proto = unittest_pb2.TestAllTypes() 1428 proto.optional_nested_message.MergeFromString('') 1429 self.assertTrue(proto.HasField('optional_nested_message')) 1430 1431 proto = unittest_pb2.TestAllTypes() 1432 proto.optional_nested_message.ParseFromString('') 1433 self.assertTrue(proto.HasField('optional_nested_message')) 1434 1435 serialized = proto.SerializeToString() 1436 proto2 = unittest_pb2.TestAllTypes() 1437 proto2.MergeFromString(serialized) 1438 self.assertTrue(proto2.HasField('optional_nested_message')) 1439 1440 def testSetInParent(self): 1441 proto = unittest_pb2.TestAllTypes() 1442 self.assertFalse(proto.HasField('optionalgroup')) 1443 proto.optionalgroup.SetInParent() 1444 self.assertTrue(proto.HasField('optionalgroup')) 1445 1446 1447# Since we had so many tests for protocol buffer equality, we broke these out 1448# into separate TestCase classes. 1449 1450 1451class TestAllTypesEqualityTest(unittest.TestCase): 1452 1453 def setUp(self): 1454 self.first_proto = unittest_pb2.TestAllTypes() 1455 self.second_proto = unittest_pb2.TestAllTypes() 1456 1457 def testNotHashable(self): 1458 self.assertRaises(TypeError, hash, self.first_proto) 1459 1460 def testSelfEquality(self): 1461 self.assertEqual(self.first_proto, self.first_proto) 1462 1463 def testEmptyProtosEqual(self): 1464 self.assertEqual(self.first_proto, self.second_proto) 1465 1466 1467class FullProtosEqualityTest(unittest.TestCase): 1468 1469 """Equality tests using completely-full protos as a starting point.""" 1470 1471 def setUp(self): 1472 self.first_proto = unittest_pb2.TestAllTypes() 1473 self.second_proto = unittest_pb2.TestAllTypes() 1474 test_util.SetAllFields(self.first_proto) 1475 test_util.SetAllFields(self.second_proto) 1476 1477 def testNotHashable(self): 1478 self.assertRaises(TypeError, hash, self.first_proto) 1479 1480 def testNoneNotEqual(self): 1481 self.assertNotEqual(self.first_proto, None) 1482 self.assertNotEqual(None, self.second_proto) 1483 1484 def testNotEqualToOtherMessage(self): 1485 third_proto = unittest_pb2.TestRequired() 1486 self.assertNotEqual(self.first_proto, third_proto) 1487 self.assertNotEqual(third_proto, self.second_proto) 1488 1489 def testAllFieldsFilledEquality(self): 1490 self.assertEqual(self.first_proto, self.second_proto) 1491 1492 def testNonRepeatedScalar(self): 1493 # Nonrepeated scalar field change should cause inequality. 1494 self.first_proto.optional_int32 += 1 1495 self.assertNotEqual(self.first_proto, self.second_proto) 1496 # ...as should clearing a field. 1497 self.first_proto.ClearField('optional_int32') 1498 self.assertNotEqual(self.first_proto, self.second_proto) 1499 1500 def testNonRepeatedComposite(self): 1501 # Change a nonrepeated composite field. 1502 self.first_proto.optional_nested_message.bb += 1 1503 self.assertNotEqual(self.first_proto, self.second_proto) 1504 self.first_proto.optional_nested_message.bb -= 1 1505 self.assertEqual(self.first_proto, self.second_proto) 1506 # Clear a field in the nested message. 1507 self.first_proto.optional_nested_message.ClearField('bb') 1508 self.assertNotEqual(self.first_proto, self.second_proto) 1509 self.first_proto.optional_nested_message.bb = ( 1510 self.second_proto.optional_nested_message.bb) 1511 self.assertEqual(self.first_proto, self.second_proto) 1512 # Remove the nested message entirely. 1513 self.first_proto.ClearField('optional_nested_message') 1514 self.assertNotEqual(self.first_proto, self.second_proto) 1515 1516 def testRepeatedScalar(self): 1517 # Change a repeated scalar field. 1518 self.first_proto.repeated_int32.append(5) 1519 self.assertNotEqual(self.first_proto, self.second_proto) 1520 self.first_proto.ClearField('repeated_int32') 1521 self.assertNotEqual(self.first_proto, self.second_proto) 1522 1523 def testRepeatedComposite(self): 1524 # Change value within a repeated composite field. 1525 self.first_proto.repeated_nested_message[0].bb += 1 1526 self.assertNotEqual(self.first_proto, self.second_proto) 1527 self.first_proto.repeated_nested_message[0].bb -= 1 1528 self.assertEqual(self.first_proto, self.second_proto) 1529 # Add a value to a repeated composite field. 1530 self.first_proto.repeated_nested_message.add() 1531 self.assertNotEqual(self.first_proto, self.second_proto) 1532 self.second_proto.repeated_nested_message.add() 1533 self.assertEqual(self.first_proto, self.second_proto) 1534 1535 def testNonRepeatedScalarHasBits(self): 1536 # Ensure that we test "has" bits as well as value for 1537 # nonrepeated scalar field. 1538 self.first_proto.ClearField('optional_int32') 1539 self.second_proto.optional_int32 = 0 1540 self.assertNotEqual(self.first_proto, self.second_proto) 1541 1542 def testNonRepeatedCompositeHasBits(self): 1543 # Ensure that we test "has" bits as well as value for 1544 # nonrepeated composite field. 1545 self.first_proto.ClearField('optional_nested_message') 1546 self.second_proto.optional_nested_message.ClearField('bb') 1547 self.assertNotEqual(self.first_proto, self.second_proto) 1548 self.first_proto.optional_nested_message.bb = 0 1549 self.first_proto.optional_nested_message.ClearField('bb') 1550 self.assertEqual(self.first_proto, self.second_proto) 1551 1552 1553class ExtensionEqualityTest(unittest.TestCase): 1554 1555 def testExtensionEquality(self): 1556 first_proto = unittest_pb2.TestAllExtensions() 1557 second_proto = unittest_pb2.TestAllExtensions() 1558 self.assertEqual(first_proto, second_proto) 1559 test_util.SetAllExtensions(first_proto) 1560 self.assertNotEqual(first_proto, second_proto) 1561 test_util.SetAllExtensions(second_proto) 1562 self.assertEqual(first_proto, second_proto) 1563 1564 # Ensure that we check value equality. 1565 first_proto.Extensions[unittest_pb2.optional_int32_extension] += 1 1566 self.assertNotEqual(first_proto, second_proto) 1567 first_proto.Extensions[unittest_pb2.optional_int32_extension] -= 1 1568 self.assertEqual(first_proto, second_proto) 1569 1570 # Ensure that we also look at "has" bits. 1571 first_proto.ClearExtension(unittest_pb2.optional_int32_extension) 1572 second_proto.Extensions[unittest_pb2.optional_int32_extension] = 0 1573 self.assertNotEqual(first_proto, second_proto) 1574 first_proto.Extensions[unittest_pb2.optional_int32_extension] = 0 1575 self.assertEqual(first_proto, second_proto) 1576 1577 # Ensure that differences in cached values 1578 # don't matter if "has" bits are both false. 1579 first_proto = unittest_pb2.TestAllExtensions() 1580 second_proto = unittest_pb2.TestAllExtensions() 1581 self.assertEqual( 1582 0, first_proto.Extensions[unittest_pb2.optional_int32_extension]) 1583 self.assertEqual(first_proto, second_proto) 1584 1585 1586class MutualRecursionEqualityTest(unittest.TestCase): 1587 1588 def testEqualityWithMutualRecursion(self): 1589 first_proto = unittest_pb2.TestMutualRecursionA() 1590 second_proto = unittest_pb2.Tes