xref: /aosp_15_r20/external/cronet/third_party/protobuf/php/tests/GeneratedClassTest.php (revision 6777b5387eb2ff775bb5750e3f5d96f37fb7352b)
1<?php
2
3require_once('test_base.php');
4require_once('test_util.php');
5
6use Google\Protobuf\Internal\RepeatedField;
7use Google\Protobuf\Internal\MapField;
8use Google\Protobuf\Internal\GPBType;
9use Bar\TestLegacyMessage;
10use Bar\TestLegacyMessage_NestedEnum;
11use Bar\TestLegacyMessage_NestedMessage;
12use Foo\Test32Fields;
13use Foo\TestEnum;
14use Foo\TestIncludeNamespaceMessage;
15use Foo\TestIncludePrefixMessage;
16use Foo\TestMessage;
17use Foo\TestMessage\Sub;
18use Foo\TestMessage_Sub;
19use Foo\TestMessage\NestedEnum;
20use Foo\TestReverseFieldOrder;
21use Foo\testLowerCaseMessage;
22use Foo\testLowerCaseEnum;
23use PBEmpty\PBEcho\TestEmptyPackage;
24use Php\Test\TestNamespace;
25
26# This is not allowed, but we at least shouldn't crash.
27class C extends \Google\Protobuf\Internal\Message {
28    public function __construct($data = null) {
29        parent::__construct($data);
30    }
31}
32
33class GeneratedClassTest extends TestBase
34{
35
36    #########################################################
37    # Test field accessors.
38    #########################################################
39
40    public function testSetterGetter()
41    {
42        $m = new TestMessage();
43        $m->setOptionalInt32(1);
44        $this->assertSame(1, $m->getOptionalInt32());
45    }
46
47    #########################################################
48    # Test int32 field.
49    #########################################################
50
51    public function testInt32Field()
52    {
53        $m = new TestMessage();
54
55        // Set integer.
56        $m->setOptionalInt32(MAX_INT32);
57        $this->assertSame(MAX_INT32, $m->getOptionalInt32());
58        $m->setOptionalInt32(MIN_INT32);
59        $this->assertSame(MIN_INT32, $m->getOptionalInt32());
60
61        // Set float.
62        $m->setOptionalInt32(1.1);
63        $this->assertSame(1, $m->getOptionalInt32());
64        $m->setOptionalInt32(MAX_INT32_FLOAT);
65        $this->assertSame(MAX_INT32, $m->getOptionalInt32());
66        $m->setOptionalInt32(MIN_INT32_FLOAT);
67        $this->assertSame(MIN_INT32, $m->getOptionalInt32());
68
69        // Set string.
70        $m->setOptionalInt32('2');
71        $this->assertSame(2, $m->getOptionalInt32());
72        $m->setOptionalInt32('3.1');
73        $this->assertSame(3, $m->getOptionalInt32());
74        $m->setOptionalInt32(MAX_INT32_STRING);
75        $this->assertSame(MAX_INT32, $m->getOptionalInt32());
76        $m->setOptionalInt32(MIN_INT32_STRING);
77        $this->assertSame(MIN_INT32, $m->getOptionalInt32());
78    }
79
80    #########################################################
81    # Test deprecated int32 field.
82    #########################################################
83
84    public function testDeprecatedInt32Field()
85    {
86        $m = new TestMessage();
87
88        // temporarily change error handler to capture the deprecated errors
89        $deprecationCount = 0;
90        set_error_handler(function ($errno, $errstr) use (&$deprecationCount) {
91            if ($errstr === 'deprecated_optional_int32 is deprecated.') {
92                $deprecationCount++;
93            }
94        }, E_USER_DEPRECATED);
95
96        // default test set
97        $m->setDeprecatedOptionalInt32(MAX_INT32);
98        $this->assertSame(MAX_INT32, $m->getDeprecatedOptionalInt32());
99        $m->setDeprecatedOptionalInt32(MIN_INT32);
100        $this->assertSame(MIN_INT32, $m->getDeprecatedOptionalInt32());
101
102        restore_error_handler();
103
104        $this->assertSame(4, $deprecationCount);
105    }
106
107    #########################################################
108    # Test optional int32 field.
109    #########################################################
110
111    public function testOptionalInt32Field()
112    {
113        $m = new TestMessage();
114
115        $this->assertFalse($m->hasTrueOptionalInt32());
116        $this->assertSame(0, $m->getTrueOptionalInt32());
117
118        // Set integer.
119        $m->setTrueOptionalInt32(MAX_INT32);
120        $this->assertTrue($m->hasTrueOptionalInt32());
121        $this->assertSame(MAX_INT32, $m->getTrueOptionalInt32());
122
123        // Clear integer.
124        $m->clearTrueOptionalInt32();
125        $this->assertFalse($m->hasTrueOptionalInt32());
126        $this->assertSame(0, $m->getTrueOptionalInt32());
127    }
128
129    #########################################################
130    # Test uint32 field.
131    #########################################################
132
133    public function testUint32Field()
134    {
135        $m = new TestMessage();
136
137        // Set integer.
138        $m->setOptionalUint32(MAX_UINT32);
139        $this->assertSame(-1, $m->getOptionalUint32());
140        $m->setOptionalUint32(-1);
141        $this->assertSame(-1, $m->getOptionalUint32());
142        $m->setOptionalUint32(MIN_UINT32);
143        $this->assertSame(MIN_INT32, $m->getOptionalUint32());
144
145        // Set float.
146        $m->setOptionalUint32(1.1);
147        $this->assertSame(1, $m->getOptionalUint32());
148        $m->setOptionalUint32(MAX_UINT32_FLOAT);
149        $this->assertSame(-1, $m->getOptionalUint32());
150        $m->setOptionalUint32(-1.0);
151        $this->assertSame(-1, $m->getOptionalUint32());
152        $m->setOptionalUint32(MIN_UINT32_FLOAT);
153        $this->assertSame(MIN_INT32, $m->getOptionalUint32());
154
155        // Set string.
156        $m->setOptionalUint32('2');
157        $this->assertSame(2, $m->getOptionalUint32());
158        $m->setOptionalUint32('3.1');
159        $this->assertSame(3, $m->getOptionalUint32());
160        $m->setOptionalUint32(MAX_UINT32_STRING);
161        $this->assertSame(-1, $m->getOptionalUint32());
162        $m->setOptionalUint32('-1.0');
163        $this->assertSame(-1, $m->getOptionalUint32());
164        $m->setOptionalUint32(MIN_UINT32_STRING);
165        $this->assertSame(MIN_INT32, $m->getOptionalUint32());
166    }
167
168    #########################################################
169    # Test int64 field.
170    #########################################################
171
172    public function testInt64Field()
173    {
174        $m = new TestMessage();
175
176        // Set integer.
177        $m->setOptionalInt64(MAX_INT64);
178        $this->assertSame(MAX_INT64, $m->getOptionalInt64());
179        $m->setOptionalInt64(MIN_INT64);
180        $this->assertEquals(MIN_INT64, $m->getOptionalInt64());
181
182        // Set float.
183        $m->setOptionalInt64(1.1);
184        if (PHP_INT_SIZE == 4) {
185            $this->assertSame('1', $m->getOptionalInt64());
186        } else {
187            $this->assertSame(1, $m->getOptionalInt64());
188        }
189
190        // Set string.
191        $m->setOptionalInt64('2');
192        if (PHP_INT_SIZE == 4) {
193            $this->assertSame('2', $m->getOptionalInt64());
194        } else {
195            $this->assertSame(2, $m->getOptionalInt64());
196        }
197
198        $m->setOptionalInt64('3.1');
199        if (PHP_INT_SIZE == 4) {
200            $this->assertSame('3', $m->getOptionalInt64());
201        } else {
202            $this->assertSame(3, $m->getOptionalInt64());
203        }
204
205        $m->setOptionalInt64(MAX_INT64_STRING);
206        if (PHP_INT_SIZE == 4) {
207            $this->assertSame(MAX_INT64_STRING, $m->getOptionalInt64());
208        } else {
209            $this->assertSame(MAX_INT64, $m->getOptionalInt64());
210        }
211
212        $m->setOptionalInt64(MIN_INT64_STRING);
213        if (PHP_INT_SIZE == 4) {
214            $this->assertSame(MIN_INT64_STRING, $m->getOptionalInt64());
215        } else {
216            $this->assertSame(MIN_INT64, $m->getOptionalInt64());
217        }
218    }
219
220    #########################################################
221    # Test uint64 field.
222    #########################################################
223
224    public function testUint64Field()
225    {
226        $m = new TestMessage();
227
228        // Set integer.
229        $m->setOptionalUint64(MAX_UINT64);
230        if (PHP_INT_SIZE == 4) {
231            $this->assertSame(MAX_UINT64_STRING, $m->getOptionalUint64());
232        } else {
233            $this->assertSame(MAX_UINT64, $m->getOptionalUint64());
234        }
235
236        // Set float.
237        $m->setOptionalUint64(1.1);
238        if (PHP_INT_SIZE == 4) {
239            $this->assertSame('1', $m->getOptionalUint64());
240        } else {
241            $this->assertSame(1, $m->getOptionalUint64());
242        }
243
244        // Set string.
245        $m->setOptionalUint64('2');
246        if (PHP_INT_SIZE == 4) {
247            $this->assertSame('2', $m->getOptionalUint64());
248        } else {
249            $this->assertSame(2, $m->getOptionalUint64());
250        }
251
252        $m->setOptionalUint64('3.1');
253        if (PHP_INT_SIZE == 4) {
254            $this->assertSame('3', $m->getOptionalUint64());
255        } else {
256            $this->assertSame(3, $m->getOptionalUint64());
257        }
258
259        $m->setOptionalUint64(MAX_UINT64_STRING);
260        if (PHP_INT_SIZE == 4) {
261            $this->assertSame(MAX_UINT64_STRING, $m->getOptionalUint64());
262        } else {
263            $this->assertSame(MAX_UINT64, $m->getOptionalUint64());
264        }
265    }
266
267    #########################################################
268    # Test enum field.
269    #########################################################
270
271    public function testEnumField()
272    {
273        $m = new TestMessage();
274
275        // Set enum.
276        $m->setOptionalEnum(TestEnum::ONE);
277        $this->assertEquals(TestEnum::ONE, $m->getOptionalEnum());
278
279        // Set integer.
280        $m->setOptionalEnum(1);
281        $this->assertEquals(TestEnum::ONE, $m->getOptionalEnum());
282
283        // Set float.
284        $m->setOptionalEnum(1.1);
285        $this->assertEquals(TestEnum::ONE, $m->getOptionalEnum());
286
287        // Set string.
288        $m->setOptionalEnum("1");
289        $this->assertEquals(TestEnum::ONE, $m->getOptionalEnum());
290
291        // Test Enum methods
292        $this->assertEquals('ONE', TestEnum::name(1));
293        $this->assertEquals(1, TestEnum::value('ONE'));
294        $this->assertEquals('ECHO', TestEnum::name(3));
295        $this->assertEquals(3, TestEnum::value('ECHO'));
296        // Backwards compat value lookup by prefixed-name.
297        $this->assertEquals(3, TestEnum::value('PBECHO'));
298    }
299
300    public function testInvalidEnumValueThrowsException()
301    {
302        $this->expectException(UnexpectedValueException::class);
303        $this->expectExceptionMessage(
304            'Enum Foo\TestEnum has no name defined for value -1');
305
306        TestEnum::name(-1);
307    }
308
309    public function testInvalidEnumNameThrowsException()
310    {
311        $this->expectException(UnexpectedValueException::class);
312        $this->expectExceptionMessage(
313            'Enum Foo\TestEnum has no value defined for name DOES_NOT_EXIST');
314
315        TestEnum::value('DOES_NOT_EXIST');
316    }
317
318    public function testNestedEnum()
319    {
320        $m = new TestMessage();
321        $m->setOptionalNestedEnum(NestedEnum::ZERO);
322        $this->assertTrue(true);
323    }
324
325    public function testLegacyNestedEnum()
326    {
327        $m = new TestMessage();
328        $m->setOptionalNestedEnum(\Foo\TestMessage_NestedEnum::ZERO);
329        $this->assertTrue(true);
330    }
331
332    public function testLegacyTypehintWithNestedEnums()
333    {
334        $this->legacyEnum(new TestLegacyMessage\NestedEnum);
335    }
336
337    public function testLegacyReadOnlyMessage()
338    {
339        $this->assertTrue(class_exists('\Upper\READONLY'));
340        $this->assertTrue(class_exists('\Lower\readonly'));
341        $this->assertTrue(class_exists('\Php\Test\TestNamespace\PBEmpty\ReadOnly'));
342    }
343
344    public function testLegacyReadOnlyEnum()
345    {
346        $this->assertTrue(class_exists('\Upper_enum\READONLY'));
347        $this->assertTrue(class_exists('\Lower_enum\readonly'));
348    }
349
350    private function legacyEnum(TestLegacyMessage_NestedEnum $enum)
351    {
352        // If we made it here without a PHP Fatal error, the typehint worked
353        $this->assertTrue(true);
354    }
355
356    #########################################################
357    # Test float field.
358    #########################################################
359
360    public function testFloatField()
361    {
362        $m = new TestMessage();
363
364        // Set integer.
365        $m->setOptionalFloat(1);
366        $this->assertFloatEquals(1.0, $m->getOptionalFloat(), MAX_FLOAT_DIFF);
367
368        // Set float.
369        $m->setOptionalFloat(1.1);
370        $this->assertFloatEquals(1.1, $m->getOptionalFloat(), MAX_FLOAT_DIFF);
371
372        // Set string.
373        $m->setOptionalFloat('2');
374        $this->assertFloatEquals(2.0, $m->getOptionalFloat(), MAX_FLOAT_DIFF);
375        $m->setOptionalFloat('3.1');
376        $this->assertFloatEquals(3.1, $m->getOptionalFloat(), MAX_FLOAT_DIFF);
377    }
378
379    #########################################################
380    # Test double field.
381    #########################################################
382
383    public function testDoubleField()
384    {
385        $m = new TestMessage();
386
387        // Set integer.
388        $m->setOptionalDouble(1);
389        $this->assertFloatEquals(1.0, $m->getOptionalDouble(), MAX_FLOAT_DIFF);
390
391        // Set float.
392        $m->setOptionalDouble(1.1);
393        $this->assertFloatEquals(1.1, $m->getOptionalDouble(), MAX_FLOAT_DIFF);
394
395        // Set string.
396        $m->setOptionalDouble('2');
397        $this->assertFloatEquals(2.0, $m->getOptionalDouble(), MAX_FLOAT_DIFF);
398        $m->setOptionalDouble('3.1');
399        $this->assertFloatEquals(3.1, $m->getOptionalDouble(), MAX_FLOAT_DIFF);
400    }
401
402    #########################################################
403    # Test bool field.
404    #########################################################
405
406    public function testBoolField()
407    {
408        $m = new TestMessage();
409
410        // Set bool.
411        $m->setOptionalBool(true);
412        $this->assertSame(true, $m->getOptionalBool());
413
414        // Set integer.
415        $m->setOptionalBool(-1);
416        $this->assertSame(true, $m->getOptionalBool());
417
418        // Set float.
419        $m->setOptionalBool(1.1);
420        $this->assertSame(true, $m->getOptionalBool());
421
422        // Set string.
423        $m->setOptionalBool('');
424        $this->assertSame(false, $m->getOptionalBool());
425    }
426
427    #########################################################
428    # Test string field.
429    #########################################################
430
431    public function testStringField()
432    {
433        $m = new TestMessage();
434
435        // Set string.
436        $m->setOptionalString('abc');
437        $this->assertSame('abc', $m->getOptionalString());
438
439        // Set integer.
440        $m->setOptionalString(1);
441        $this->assertSame('1', $m->getOptionalString());
442
443        // Set double.
444        $m->setOptionalString(1.1);
445        $this->assertSame('1.1', $m->getOptionalString());
446
447        // Set bool.
448        $m->setOptionalString(true);
449        $this->assertSame('1', $m->getOptionalString());
450    }
451
452    #########################################################
453    # Test bytes field.
454    #########################################################
455
456    public function testBytesField()
457    {
458        $m = new TestMessage();
459
460        // Set string.
461        $m->setOptionalBytes('abc');
462        $this->assertSame('abc', $m->getOptionalBytes());
463
464        // Set integer.
465        $m->setOptionalBytes(1);
466        $this->assertSame('1', $m->getOptionalBytes());
467
468        // Set double.
469        $m->setOptionalBytes(1.1);
470        $this->assertSame('1.1', $m->getOptionalBytes());
471
472        // Set bool.
473        $m->setOptionalBytes(true);
474        $this->assertSame('1', $m->getOptionalBytes());
475    }
476
477      public function testBytesFieldInvalidUTF8Success()
478      {
479          $m = new TestMessage();
480          $hex = hex2bin("ff");
481          $m->setOptionalBytes($hex);
482          $this->assertTrue(true);
483      }
484
485    #########################################################
486    # Test message field.
487    #########################################################
488
489    public function testMessageField()
490    {
491        $m = new TestMessage();
492
493        $this->assertNull($m->getOptionalMessage());
494
495        $sub_m = new Sub();
496        $sub_m->setA(1);
497        $m->setOptionalMessage($sub_m);
498        $this->assertSame(1, $m->getOptionalMessage()->getA());
499        $this->assertTrue($m->hasOptionalMessage());
500
501        $null = null;
502        $m->setOptionalMessage($null);
503        $this->assertNull($m->getOptionalMessage());
504        $this->assertFalse($m->hasOptionalMessage());
505    }
506
507    public function testLegacyMessageField()
508    {
509        $m = new TestMessage();
510
511        $sub_m = new TestMessage_Sub();
512        $sub_m->setA(1);
513        $m->setOptionalMessage($sub_m);
514        $this->assertSame(1, $m->getOptionalMessage()->getA());
515
516        $null = null;
517        $m->setOptionalMessage($null);
518        $this->assertNull($m->getOptionalMessage());
519    }
520
521    public function testLegacyTypehintWithNestedMessages()
522    {
523        $this->legacyMessage(new TestLegacyMessage\NestedMessage);
524    }
525
526    private function legacyMessage(TestLegacyMessage_NestedMessage $sub)
527    {
528        // If we made it here without a PHP Fatal error, the typehint worked
529        $this->assertTrue(true);
530    }
531
532    #########################################################
533    # Test repeated field.
534    #########################################################
535
536    public function testRepeatedField()
537    {
538        $m = new TestMessage();
539
540        $repeated_int32 = new RepeatedField(GPBType::INT32);
541        $m->setRepeatedInt32($repeated_int32);
542        $this->assertSame($repeated_int32, $m->getRepeatedInt32());
543    }
544
545    public function testRepeatedFieldViaArray()
546    {
547        $m = new TestMessage();
548
549        $arr = array();
550        $m->setRepeatedInt32($arr);
551        $this->assertSame(0, count($m->getRepeatedInt32()));
552
553        $arr = array(1, 2.1, "3");
554        $m->setRepeatedInt32($arr);
555        $this->assertTrue($m->getRepeatedInt32() instanceof RepeatedField);
556        $this->assertSame("Google\Protobuf\Internal\RepeatedField",
557                          get_class($m->getRepeatedInt32()));
558        $this->assertSame(3, count($m->getRepeatedInt32()));
559        $this->assertSame(1, $m->getRepeatedInt32()[0]);
560        $this->assertSame(2, $m->getRepeatedInt32()[1]);
561        $this->assertSame(3, $m->getRepeatedInt32()[2]);
562        $this->assertFalse($arr instanceof RepeatedField);
563    }
564
565    #########################################################
566    # Test map field.
567    #########################################################
568
569    public function testMapField()
570    {
571        $m = new TestMessage();
572
573        $map_int32_int32 = new MapField(GPBType::INT32, GPBType::INT32);
574        $m->setMapInt32Int32($map_int32_int32);
575        $this->assertSame($map_int32_int32, $m->getMapInt32Int32());
576    }
577
578    public function testMapFieldViaArray()
579    {
580        $m = new TestMessage();
581
582        $dict = array();
583        $m->setMapInt32Int32($dict);
584        $this->assertSame(0, count($m->getMapInt32Int32()));
585
586        $dict = array(5 => 5, 6 => 6.1, "7" => "7");
587        $m->setMapInt32Int32($dict);
588        $this->assertTrue($m->getMapInt32Int32() instanceof MapField);
589        $this->assertSame(3, count($m->getMapInt32Int32()));
590        $this->assertSame(5, $m->getMapInt32Int32()[5]);
591        $this->assertSame(6, $m->getMapInt32Int32()[6]);
592        $this->assertSame(7, $m->getMapInt32Int32()[7]);
593        $this->assertFalse($dict instanceof MapField);
594    }
595
596    #########################################################
597    # Test oneof field.
598    #########################################################
599
600    public function testOneofField() {
601        $m = new TestMessage();
602
603        $this->assertSame("", $m->getMyOneof());
604
605        $m->setOneofInt32(1);
606        $this->assertSame(1, $m->getOneofInt32());
607        $this->assertSame(0.0, $m->getOneofFloat());
608        $this->assertSame('', $m->getOneofString());
609        $this->assertSame(NULL, $m->getOneofMessage());
610        $this->assertSame("oneof_int32", $m->getMyOneof());
611
612        $m->setOneofFloat(2.0);
613        $this->assertSame(0, $m->getOneofInt32());
614        $this->assertSame(2.0, $m->getOneofFloat());
615        $this->assertSame('', $m->getOneofString());
616        $this->assertSame(NULL, $m->getOneofMessage());
617        $this->assertSame("oneof_float", $m->getMyOneof());
618
619        $m->setOneofString('abc');
620        $this->assertSame(0, $m->getOneofInt32());
621        $this->assertSame(0.0, $m->getOneofFloat());
622        $this->assertSame('abc', $m->getOneofString());
623        $this->assertSame(NULL, $m->getOneofMessage());
624        $this->assertSame("oneof_string", $m->getMyOneof());
625
626        $sub_m = new Sub();
627        $sub_m->setA(1);
628        $m->setOneofMessage($sub_m);
629        $this->assertSame(0, $m->getOneofInt32());
630        $this->assertSame(0.0, $m->getOneofFloat());
631        $this->assertSame('', $m->getOneofString());
632        $this->assertSame(1, $m->getOneofMessage()->getA());
633        $this->assertSame("oneof_message", $m->getMyOneof());
634    }
635
636    #########################################################
637    # Test clear method.
638    #########################################################
639
640    public function testMessageClear()
641    {
642        $m = new TestMessage();
643        $this->setFields($m);
644        $this->expectFields($m);
645        $m->clear();
646        $this->expectEmptyFields($m);
647    }
648
649    #########################################################
650    # Test mergeFrom method.
651    #########################################################
652
653    public function testMessageMergeFrom()
654    {
655        $m = new TestMessage();
656        $this->setFields($m);
657        $this->expectFields($m);
658        $arr = $m->getOptionalMessage()->getB();
659        $arr[] = 1;
660
661        $n = new TestMessage();
662
663        // Singular
664        $n->setOptionalInt32(100);
665        $sub1 = new Sub();
666        $sub1->setA(101);
667
668        $b = $sub1->getB();
669        $b[] = 102;
670        $sub1->setB($b);
671
672        $n->setOptionalMessage($sub1);
673
674        // Repeated
675        $repeatedInt32 = $n->getRepeatedInt32();
676        $repeatedInt32[] = 200;
677        $n->setRepeatedInt32($repeatedInt32);
678
679        $repeatedString = $n->getRepeatedString();
680        $repeatedString[] = 'abc';
681        $n->setRepeatedString($repeatedString);
682
683        $sub2 = new Sub();
684        $sub2->setA(201);
685        $repeatedMessage = $n->getRepeatedMessage();
686        $repeatedMessage[] = $sub2;
687        $n->setRepeatedMessage($repeatedMessage);
688
689        // Map
690        $mapInt32Int32 = $n->getMapInt32Int32();
691        $mapInt32Int32[1] = 300;
692        $mapInt32Int32[-62] = 301;
693        $n->setMapInt32Int32($mapInt32Int32);
694
695        $mapStringString = $n->getMapStringString();
696        $mapStringString['def'] = 'def';
697        $n->setMapStringString($mapStringString);
698
699        $mapInt32Message = $n->getMapInt32Message();
700        $mapInt32Message[1] = new Sub();
701        $mapInt32Message[1]->setA(302);
702        $mapInt32Message[2] = new Sub();
703        $mapInt32Message[2]->setA(303);
704        $n->setMapInt32Message($mapInt32Message);
705
706        $m->mergeFrom($n);
707
708        $this->assertSame(100, $m->getOptionalInt32());
709        $this->assertSame(42, $m->getOptionalUint32());
710        $this->assertSame(101, $m->getOptionalMessage()->getA());
711        $this->assertSame(2, count($m->getOptionalMessage()->getB()));
712        $this->assertSame(1, $m->getOptionalMessage()->getB()[0]);
713        $this->assertSame(102, $m->getOptionalMessage()->getB()[1]);
714
715        $this->assertSame(3, count($m->getRepeatedInt32()));
716        $this->assertSame(200, $m->getRepeatedInt32()[2]);
717        $this->assertSame(2, count($m->getRepeatedUint32()));
718        $this->assertSame(3, count($m->getRepeatedString()));
719        $this->assertSame('abc', $m->getRepeatedString()[2]);
720        $this->assertSame(3, count($m->getRepeatedMessage()));
721        $this->assertSame(201, $m->getRepeatedMessage()[2]->getA());
722
723        $this->assertSame(2, count($m->getMapInt32Int32()));
724        $this->assertSame(300, $m->getMapInt32Int32()[1]);
725        $this->assertSame(301, $m->getMapInt32Int32()[-62]);
726        $this->assertSame(1, count($m->getMapUint32Uint32()));
727        $this->assertSame(2, count($m->getMapStringString()));
728        $this->assertSame('def', $m->getMapStringString()['def']);
729
730        $this->assertSame(2, count($m->getMapInt32Message()));
731        $this->assertSame(302, $m->getMapInt32Message()[1]->getA());
732        $this->assertSame(303, $m->getMapInt32Message()[2]->getA());
733
734        $this->assertSame("", $m->getMyOneof());
735
736        // Check sub-messages are copied by value.
737        $n->getOptionalMessage()->setA(-101);
738        $this->assertSame(101, $m->getOptionalMessage()->getA());
739
740        $repeatedMessage = $n->getRepeatedMessage();
741        $repeatedMessage[0]->setA(-201);
742        $n->setRepeatedMessage($repeatedMessage);
743        $this->assertSame(201, $m->getRepeatedMessage()[2]->getA());
744
745        $mapInt32Message = $n->getMapInt32Message();
746        $mapInt32Message[1]->setA(-302);
747        $n->setMapInt32Message($mapInt32Message);
748
749        $this->assertSame(302, $m->getMapInt32Message()[1]->getA());
750
751        // Test merge oneof.
752        $m = new TestMessage();
753
754        $n = new TestMessage();
755        $n->setOneofInt32(1);
756        $m->mergeFrom($n);
757        $this->assertSame(1, $m->getOneofInt32());
758
759        $sub = new Sub();
760        $n->setOneofMessage($sub);
761        $n->getOneofMessage()->setA(400);
762        $m->mergeFrom($n);
763        $this->assertSame(400, $m->getOneofMessage()->getA());
764        $n->getOneofMessage()->setA(-400);
765        $this->assertSame(400, $m->getOneofMessage()->getA());
766
767        // Test all fields
768        $m = new TestMessage();
769        $n = new TestMessage();
770        $this->setFields($m);
771        $n->mergeFrom($m);
772        $this->expectFields($n);
773    }
774
775    #########################################################
776    # Test message/enum without namespace.
777    #########################################################
778
779    public function testMessageWithoutNamespace()
780    {
781        $m = new TestMessage();
782        $n = new NoNamespaceMessage();
783        $m->setOptionalNoNamespaceMessage($n);
784        $repeatedNoNamespaceMessage = $m->getRepeatedNoNamespaceMessage();
785        $repeatedNoNamespaceMessage[] = new NoNamespaceMessage();
786        $m->setRepeatedNoNamespaceMessage($repeatedNoNamespaceMessage);
787
788        // test nested messages
789        $sub = new NoNamespaceMessage\NestedMessage();
790        $n->setNestedMessage($sub);
791
792        $this->assertTrue(true);
793    }
794
795    public function testEnumWithoutNamespace()
796    {
797        $m = new TestMessage();
798        $m->setOptionalNoNamespaceEnum(NoNamespaceEnum::VALUE_A);
799        $repeatedNoNamespaceEnum = $m->getRepeatedNoNamespaceEnum();
800        $repeatedNoNamespaceEnum[] = NoNamespaceEnum::VALUE_A;
801        $m->setRepeatedNoNamespaceEnum($repeatedNoNamespaceEnum);
802        $this->assertTrue(true);
803    }
804
805    #########################################################
806    # Test message with given namespace.
807    #########################################################
808
809    public function testNestedMessagesAndEnums()
810    {
811        $m = new TestMessage();
812        $n = new TestMessage\Sub();
813        $m->setOptionalMessage($n);
814        $m->setOptionalNestedEnum(TestMessage\NestedEnum::ZERO);
815        $this->assertSame($n, $m->getOptionalMessage());
816        $this->assertSame(TestMessage\NestedEnum::ZERO, $m->getOptionalNestedEnum());
817    }
818
819    public function testMessagesAndEnumsWithPrefix()
820    {
821        // Test message prefix
822        $m = new TestIncludePrefixMessage();
823        $n = new PrefixTestPrefix();
824        $n->setA(1);
825        $m->setPrefixMessage($n);
826        $this->assertSame(1, $m->getPrefixMessage()->getA());
827
828        // Test nested message prefix
829        $o = new PrefixTestPrefix();
830        $p = new PrefixTestPrefix\PrefixNestedMessage();
831        $o->setNestedMessage($p);
832        $o->setNestedEnum(PrefixTestPrefix\PrefixNestedEnum::ZERO);
833        $this->assertSame($p, $o->getNestedMessage());
834        $this->assertSame(PrefixTestPrefix\PrefixNestedEnum::ZERO, $o->getNestedEnum());
835    }
836
837    public function testMessagesAndEnumsWithPhpNamespace()
838    {
839        $m = new TestNamespace();
840        $n = new TestNamespace\NestedMessage();
841        $m->setNestedMessage($n);
842        $m->setNestedEnum(TestNamespace\NestedEnum::ZERO);
843        $this->assertSame($n, $m->getNestedMessage());
844        $this->assertSame(TestNamespace\NestedEnum::ZERO, $m->getNestedEnum());
845    }
846
847    public function testMesssagesAndEnumsWithEmptyPhpNamespace()
848    {
849        $m = new TestEmptyNamespace();
850        $n = new TestEmptyNamespace\NestedMessage();
851        $m->setNestedMessage($n);
852        $m->setNestedEnum(TestEmptyNamespace\NestedEnum::ZERO);
853        $this->assertSame($n, $m->getNestedMessage());
854        $this->assertSame(TestEmptyNamespace\NestedEnum::ZERO, $m->getNestedEnum());
855    }
856
857    public function testMessagesAndEnumsWithNoNamespace()
858    {
859        $m = new NoNamespaceMessage();
860        $n = new NoNamespaceMessage\NestedMessage();
861        $m->setNestedMessage($n);
862        $m->setNestedEnum(NoNamespaceMessage\NestedEnum::ZERO);
863        $this->assertSame($n, $m->getNestedMessage());
864        $this->assertSame(NoNamespaceMessage\NestedEnum::ZERO, $m->getNestedEnum());
865    }
866
867    public function testReservedWordsInPackageName()
868    {
869        $m = new TestEmptyPackage();
870        $n = new TestEmptyPackage\NestedMessage();
871        $m->setNestedMessage($n);
872        $m->setNestedEnum(TestEmptyPackage\NestedEnum::ZERO);
873        $this->assertSame($n, $m->getNestedMessage());
874        $this->assertSame(TestEmptyPackage\NestedEnum::ZERO, $m->getNestedEnum());
875    }
876
877    public function testReservedWordsInNamespace()
878    {
879        $m = new TestNamespace();
880        $n = new TestNamespace\PBEmpty();
881        $o = new TestNamespace\PBEmpty\NestedMessage();
882        $n->setNestedMessage($o);
883        $n->setNestedEnum(TestNamespace\PBEmpty\NestedEnum::ZERO);
884        $m->setReservedName($n);
885        $this->assertSame($n, $m->getReservedName());
886        $this->assertSame($o, $n->getNestedMessage());
887        $this->assertSame(
888            TestNamespace\PBEmpty\NestedEnum::ZERO,
889            $n->getNestedEnum()
890        );
891    }
892
893    #########################################################
894    # Test prefix for reserved words.
895    #########################################################
896
897    public function testPrefixForReservedWords()
898    {
899        $m = new \Foo\TestMessage\PBEmpty();
900        $m = new \Foo\PBEmpty();
901        $m = new \PrefixEmpty();
902        $m = new \Foo\PBARRAY();
903
904        $m = new \Lower\PBabstract();
905        $m = new \Lower\PBand();
906        $m = new \Lower\PBarray();
907        $m = new \Lower\PBas();
908        $m = new \Lower\PBbreak();
909        $m = new \Lower\PBcallable();
910        $m = new \Lower\PBcase();
911        $m = new \Lower\PBcatch();
912        $m = new \Lower\PBclass();
913        $m = new \Lower\PBclone();
914        $m = new \Lower\PBconst();
915        $m = new \Lower\PBcontinue();
916        $m = new \Lower\PBdeclare();
917        $m = new \Lower\PBdefault();
918        $m = new \Lower\PBdie();
919        $m = new \Lower\PBdo();
920        $m = new \Lower\PBecho();
921        $m = new \Lower\PBelse();
922        $m = new \Lower\PBelseif();
923        $m = new \Lower\PBempty();
924        $m = new \Lower\PBenddeclare();
925        $m = new \Lower\PBendfor();
926        $m = new \Lower\PBendforeach();
927        $m = new \Lower\PBendif();
928        $m = new \Lower\PBendswitch();
929        $m = new \Lower\PBendwhile();
930        $m = new \Lower\PBeval();
931        $m = new \Lower\PBexit();
932        $m = new \Lower\PBextends();
933        $m = new \Lower\PBfinal();
934        $m = new \Lower\PBfinally();
935        $m = new \Lower\PBfn();
936        $m = new \Lower\PBfor();
937        $m = new \Lower\PBforeach();
938        $m = new \Lower\PBfunction();
939        $m = new \Lower\PBglobal();
940        $m = new \Lower\PBgoto();
941        $m = new \Lower\PBif();
942        $m = new \Lower\PBimplements();
943        $m = new \Lower\PBinclude();
944        $m = new \Lower\PBinclude_once();
945        $m = new \Lower\PBinstanceof();
946        $m = new \Lower\PBinsteadof();
947        $m = new \Lower\PBinterface();
948        $m = new \Lower\PBisset();
949        $m = new \Lower\PBlist();
950        $m = new \Lower\PBmatch();
951        $m = new \Lower\PBnamespace();
952        $m = new \Lower\PBnew();
953        $m = new \Lower\PBor();
954        $m = new \Lower\PBparent();
955        $m = new \Lower\PBprint();
956        $m = new \Lower\PBprivate();
957        $m = new \Lower\PBprotected();
958        $m = new \Lower\PBpublic();
959        $m = new \Lower\PBreadonly();
960        $m = new \Lower\PBrequire();
961        $m = new \Lower\PBrequire_once();
962        $m = new \Lower\PBreturn();
963        $m = new \Lower\PBself();
964        $m = new \Lower\PBstatic();
965        $m = new \Lower\PBswitch();
966        $m = new \Lower\PBthrow();
967        $m = new \Lower\PBtrait();
968        $m = new \Lower\PBtry();
969        $m = new \Lower\PBunset();
970        $m = new \Lower\PBuse();
971        $m = new \Lower\PBvar();
972        $m = new \Lower\PBwhile();
973        $m = new \Lower\PBxor();
974        $m = new \Lower\PByield();
975        $m = new \Lower\PBint();
976        $m = new \Lower\PBfloat();
977        $m = new \Lower\PBbool();
978        $m = new \Lower\PBstring();
979        $m = new \Lower\PBtrue();
980        $m = new \Lower\PBfalse();
981        $m = new \Lower\PBnull();
982        $m = new \Lower\PBvoid();
983        $m = new \Lower\PBiterable();
984
985        $m = new \Upper\PBABSTRACT();
986        $m = new \Upper\PBAND();
987        $m = new \Upper\PBARRAY();
988        $m = new \Upper\PBAS();
989        $m = new \Upper\PBBREAK();
990        $m = new \Upper\PBCALLABLE();
991        $m = new \Upper\PBCASE();
992        $m = new \Upper\PBCATCH();
993        $m = new \Upper\PBCLASS();
994        $m = new \Upper\PBCLONE();
995        $m = new \Upper\PBCONST();
996        $m = new \Upper\PBCONTINUE();
997        $m = new \Upper\PBDECLARE();
998        $m = new \Upper\PBDEFAULT();
999        $m = new \Upper\PBDIE();
1000        $m = new \Upper\PBDO();
1001        $m = new \Upper\PBECHO();
1002        $m = new \Upper\PBELSE();
1003        $m = new \Upper\PBELSEIF();
1004        $m = new \Upper\PBEMPTY();
1005        $m = new \Upper\PBENDDECLARE();
1006        $m = new \Upper\PBENDFOR();
1007        $m = new \Upper\PBENDFOREACH();
1008        $m = new \Upper\PBENDIF();
1009        $m = new \Upper\PBENDSWITCH();
1010        $m = new \Upper\PBENDWHILE();
1011        $m = new \Upper\PBEVAL();
1012        $m = new \Upper\PBEXIT();
1013        $m = new \Upper\PBEXTENDS();
1014        $m = new \Upper\PBFINAL();
1015        $m = new \Upper\PBFINALLY();
1016        $m = new \Upper\PBFN();
1017        $m = new \Upper\PBFOR();
1018        $m = new \Upper\PBFOREACH();
1019        $m = new \Upper\PBFUNCTION();
1020        $m = new \Upper\PBGLOBAL();
1021        $m = new \Upper\PBGOTO();
1022        $m = new \Upper\PBIF();
1023        $m = new \Upper\PBIMPLEMENTS();
1024        $m = new \Upper\PBINCLUDE();
1025        $m = new \Upper\PBINCLUDE_ONCE();
1026        $m = new \Upper\PBINSTANCEOF();
1027        $m = new \Upper\PBINSTEADOF();
1028        $m = new \Upper\PBINTERFACE();
1029        $m = new \Upper\PBISSET();
1030        $m = new \Upper\PBLIST();
1031        $m = new \Upper\PBMATCH();
1032        $m = new \Upper\PBNAMESPACE();
1033        $m = new \Upper\PBNEW();
1034        $m = new \Upper\PBOR();
1035        $m = new \Upper\PBPARENT();
1036        $m = new \Upper\PBPRINT();
1037        $m = new \Upper\PBPRIVATE();
1038        $m = new \Upper\PBPROTECTED();
1039        $m = new \Upper\PBPUBLIC();
1040        $m = new \Upper\PBREADONLY();
1041        $m = new \Upper\PBREQUIRE();
1042        $m = new \Upper\PBREQUIRE_ONCE();
1043        $m = new \Upper\PBRETURN();
1044        $m = new \Upper\PBSELF();
1045        $m = new \Upper\PBSTATIC();
1046        $m = new \Upper\PBSWITCH();
1047        $m = new \Upper\PBTHROW();
1048        $m = new \Upper\PBTRAIT();
1049        $m = new \Upper\PBTRY();
1050        $m = new \Upper\PBUNSET();
1051        $m = new \Upper\PBUSE();
1052        $m = new \Upper\PBVAR();
1053        $m = new \Upper\PBWHILE();
1054        $m = new \Upper\PBXOR();
1055        $m = new \Upper\PBYIELD();
1056        $m = new \Upper\PBINT();
1057        $m = new \Upper\PBFLOAT();
1058        $m = new \Upper\PBBOOL();
1059        $m = new \Upper\PBSTRING();
1060        $m = new \Upper\PBTRUE();
1061        $m = new \Upper\PBFALSE();
1062        $m = new \Upper\PBNULL();
1063        $m = new \Upper\PBVOID();
1064        $m = new \Upper\PBITERABLE();
1065
1066        $m = new \Lower_enum\PBabstract();
1067        $m = new \Lower_enum\PBand();
1068        $m = new \Lower_enum\PBarray();
1069        $m = new \Lower_enum\PBas();
1070        $m = new \Lower_enum\PBbreak();
1071        $m = new \Lower_enum\PBcallable();
1072        $m = new \Lower_enum\PBcase();
1073        $m = new \Lower_enum\PBcatch();
1074        $m = new \Lower_enum\PBclass();
1075        $m = new \Lower_enum\PBclone();
1076        $m = new \Lower_enum\PBconst();
1077        $m = new \Lower_enum\PBcontinue();
1078        $m = new \Lower_enum\PBdeclare();
1079        $m = new \Lower_enum\PBdefault();
1080        $m = new \Lower_enum\PBdie();
1081        $m = new \Lower_enum\PBdo();
1082        $m = new \Lower_enum\PBecho();
1083        $m = new \Lower_enum\PBelse();
1084        $m = new \Lower_enum\PBelseif();
1085        $m = new \Lower_enum\PBempty();
1086        $m = new \Lower_enum\PBenddeclare();
1087        $m = new \Lower_enum\PBendfor();
1088        $m = new \Lower_enum\PBendforeach();
1089        $m = new \Lower_enum\PBendif();
1090        $m = new \Lower_enum\PBendswitch();
1091        $m = new \Lower_enum\PBendwhile();
1092        $m = new \Lower_enum\PBeval();
1093        $m = new \Lower_enum\PBexit();
1094        $m = new \Lower_enum\PBextends();
1095        $m = new \Lower_enum\PBfinal();
1096        $m = new \Lower_enum\PBfinally();
1097        $m = new \Lower_enum\PBfn();
1098        $m = new \Lower_enum\PBfor();
1099        $m = new \Lower_enum\PBforeach();
1100        $m = new \Lower_enum\PBfunction();
1101        $m = new \Lower_enum\PBglobal();
1102        $m = new \Lower_enum\PBgoto();
1103        $m = new \Lower_enum\PBif();
1104        $m = new \Lower_enum\PBimplements();
1105        $m = new \Lower_enum\PBinclude();
1106        $m = new \Lower_enum\PBinclude_once();
1107        $m = new \Lower_enum\PBinstanceof();
1108        $m = new \Lower_enum\PBinsteadof();
1109        $m = new \Lower_enum\PBinterface();
1110        $m = new \Lower_enum\PBisset();
1111        $m = new \Lower_enum\PBlist();
1112        $m = new \Lower_enum\PBmatch();
1113        $m = new \Lower_enum\PBnamespace();
1114        $m = new \Lower_enum\PBnew();
1115        $m = new \Lower_enum\PBor();
1116        $m = new \Lower_enum\PBparent();
1117        $m = new \Lower_enum\PBprint();
1118        $m = new \Lower_enum\PBprivate();
1119        $m = new \Lower_enum\PBprotected();
1120        $m = new \Lower_enum\PBpublic();
1121        $m = new \Lower_enum\PBrequire();
1122        $m = new \Lower_enum\PBreadonly();
1123        $m = new \Lower_enum\PBrequire_once();
1124        $m = new \Lower_enum\PBreturn();
1125        $m = new \Lower_enum\PBself();
1126        $m = new \Lower_enum\PBstatic();
1127        $m = new \Lower_enum\PBswitch();
1128        $m = new \Lower_enum\PBthrow();
1129        $m = new \Lower_enum\PBtrait();
1130        $m = new \Lower_enum\PBtry();
1131        $m = new \Lower_enum\PBunset();
1132        $m = new \Lower_enum\PBuse();
1133        $m = new \Lower_enum\PBvar();
1134        $m = new \Lower_enum\PBwhile();
1135        $m = new \Lower_enum\PBxor();
1136        $m = new \Lower_enum\PByield();
1137        $m = new \Lower_enum\PBint();
1138        $m = new \Lower_enum\PBfloat();
1139        $m = new \Lower_enum\PBbool();
1140        $m = new \Lower_enum\PBstring();
1141        $m = new \Lower_enum\PBtrue();
1142        $m = new \Lower_enum\PBfalse();
1143        $m = new \Lower_enum\PBnull();
1144        $m = new \Lower_enum\PBvoid();
1145        $m = new \Lower_enum\PBiterable();
1146
1147        $m = new \Upper_enum\PBABSTRACT();
1148        $m = new \Upper_enum\PBAND();
1149        $m = new \Upper_enum\PBARRAY();
1150        $m = new \Upper_enum\PBAS();
1151        $m = new \Upper_enum\PBBREAK();
1152        $m = new \Upper_enum\PBCALLABLE();
1153        $m = new \Upper_enum\PBCASE();
1154        $m = new \Upper_enum\PBCATCH();
1155        $m = new \Upper_enum\PBCLASS();
1156        $m = new \Upper_enum\PBCLONE();
1157        $m = new \Upper_enum\PBCONST();
1158        $m = new \Upper_enum\PBCONTINUE();
1159        $m = new \Upper_enum\PBDECLARE();
1160        $m = new \Upper_enum\PBDEFAULT();
1161        $m = new \Upper_enum\PBDIE();
1162        $m = new \Upper_enum\PBDO();
1163        $m = new \Upper_enum\PBECHO();
1164        $m = new \Upper_enum\PBELSE();
1165        $m = new \Upper_enum\PBELSEIF();
1166        $m = new \Upper_enum\PBEMPTY();
1167        $m = new \Upper_enum\PBENDDECLARE();
1168        $m = new \Upper_enum\PBENDFOR();
1169        $m = new \Upper_enum\PBENDFOREACH();
1170        $m = new \Upper_enum\PBENDIF();
1171        $m = new \Upper_enum\PBENDSWITCH();
1172        $m = new \Upper_enum\PBENDWHILE();
1173        $m = new \Upper_enum\PBEVAL();
1174        $m = new \Upper_enum\PBEXIT();
1175        $m = new \Upper_enum\PBEXTENDS();
1176        $m = new \Upper_enum\PBFINAL();
1177        $m = new \Upper_enum\PBFINALLY();
1178        $m = new \Upper_enum\PBFN();
1179        $m = new \Upper_enum\PBFOR();
1180        $m = new \Upper_enum\PBFOREACH();
1181        $m = new \Upper_enum\PBFUNCTION();
1182        $m = new \Upper_enum\PBGLOBAL();
1183        $m = new \Upper_enum\PBGOTO();
1184        $m = new \Upper_enum\PBIF();
1185        $m = new \Upper_enum\PBIMPLEMENTS();
1186        $m = new \Upper_enum\PBINCLUDE();
1187        $m = new \Upper_enum\PBINCLUDE_ONCE();
1188        $m = new \Upper_enum\PBINSTANCEOF();
1189        $m = new \Upper_enum\PBINSTEADOF();
1190        $m = new \Upper_enum\PBINTERFACE();
1191        $m = new \Upper_enum\PBISSET();
1192        $m = new \Upper_enum\PBLIST();
1193        $m = new \Upper_enum\PBMATCH();
1194        $m = new \Upper_enum\PBNAMESPACE();
1195        $m = new \Upper_enum\PBNEW();
1196        $m = new \Upper_enum\PBOR();
1197        $m = new \Upper_enum\PBPARENT();
1198        $m = new \Upper_enum\PBPRINT();
1199        $m = new \Upper_enum\PBPRIVATE();
1200        $m = new \Upper_enum\PBPROTECTED();
1201        $m = new \Upper_enum\PBPUBLIC();
1202        $m = new \Upper_enum\PBREADONLY();
1203        $m = new \Upper_enum\PBREQUIRE();
1204        $m = new \Upper_enum\PBREQUIRE_ONCE();
1205        $m = new \Upper_enum\PBRETURN();
1206        $m = new \Upper_enum\PBSELF();
1207        $m = new \Upper_enum\PBSTATIC();
1208        $m = new \Upper_enum\PBSWITCH();
1209        $m = new \Upper_enum\PBTHROW();
1210        $m = new \Upper_enum\PBTRAIT();
1211        $m = new \Upper_enum\PBTRY();
1212        $m = new \Upper_enum\PBUNSET();
1213        $m = new \Upper_enum\PBUSE();
1214        $m = new \Upper_enum\PBVAR();
1215        $m = new \Upper_enum\PBWHILE();
1216        $m = new \Upper_enum\PBXOR();
1217        $m = new \Upper_enum\PBYIELD();
1218        $m = new \Upper_enum\PBINT();
1219        $m = new \Upper_enum\PBFLOAT();
1220        $m = new \Upper_enum\PBBOOL();
1221        $m = new \Upper_enum\PBSTRING();
1222        $m = new \Upper_enum\PBTRUE();
1223        $m = new \Upper_enum\PBFALSE();
1224        $m = new \Upper_enum\PBNULL();
1225        $m = new \Upper_enum\PBVOID();
1226        $m = new \Upper_enum\PBITERABLE();
1227
1228        $m = \Lower_enum_value\NotAllowed::PBabstract;
1229        $m = \Lower_enum_value\NotAllowed::PBand;
1230        $m = \Lower_enum_value\NotAllowed::PBarray;
1231        $m = \Lower_enum_value\NotAllowed::PBas;
1232        $m = \Lower_enum_value\NotAllowed::PBbreak;
1233        $m = \Lower_enum_value\NotAllowed::PBcallable;
1234        $m = \Lower_enum_value\NotAllowed::PBcase;
1235        $m = \Lower_enum_value\NotAllowed::PBcatch;
1236        $m = \Lower_enum_value\NotAllowed::PBclass;
1237        $m = \Lower_enum_value\NotAllowed::PBclone;
1238        $m = \Lower_enum_value\NotAllowed::PBconst;
1239        $m = \Lower_enum_value\NotAllowed::PBcontinue;
1240        $m = \Lower_enum_value\NotAllowed::PBdeclare;
1241        $m = \Lower_enum_value\NotAllowed::PBdefault;
1242        $m = \Lower_enum_value\NotAllowed::PBdie;
1243        $m = \Lower_enum_value\NotAllowed::PBdo;
1244        $m = \Lower_enum_value\NotAllowed::PBecho;
1245        $m = \Lower_enum_value\NotAllowed::PBelse;
1246        $m = \Lower_enum_value\NotAllowed::PBelseif;
1247        $m = \Lower_enum_value\NotAllowed::PBempty;
1248        $m = \Lower_enum_value\NotAllowed::PBenddeclare;
1249        $m = \Lower_enum_value\NotAllowed::PBendfor;
1250        $m = \Lower_enum_value\NotAllowed::PBendforeach;
1251        $m = \Lower_enum_value\NotAllowed::PBendif;
1252        $m = \Lower_enum_value\NotAllowed::PBendswitch;
1253        $m = \Lower_enum_value\NotAllowed::PBendwhile;
1254        $m = \Lower_enum_value\NotAllowed::PBeval;
1255        $m = \Lower_enum_value\NotAllowed::PBexit;
1256        $m = \Lower_enum_value\NotAllowed::PBextends;
1257        $m = \Lower_enum_value\NotAllowed::PBfinal;
1258        $m = \Lower_enum_value\NotAllowed::PBfinally;
1259        $m = \Lower_enum_value\NotAllowed::PBfn;
1260        $m = \Lower_enum_value\NotAllowed::PBfor;
1261        $m = \Lower_enum_value\NotAllowed::PBforeach;
1262        $m = \Lower_enum_value\NotAllowed::PBfunction;
1263        $m = \Lower_enum_value\NotAllowed::PBglobal;
1264        $m = \Lower_enum_value\NotAllowed::PBgoto;
1265        $m = \Lower_enum_value\NotAllowed::PBif;
1266        $m = \Lower_enum_value\NotAllowed::PBimplements;
1267        $m = \Lower_enum_value\NotAllowed::PBinclude;
1268        $m = \Lower_enum_value\NotAllowed::PBinclude_once;
1269        $m = \Lower_enum_value\NotAllowed::PBinstanceof;
1270        $m = \Lower_enum_value\NotAllowed::PBinsteadof;
1271        $m = \Lower_enum_value\NotAllowed::PBinterface;
1272        $m = \Lower_enum_value\NotAllowed::PBisset;
1273        $m = \Lower_enum_value\NotAllowed::PBlist;
1274        $m = \Lower_enum_value\NotAllowed::PBmatch;
1275        $m = \Lower_enum_value\NotAllowed::PBnamespace;
1276        $m = \Lower_enum_value\NotAllowed::PBnew;
1277        $m = \Lower_enum_value\NotAllowed::PBor;
1278        $m = \Lower_enum_value\NotAllowed::PBprint;
1279        $m = \Lower_enum_value\NotAllowed::PBprivate;
1280        $m = \Lower_enum_value\NotAllowed::PBprotected;
1281        $m = \Lower_enum_value\NotAllowed::PBpublic;
1282        $m = \Lower_enum_value\NotAllowed::PBrequire;
1283        $m = \Lower_enum_value\NotAllowed::PBrequire_once;
1284        $m = \Lower_enum_value\NotAllowed::PBreturn;
1285        $m = \Lower_enum_value\NotAllowed::PBstatic;
1286        $m = \Lower_enum_value\NotAllowed::PBswitch;
1287        $m = \Lower_enum_value\NotAllowed::PBthrow;
1288        $m = \Lower_enum_value\NotAllowed::PBtrait;
1289        $m = \Lower_enum_value\NotAllowed::PBtry;
1290        $m = \Lower_enum_value\NotAllowed::PBunset;
1291        $m = \Lower_enum_value\NotAllowed::PBuse;
1292        $m = \Lower_enum_value\NotAllowed::PBvar;
1293        $m = \Lower_enum_value\NotAllowed::PBwhile;
1294        $m = \Lower_enum_value\NotAllowed::PBxor;
1295        $m = \Lower_enum_value\NotAllowed::PByield;
1296        $m = \Lower_enum_value\NotAllowed::int;
1297        $m = \Lower_enum_value\NotAllowed::float;
1298        $m = \Lower_enum_value\NotAllowed::bool;
1299        $m = \Lower_enum_value\NotAllowed::string;
1300        $m = \Lower_enum_value\NotAllowed::true;
1301        $m = \Lower_enum_value\NotAllowed::false;
1302        $m = \Lower_enum_value\NotAllowed::null;
1303        $m = \Lower_enum_value\NotAllowed::void;
1304        $m = \Lower_enum_value\NotAllowed::iterable;
1305        $m = \Lower_enum_value\NotAllowed::parent;
1306        $m = \Lower_enum_value\NotAllowed::self;
1307        $m = \Lower_enum_value\NotAllowed::readonly;
1308
1309        $m = \Upper_enum_value\NotAllowed::PBABSTRACT;
1310        $m = \Upper_enum_value\NotAllowed::PBAND;
1311        $m = \Upper_enum_value\NotAllowed::PBARRAY;
1312        $m = \Upper_enum_value\NotAllowed::PBAS;
1313        $m = \Upper_enum_value\NotAllowed::PBBREAK;
1314        $m = \Upper_enum_value\NotAllowed::PBCALLABLE;
1315        $m = \Upper_enum_value\NotAllowed::PBCASE;
1316        $m = \Upper_enum_value\NotAllowed::PBCATCH;
1317        $m = \Upper_enum_value\NotAllowed::PBCLASS;
1318        $m = \Upper_enum_value\NotAllowed::PBCLONE;
1319        $m = \Upper_enum_value\NotAllowed::PBCONST;
1320        $m = \Upper_enum_value\NotAllowed::PBCONTINUE;
1321        $m = \Upper_enum_value\NotAllowed::PBDECLARE;
1322        $m = \Upper_enum_value\NotAllowed::PBDEFAULT;
1323        $m = \Upper_enum_value\NotAllowed::PBDIE;
1324        $m = \Upper_enum_value\NotAllowed::PBDO;
1325        $m = \Upper_enum_value\NotAllowed::PBECHO;
1326        $m = \Upper_enum_value\NotAllowed::PBELSE;
1327        $m = \Upper_enum_value\NotAllowed::PBELSEIF;
1328        $m = \Upper_enum_value\NotAllowed::PBEMPTY;
1329        $m = \Upper_enum_value\NotAllowed::PBENDDECLARE;
1330        $m = \Upper_enum_value\NotAllowed::PBENDFOR;
1331        $m = \Upper_enum_value\NotAllowed::PBENDFOREACH;
1332        $m = \Upper_enum_value\NotAllowed::PBENDIF;
1333        $m = \Upper_enum_value\NotAllowed::PBENDSWITCH;
1334        $m = \Upper_enum_value\NotAllowed::PBENDWHILE;
1335        $m = \Upper_enum_value\NotAllowed::PBEVAL;
1336        $m = \Upper_enum_value\NotAllowed::PBEXIT;
1337        $m = \Upper_enum_value\NotAllowed::PBEXTENDS;
1338        $m = \Upper_enum_value\NotAllowed::PBFINAL;
1339        $m = \Upper_enum_value\NotAllowed::PBFINALLY;
1340        $m = \Upper_enum_value\NotAllowed::PBFN;
1341        $m = \Upper_enum_value\NotAllowed::PBFOR;
1342        $m = \Upper_enum_value\NotAllowed::PBFOREACH;
1343        $m = \Upper_enum_value\NotAllowed::PBFUNCTION;
1344        $m = \Upper_enum_value\NotAllowed::PBGLOBAL;
1345        $m = \Upper_enum_value\NotAllowed::PBGOTO;
1346        $m = \Upper_enum_value\NotAllowed::PBIF;
1347        $m = \Upper_enum_value\NotAllowed::PBIMPLEMENTS;
1348        $m = \Upper_enum_value\NotAllowed::PBINCLUDE;
1349        $m = \Upper_enum_value\NotAllowed::PBINCLUDE_ONCE;
1350        $m = \Upper_enum_value\NotAllowed::PBINSTANCEOF;
1351        $m = \Upper_enum_value\NotAllowed::PBINSTEADOF;
1352        $m = \Upper_enum_value\NotAllowed::PBINTERFACE;
1353        $m = \Upper_enum_value\NotAllowed::PBISSET;
1354        $m = \Upper_enum_value\NotAllowed::PBLIST;
1355        $m = \Upper_enum_value\NotAllowed::PBMATCH;
1356        $m = \Upper_enum_value\NotAllowed::PBNAMESPACE;
1357        $m = \Upper_enum_value\NotAllowed::PBNEW;
1358        $m = \Upper_enum_value\NotAllowed::PBOR;
1359        $m = \Upper_enum_value\NotAllowed::PBPRINT;
1360        $m = \Upper_enum_value\NotAllowed::PBPRIVATE;
1361        $m = \Upper_enum_value\NotAllowed::PBPROTECTED;
1362        $m = \Upper_enum_value\NotAllowed::PBPUBLIC;
1363        $m = \Upper_enum_value\NotAllowed::PBREQUIRE;
1364        $m = \Upper_enum_value\NotAllowed::PBREQUIRE_ONCE;
1365        $m = \Upper_enum_value\NotAllowed::PBRETURN;
1366        $m = \Upper_enum_value\NotAllowed::PBSTATIC;
1367        $m = \Upper_enum_value\NotAllowed::PBSWITCH;
1368        $m = \Upper_enum_value\NotAllowed::PBTHROW;
1369        $m = \Upper_enum_value\NotAllowed::PBTRAIT;
1370        $m = \Upper_enum_value\NotAllowed::PBTRY;
1371        $m = \Upper_enum_value\NotAllowed::PBUNSET;
1372        $m = \Upper_enum_value\NotAllowed::PBUSE;
1373        $m = \Upper_enum_value\NotAllowed::PBVAR;
1374        $m = \Upper_enum_value\NotAllowed::PBWHILE;
1375        $m = \Upper_enum_value\NotAllowed::PBXOR;
1376        $m = \Upper_enum_value\NotAllowed::PBYIELD;
1377        $m = \Upper_enum_value\NotAllowed::INT;
1378        $m = \Upper_enum_value\NotAllowed::FLOAT;
1379        $m = \Upper_enum_value\NotAllowed::BOOL;
1380        $m = \Upper_enum_value\NotAllowed::STRING;
1381        $m = \Upper_enum_value\NotAllowed::TRUE;
1382        $m = \Upper_enum_value\NotAllowed::FALSE;
1383        $m = \Upper_enum_value\NotAllowed::NULL;
1384        $m = \Upper_enum_value\NotAllowed::VOID;
1385        $m = \Upper_enum_value\NotAllowed::ITERABLE;
1386        $m = \Upper_enum_value\NotAllowed::PARENT;
1387        $m = \Upper_enum_value\NotAllowed::SELF;
1388        $m = \Upper_enum_value\NotAllowed::READONLY;
1389
1390        $this->assertTrue(true);
1391    }
1392
1393    #########################################################
1394    # Test fluent setters.
1395    #########################################################
1396
1397    public function testFluentSetters()
1398    {
1399        $m = (new TestMessage())
1400            ->setOptionalInt32(1)
1401            ->setOptionalUInt32(2);
1402        $this->assertSame(1, $m->getOptionalInt32());
1403        $this->assertSame(2, $m->getOptionalUInt32());
1404    }
1405
1406    #########################################################
1407    # Test Reverse Field Order.
1408    #########################################################
1409
1410    public function testReverseFieldOrder()
1411    {
1412        $m = new TestReverseFieldOrder();
1413        $m->setB("abc");
1414        $this->assertSame("abc", $m->getB());
1415        $this->assertNotSame("abc", $m->getA());
1416    }
1417
1418    #########################################################
1419    # Test Reverse Field Order.
1420    #########################################################
1421
1422    public function testLowerCase()
1423    {
1424        $m = new testLowerCaseMessage();
1425        $n = testLowerCaseEnum::VALUE;
1426        $this->assertTrue(true);
1427    }
1428
1429    #########################################################
1430    # Test Array Constructor.
1431    #########################################################
1432
1433    public function testArrayConstructor()
1434    {
1435        $m = new TestMessage([
1436            'optional_int32' => -42,
1437            'optional_int64' => -43,
1438            'optional_uint32' => 42,
1439            'optional_uint64' => 43,
1440            'optional_sint32' => -44,
1441            'optional_sint64' => -45,
1442            'optional_fixed32' => 46,
1443            'optional_fixed64' => 47,
1444            'optional_sfixed32' => -46,
1445            'optional_sfixed64' => -47,
1446            'optional_float' => 1.5,
1447            'optional_double' => 1.6,
1448            'optional_bool' => true,
1449            'optional_string' => 'a',
1450            'optional_bytes' => 'bbbb',
1451            'optional_enum' => TestEnum::ONE,
1452            'optional_message' => new Sub([
1453                'a' => 33
1454            ]),
1455            'repeated_int32' => [-42, -52],
1456            'repeated_int64' => [-43, -53],
1457            'repeated_uint32' => [42, 52],
1458            'repeated_uint64' => [43, 53],
1459            'repeated_sint32' => [-44, -54],
1460            'repeated_sint64' => [-45, -55],
1461            'repeated_fixed32' => [46, 56],
1462            'repeated_fixed64' => [47, 57],
1463            'repeated_sfixed32' => [-46, -56],
1464            'repeated_sfixed64' => [-47, -57],
1465            'repeated_float' => [1.5, 2.5],
1466            'repeated_double' => [1.6, 2.6],
1467            'repeated_bool' => [true, false],
1468            'repeated_string' => ['a', 'c'],
1469            'repeated_bytes' => ['bbbb', 'dddd'],
1470            'repeated_enum' => [TestEnum::ZERO, TestEnum::ONE],
1471            'repeated_message' => [new Sub(['a' => 34]),
1472                                   new Sub(['a' => 35])],
1473            'map_int32_int32' => [-62 => -62],
1474            'map_int64_int64' => [-63 => -63],
1475            'map_uint32_uint32' => [62 => 62],
1476            'map_uint64_uint64' => [63 => 63],
1477            'map_sint32_sint32' => [-64 => -64],
1478            'map_sint64_sint64' => [-65 => -65],
1479            'map_fixed32_fixed32' => [66 => 66],
1480            'map_fixed64_fixed64' => [67 => 67],
1481            'map_sfixed32_sfixed32' => [-68 => -68],
1482            'map_sfixed64_sfixed64' => [-69 => -69],
1483            'map_int32_float' => [1 => 3.5],
1484            'map_int32_double' => [1 => 3.6],
1485            'map_bool_bool' => [true => true],
1486            'map_string_string' => ['e' => 'e'],
1487            'map_int32_bytes' => [1 => 'ffff'],
1488            'map_int32_enum' => [1 => TestEnum::ONE],
1489            'map_int32_message' => [1 => new Sub(['a' => 36])],
1490        ]);
1491
1492        TestUtil::assertTestMessage($m);
1493        $this->assertTrue(true);
1494    }
1495
1496    public function testReferenceInArrayConstructor()
1497    {
1498        $keys = [[
1499                    'optional_bool' => true,
1500                    'repeated_bool' => [true],
1501                    'map_bool_bool' => [true => true],
1502                    'optional_double' => 1.0,
1503                    'repeated_double' => [1.0],
1504                    'map_int32_double' => [1 => 1.0],
1505                    'optional_int32' => 1,
1506                    'repeated_int32' => [1],
1507                    'map_int32_int32' => [1 => 1],
1508                    'optional_string' => 'a',
1509                    'repeated_string' => ['a'],
1510                    'map_string_string' => ['a' => 'a'],
1511                    'optional_message' => ['a' => 1],
1512                    'repeated_message' => [['a' => 1]],
1513                    'map_int32_message' => [1 => ['a' => 1]],
1514                ]];
1515
1516        foreach ($keys as &$key) {
1517            foreach ($key as $id => &$value) {
1518                if ($id === 'repeated_bool') {
1519                    foreach ($value as &$element) {
1520                    }
1521                }
1522                if ($id === 'map_bool_bool') {
1523                    foreach ($value as $mapKey => &$element) {
1524                    }
1525                }
1526                if ($id === 'repeated_double') {
1527                    foreach ($value as &$element) {
1528                    }
1529                }
1530                if ($id === 'map_int32_double') {
1531                    foreach ($value as $mapKey => &$element) {
1532                    }
1533                }
1534                if ($id === 'repeated_int32') {
1535                    foreach ($value as &$element) {
1536                    }
1537                }
1538                if ($id === 'map_int32_int32') {
1539                    foreach ($value as $mapKey => &$element) {
1540                    }
1541                }
1542                if ($id === 'repeated_string') {
1543                    foreach ($value as &$element) {
1544                    }
1545                }
1546                if ($id === 'map_string_string') {
1547                    foreach ($value as $mapKey => &$element) {
1548                    }
1549                }
1550                if ($id === 'optional_message') {
1551                    $value = new Sub($value);
1552                }
1553                if ($id === 'repeated_message') {
1554                    foreach ($value as &$element) {
1555                        $element = new Sub($element);
1556                    }
1557                }
1558                if ($id === 'map_int32_message') {
1559                    foreach ($value as $mapKey => &$element) {
1560                        $element = new Sub($element);
1561                    }
1562                }
1563            }
1564            $key = new TestMessage($key);
1565        }
1566
1567        $this->assertTrue(true);
1568    }
1569
1570    public function testOneofMessageInArrayConstructor()
1571    {
1572        $m = new TestMessage([
1573            'oneof_message' => new Sub(),
1574        ]);
1575        $this->assertSame('oneof_message', $m->getMyOneof());
1576        $this->assertNotNull($m->getOneofMessage());
1577
1578        $this->assertTrue(true);
1579    }
1580
1581    public function testOneofStringInArrayConstructor()
1582    {
1583        $m = new TestMessage([
1584            'oneof_string' => 'abc',
1585        ]);
1586
1587        $this->assertTrue(true);
1588    }
1589
1590    #########################################################
1591    # Test clone.
1592    #########################################################
1593
1594    public function testClone()
1595    {
1596        $m = new TestMessage([
1597            'optional_int32' => -42,
1598            'optional_int64' => -43,
1599            'optional_message' => new Sub([
1600                'a' => 33
1601            ]),
1602            'map_int32_message' => [1 => new Sub(['a' => 36])],
1603        ]);
1604        $m2 = clone $m;
1605        $this->assertEquals($m->getOptionalInt32(), $m2->getOptionalInt32());
1606        $this->assertEquals($m->getOptionalInt64(), $m2->getOptionalInt64());
1607        $this->assertSame($m->getOptionalMessage(), $m2->getOptionalMessage());
1608        $this->assertSame($m->getMapInt32Message()[1], $m2->getMapInt32Message()[1]);
1609        $this->assertEquals($m->serializeToJsonString(), $m2->serializeToJsonString());
1610    }
1611
1612    #########################################################
1613    # Test message equals.
1614    #########################################################
1615
1616    public function testMessageEquals()
1617    {
1618        $m = new TestMessage();
1619        TestUtil::setTestMessage($m);
1620        $n = new TestMessage();
1621        TestUtil::setTestMessage($n);
1622        $this->assertEquals($m, $n);
1623    }
1624
1625    #########################################################
1626    # Test reference of value
1627    #########################################################
1628
1629    public function testValueIsReference()
1630    {
1631        // Bool element
1632        $values = [true];
1633        array_walk($values, function (&$value) {});
1634        $m = new TestMessage();
1635        $m->setOptionalBool($values[0]);
1636
1637        // Int32 element
1638        $values = [1];
1639        array_walk($values, function (&$value) {});
1640        $m = new TestMessage();
1641        $m->setOptionalInt32($values[0]);
1642
1643        // Double element
1644        $values = [1.0];
1645        array_walk($values, function (&$value) {});
1646        $m = new TestMessage();
1647        $m->setOptionalDouble($values[0]);
1648
1649        // String element
1650        $values = ['a'];
1651        array_walk($values, function (&$value) {});
1652        $m = new TestMessage();
1653        $m->setOptionalString($values[0]);
1654
1655        $this->assertTrue(true);
1656    }
1657
1658    #########################################################
1659    # Test equality
1660    #########################################################
1661
1662    public function testShallowEquality()
1663    {
1664        $m1 = new TestMessage([
1665            'optional_int32' => -42,
1666            'optional_int64' => -43,
1667            'optional_uint32' => 42,
1668            'optional_uint64' => 43,
1669            'optional_sint32' => -44,
1670            'optional_sint64' => -45,
1671            'optional_fixed32' => 46,
1672            'optional_fixed64' => 47,
1673            'optional_sfixed32' => -46,
1674            'optional_sfixed64' => -47,
1675            'optional_float' => 1.5,
1676            'optional_double' => 1.6,
1677            'optional_bool' => true,
1678            'optional_string' => 'a',
1679            'optional_bytes' => 'bbbb',
1680            'optional_enum' => TestEnum::ONE,
1681            ]);
1682        $data = $m1->serializeToString();
1683        $m2 = new TestMessage();
1684        $m2->mergeFromString($data);
1685        $this->assertTrue($m1 == $m2);
1686
1687        $m1->setOptionalInt32(1234);
1688        $this->assertTrue($m1 != $m2);
1689    }
1690
1691    public function testDeepEquality()
1692    {
1693        $m1 = new TestMessage([
1694            'optional_int32' => -42,
1695            'optional_int64' => -43,
1696            'optional_uint32' => 42,
1697            'optional_uint64' => 43,
1698            'optional_sint32' => -44,
1699            'optional_sint64' => -45,
1700            'optional_fixed32' => 46,
1701            'optional_fixed64' => 47,
1702            'optional_sfixed32' => -46,
1703            'optional_sfixed64' => -47,
1704            'optional_float' => 1.5,
1705            'optional_double' => 1.6,
1706            'optional_bool' => true,
1707            'optional_string' => 'a',
1708            'optional_bytes' => 'bbbb',
1709            'optional_enum' => TestEnum::ONE,
1710            'optional_message' => new Sub([
1711                'a' => 33
1712            ]),
1713            'repeated_int32' => [-42, -52],
1714            'repeated_int64' => [-43, -53],
1715            'repeated_uint32' => [42, 52],
1716            'repeated_uint64' => [43, 53],
1717            'repeated_sint32' => [-44, -54],
1718            'repeated_sint64' => [-45, -55],
1719            'repeated_fixed32' => [46, 56],
1720            'repeated_fixed64' => [47, 57],
1721            'repeated_sfixed32' => [-46, -56],
1722            'repeated_sfixed64' => [-47, -57],
1723            'repeated_float' => [1.5, 2.5],
1724            'repeated_double' => [1.6, 2.6],
1725            'repeated_bool' => [true, false],
1726            'repeated_string' => ['a', 'c'],
1727            'repeated_bytes' => ['bbbb', 'dddd'],
1728            'repeated_enum' => [TestEnum::ZERO, TestEnum::ONE],
1729            'repeated_message' => [new Sub(['a' => 34]),
1730                                   new Sub(['a' => 35])],
1731            'map_int32_int32' => [-62 => -62],
1732            'map_int64_int64' => [-63 => -63],
1733            'map_uint32_uint32' => [62 => 62],
1734            'map_uint64_uint64' => [63 => 63],
1735            'map_sint32_sint32' => [-64 => -64],
1736            'map_sint64_sint64' => [-65 => -65],
1737            'map_fixed32_fixed32' => [66 => 66],
1738            'map_fixed64_fixed64' => [67 => 67],
1739            'map_sfixed32_sfixed32' => [-68 => -68],
1740            'map_sfixed64_sfixed64' => [-69 => -69],
1741            'map_int32_float' => [1 => 3.5],
1742            'map_int32_double' => [1 => 3.6],
1743            'map_bool_bool' => [true => true],
1744            'map_string_string' => ['e' => 'e'],
1745            'map_int32_bytes' => [1 => 'ffff'],
1746            'map_int32_enum' => [1 => TestEnum::ONE],
1747            'map_int32_message' => [1 => new Sub(['a' => 36])],
1748        ]);
1749        $data = $m1->serializeToString();
1750
1751        $m2 = new TestMessage();
1752        $m2->mergeFromString($data);
1753        $this->assertTrue($m1 == $m2);
1754
1755        # Nested sub-message is checked.
1756        $m2 = new TestMessage();
1757        $m2->mergeFromString($data);
1758        $m2->getOptionalMessage()->setA(1234);
1759        $this->assertTrue($m1 != $m2);
1760
1761        # Repeated field element is checked.
1762        $m2 = new TestMessage();
1763        $m2->mergeFromString($data);
1764        $m2->getRepeatedInt32()[0] = 1234;
1765        $this->assertTrue($m1 != $m2);
1766
1767        # Repeated field length is checked.
1768        $m2 = new TestMessage();
1769        $m2->mergeFromString($data);
1770        $m2->getRepeatedInt32()[] = 1234;
1771        $this->assertTrue($m1 != $m2);
1772
1773        # SubMessage inside repeated field is checked.
1774        $m2 = new TestMessage();
1775        $m2->mergeFromString($data);
1776        $m2->getRepeatedMessage()[0]->setA(1234);
1777        $this->assertTrue($m1 != $m2);
1778
1779        # Map value is checked.
1780        $m2 = new TestMessage();
1781        $m2->mergeFromString($data);
1782        $m2->getMapInt32Int32()[-62] = 1234;
1783        $this->assertTrue($m1 != $m2);
1784
1785        # Map size is checked.
1786        $m2 = new TestMessage();
1787        $m2->mergeFromString($data);
1788        $m2->getMapInt32Int32()[1234] = 1234;
1789        $this->assertTrue($m1 != $m2);
1790
1791        # SubMessage inside map field is checked.
1792        $m2 = new TestMessage();
1793        $m2->mergeFromString($data);
1794        $m2->getMapInt32Message()[1]->setA(1234);
1795        $this->assertTrue($m1 != $m2);
1796
1797        # TODO: what about unknown fields?
1798    }
1799
1800    #########################################################
1801    # Test hasOneof<Field> methods exists and working
1802    #########################################################
1803
1804    public function testHasOneof() {
1805        $m = new TestMessage();
1806        $this->assertFalse($m->hasOneofInt32());
1807        $m->setOneofInt32(42);
1808        $this->assertTrue($m->hasOneofInt32());
1809        $m->setOneofString("bar");
1810        $this->assertFalse($m->hasOneofInt32());
1811        $this->assertTrue($m->hasOneofString());
1812        $m->clear();
1813        $this->assertFalse($m->hasOneofInt32());
1814        $this->assertFalse($m->hasOneofString());
1815
1816        $sub_m = new Sub();
1817        $sub_m->setA(1);
1818        $m->setOneofMessage($sub_m);
1819        $this->assertTrue($m->hasOneofMessage());
1820        $m->setOneofMessage(null);
1821        $this->assertFalse($m->hasOneofMessage());
1822    }
1823
1824    #########################################################
1825    # Test that we don't crash if users create their own messages.
1826    #########################################################
1827
1828    public function testUserDefinedClass() {
1829        if (getenv("USE_ZEND_ALLOC") === "0") {
1830            // We're running a memory test. This test appears to leak in a way
1831            // we cannot control, PHP bug?
1832            //
1833            // TODO: investigate further.
1834            $this->markTestSkipped();
1835            return;
1836        }
1837
1838        # This is not allowed, but at least we shouldn't crash.
1839        $this->expectException(Exception::class);
1840        new C();
1841    }
1842
1843    #########################################################
1844    # Test no segfault when error happens
1845    #########################################################
1846
1847    function throwIntendedException()
1848    {
1849        throw new Exception('Intended');
1850    }
1851    public function testNoSegfaultWithError()
1852    {
1853        if (getenv("USE_ZEND_ALLOC") === "0") {
1854            // We're running a memory test. This test appears to leak in a way
1855            // we cannot control, PHP bug?
1856            //
1857            // TODO: investigate further.
1858            $this->markTestSkipped();
1859            return;
1860        }
1861        $this->expectException(Exception::class);
1862
1863        new TestMessage(['optional_int32' => $this->throwIntendedException()]);
1864    }
1865
1866    public function testNoExceptionWithVarDump()
1867    {
1868        $m = new Sub(['a' => 1]);
1869        /*
1870         * This line currently segfaults on macOS with:
1871         *
1872         *    frame #0: 0x00000001029936cc xdebug.so`xdebug_zend_hash_is_recursive + 4
1873         *    frame #1: 0x00000001029a6736 xdebug.so`xdebug_var_export_text_ansi + 1006
1874         *    frame #2: 0x00000001029a715d xdebug.so`xdebug_get_zval_value_text_ansi + 273
1875         *    frame #3: 0x000000010298a441 xdebug.so`zif_xdebug_var_dump + 297
1876         *    frame #4: 0x000000010298d558 xdebug.so`xdebug_execute_internal + 640
1877         *    frame #5: 0x000000010046d47f php`ZEND_DO_FCALL_SPEC_RETVAL_UNUSED_HANDLER + 364
1878         *    frame #6: 0x000000010043cabc php`execute_ex + 44
1879         *    frame #7: 0x000000010298d151 xdebug.so`xdebug_execute_ex + 1662
1880         *    frame #8: 0x000000010046d865 php`ZEND_DO_FCALL_SPEC_RETVAL_USED_HANDLER + 426
1881         *
1882         * The value we are passing to var_dump() appears to be corrupt somehow.
1883         */
1884        /* var_dump($m); */
1885
1886        $this->assertTrue(true);
1887    }
1888
1889    public function testIssue9440()
1890    {
1891        $m = new Test32Fields();
1892        $m->setId(8);
1893        $this->assertEquals(8, $m->getId());
1894        $m->setVersion('1');
1895        $this->assertEquals(8, $m->getId());
1896    }
1897}
1898