Browse Source

Check realoneof in json parsing (#7763)

* Check realoneof in json parsing

* Fix whichoneof to also work for synthetic oneof
Paul Yang 5 years ago
parent
commit
0929596575
3 changed files with 27 additions and 2 deletions
  1. 3 0
      .gitignore
  2. 6 2
      php/ext/google/protobuf/php-upb.c
  3. 18 0
      php/tests/encode_decode_test.php

+ 3 - 0
.gitignore

@@ -144,12 +144,15 @@ php/tests/core
 php/tests/vgcore*
 php/tests/vgcore*
 php/tests/multirequest.result
 php/tests/multirequest.result
 php/tests/nohup.out
 php/tests/nohup.out
+php/tests/.phpunit.result.cache
+php/tests/phpunit-*
 php/ext/google/protobuf/.libs/
 php/ext/google/protobuf/.libs/
 php/ext/google/protobuf/Makefile.fragments
 php/ext/google/protobuf/Makefile.fragments
 php/ext/google/protobuf/Makefile.global
 php/ext/google/protobuf/Makefile.global
 php/ext/google/protobuf/Makefile.objects
 php/ext/google/protobuf/Makefile.objects
 php/ext/google/protobuf/acinclude.m4
 php/ext/google/protobuf/acinclude.m4
 php/ext/google/protobuf/build/
 php/ext/google/protobuf/build/
+php/ext/google/protobuf/bundled_php.c
 php/ext/google/protobuf/config.h
 php/ext/google/protobuf/config.h
 php/ext/google/protobuf/config.h.in~
 php/ext/google/protobuf/config.h.in~
 php/ext/google/protobuf/config.nice
 php/ext/google/protobuf/config.nice

+ 6 - 2
php/ext/google/protobuf/php-upb.c

@@ -5665,7 +5665,11 @@ const upb_fielddef *upb_msg_whichoneof(const upb_msg *msg,
   if (upb_oneof_done(&i)) return false;
   if (upb_oneof_done(&i)) return false;
   f = upb_oneof_iter_field(&i);
   f = upb_oneof_iter_field(&i);
   field = upb_fielddef_layout(f);
   field = upb_fielddef_layout(f);
-  oneof_case = _upb_getoneofcase_field(msg, field);
+  if (in_oneof(field)) {
+    oneof_case = _upb_getoneofcase_field(msg, field);
+  } else {
+    return _upb_hasbit_field(msg, field) ? f : NULL;
+  }
 
 
   return oneof_case ? upb_msgdef_itof(m, oneof_case) : NULL;
   return oneof_case ? upb_msgdef_itof(m, oneof_case) : NULL;
 }
 }
@@ -6876,7 +6880,7 @@ static void jsondec_field(jsondec *d, upb_msg *msg, const upb_msgdef *m) {
     return;
     return;
   }
   }
 
 
-  if (upb_fielddef_containingoneof(f) &&
+  if (upb_fielddef_realcontainingoneof(f) &&
       upb_msg_whichoneof(msg, upb_fielddef_containingoneof(f))) {
       upb_msg_whichoneof(msg, upb_fielddef_containingoneof(f))) {
     jsondec_err(d, "More than one field for this oneof.");
     jsondec_err(d, "More than one field for this oneof.");
   }
   }

+ 18 - 0
php/tests/encode_decode_test.php

@@ -344,6 +344,24 @@ class EncodeDecodeTest extends TestBase
       $this->assertSame(0, $m2->getTrueOptionalInt32());
       $this->assertSame(0, $m2->getTrueOptionalInt32());
     }
     }
 
 
+    public function testJsonEncodeDecodeOptional()
+    {
+      $m = new TestMessage();
+      $this->assertFalse($m->hasTrueOptionalInt32());
+      $data = $m->serializeToJsonString();
+      $this->assertSame("{}", $data);
+
+      $m->setTrueOptionalInt32(0);
+      $this->assertTrue($m->hasTrueOptionalInt32());
+      $data = $m->serializeToJsonString();
+      $this->assertNotSame("{}", $data);
+
+      $m2 = new TestMessage();
+      $m2->mergeFromJsonString($data);
+      $this->assertTrue($m2->hasTrueOptionalInt32());
+      $this->assertSame(0, $m2->getTrueOptionalInt32());
+    }
+
     public function testJsonEncodeDecodeOneof()
     public function testJsonEncodeDecodeOneof()
     {
     {
         $m = new TestMessage();
         $m = new TestMessage();