mirror of
https://github.com/protocolbuffers/protobuf
synced 2026-08-26 02:23:14 -04:00
Fixed a bug in msg.MergeFrom(msg2) in Python.
In `FixupMessageAfterMerge()`, the loop over fields was exiting the entire function if a mutable field was found, but this skips other fields that may need fixing up. PiperOrigin-RevId: 882766354
This commit is contained in:
parent
08244d7a74
commit
ab14c0f8ad
3 changed files with 54 additions and 1 deletions
|
|
@ -3071,6 +3071,34 @@ class PackedFieldTest(unittest.TestCase):
|
|||
self.assertEqual(golden_data, message.SerializeToString())
|
||||
|
||||
|
||||
@testing_refleaks.TestCase
|
||||
class MergeFromTest(unittest.TestCase):
|
||||
def testBugFixupAfterMerge(self):
|
||||
target = more_messages_pb2.LotsOfMessageFields()
|
||||
wrappers = []
|
||||
|
||||
# Access all fields mutably, except for a10 which is accessed read-only.
|
||||
for i in range(1, 21):
|
||||
sub = getattr(target, f'a{i}')
|
||||
wrappers.append(sub)
|
||||
if i != 10:
|
||||
# Access mutable.
|
||||
sub.b = 1
|
||||
|
||||
self.assertEqual(target.a10.b, 0)
|
||||
self.assertFalse(target.HasField('a10'))
|
||||
|
||||
source = more_messages_pb2.LotsOfMessageFields()
|
||||
source.a10.b = 1
|
||||
|
||||
# The read-only message target.a10 needs to be updated to point to the new
|
||||
# message that is created by MergeFrom.
|
||||
target.MergeFrom(source)
|
||||
|
||||
self.assertEqual(target.a10.b, 1)
|
||||
self.assertTrue(target.HasField('a10'))
|
||||
|
||||
|
||||
@testing_refleaks.TestCase
|
||||
class OversizeProtosTest(unittest.TestCase):
|
||||
|
||||
|
|
|
|||
|
|
@ -342,6 +342,31 @@ message LotsNestedMessage {
|
|||
message B255 {}
|
||||
}
|
||||
|
||||
message LotsOfMessageFields {
|
||||
optional LotsOfMessageFields a1 = 1;
|
||||
optional LotsOfMessageFields a2 = 2;
|
||||
optional LotsOfMessageFields a3 = 3;
|
||||
optional LotsOfMessageFields a4 = 4;
|
||||
optional LotsOfMessageFields a5 = 5;
|
||||
optional LotsOfMessageFields a6 = 6;
|
||||
optional LotsOfMessageFields a7 = 7;
|
||||
optional LotsOfMessageFields a8 = 8;
|
||||
optional LotsOfMessageFields a9 = 9;
|
||||
optional LotsOfMessageFields a10 = 10;
|
||||
optional LotsOfMessageFields a11 = 11;
|
||||
optional LotsOfMessageFields a12 = 12;
|
||||
optional LotsOfMessageFields a13 = 13;
|
||||
optional LotsOfMessageFields a14 = 14;
|
||||
optional LotsOfMessageFields a15 = 15;
|
||||
optional LotsOfMessageFields a16 = 16;
|
||||
optional LotsOfMessageFields a17 = 17;
|
||||
optional LotsOfMessageFields a18 = 18;
|
||||
optional LotsOfMessageFields a19 = 19;
|
||||
optional LotsOfMessageFields a20 = 20;
|
||||
|
||||
optional int32 b = 100;
|
||||
}
|
||||
|
||||
message RequiredField {
|
||||
required int32 id = 1;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -810,7 +810,7 @@ int FixupMessageAfterMerge(CMessage* self) {
|
|||
!descriptor->is_repeated()) {
|
||||
CMessage* cmsg = reinterpret_cast<CMessage*>(item.second);
|
||||
if (cmsg->read_only == false) {
|
||||
return 0;
|
||||
continue;
|
||||
}
|
||||
Message* message = self->message;
|
||||
const Reflection* reflection = message->GetReflection();
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue