blob: 12224e9b32171e0ea7d1f878b3ec10534f65d48e [file] [log] [blame]
csharptest71f662c2011-05-20 15:15:34 -05001#region Copyright notice and license
2
3// Protocol Buffers - Google's data interchange format
4// Copyright 2008 Google Inc. All rights reserved.
5// http://github.com/jskeet/dotnet-protobufs/
6// Original C++/Java/Python code:
7// http://code.google.com/p/protobuf/
8//
9// Redistribution and use in source and binary forms, with or without
10// modification, are permitted provided that the following conditions are
11// met:
12//
13// * Redistributions of source code must retain the above copyright
14// notice, this list of conditions and the following disclaimer.
15// * Redistributions in binary form must reproduce the above
16// copyright notice, this list of conditions and the following disclaimer
17// in the documentation and/or other materials provided with the
18// distribution.
19// * Neither the name of Google Inc. nor the names of its
20// contributors may be used to endorse or promote products derived from
21// this software without specific prior written permission.
22//
23// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
26// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
27// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
28// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
29// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
30// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
31// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
32// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
33// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34
35#endregion
36
37using System;
38using System.Collections.Generic;
39using Google.ProtocolBuffers.Collections;
40using Google.ProtocolBuffers.TestProtos;
41using NUnit.Framework;
42
43namespace Google.ProtocolBuffers
44{
45 [TestFixture]
46 public class GeneratedMessageTest
47 {
48 private ReflectionTester reflectionTester;
49 private ReflectionTester extensionsReflectionTester;
50
51 [SetUp]
52 public void SetUp()
53 {
54 reflectionTester = ReflectionTester.CreateTestAllTypesInstance();
55 extensionsReflectionTester = ReflectionTester.CreateTestAllExtensionsInstance();
56 }
57
58 [Test]
59 public void RepeatedAddPrimitiveBeforeBuild()
60 {
61 TestAllTypes message = new TestAllTypes.Builder {RepeatedInt32List = {1, 2, 3}}.Build();
62 TestUtil.AssertEqual(new int[] {1, 2, 3}, message.RepeatedInt32List);
63 }
64
65 [Test]
66 public void AddPrimitiveFailsAfterBuild()
67 {
68 TestAllTypes.Builder builder = new TestAllTypes.Builder();
69 IList<int> list = builder.RepeatedInt32List;
70 list.Add(1); // Fine
71 builder.Build();
72
73 try
74 {
75 list.Add(2);
76 Assert.Fail("List should be frozen");
77 }
78 catch (NotSupportedException)
79 {
80 // Expected
81 }
82 }
83
84 [Test]
85 public void RepeatedAddMessageBeforeBuild()
86 {
87 TestAllTypes message = new TestAllTypes.Builder
88 {
89 RepeatedNestedMessageList =
90 {new TestAllTypes.Types.NestedMessage.Builder {Bb = 10}.Build()}
91 }.Build();
92 Assert.AreEqual(1, message.RepeatedNestedMessageCount);
93 Assert.AreEqual(10, message.RepeatedNestedMessageList[0].Bb);
94 }
95
96 [Test]
97 public void AddMessageFailsAfterBuild()
98 {
99 TestAllTypes.Builder builder = new TestAllTypes.Builder();
100 IList<TestAllTypes.Types.NestedMessage> list = builder.RepeatedNestedMessageList;
101 builder.Build();
102
103 try
104 {
105 list.Add(new TestAllTypes.Types.NestedMessage.Builder {Bb = 10}.Build());
106 Assert.Fail("List should be frozen");
107 }
108 catch (NotSupportedException)
109 {
110 // Expected
111 }
112 }
113
114 [Test]
csharptest71f662c2011-05-20 15:15:34 -0500115 public void DefaultInstance()
116 {
117 Assert.AreSame(TestAllTypes.DefaultInstance, TestAllTypes.DefaultInstance.DefaultInstanceForType);
118 Assert.AreSame(TestAllTypes.DefaultInstance, TestAllTypes.CreateBuilder().DefaultInstanceForType);
119 }
120
121 [Test]
122 public void Accessors()
123 {
124 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
125 TestUtil.SetAllFields(builder);
126 TestAllTypes message = builder.Build();
127 TestUtil.AssertAllFieldsSet(message);
128 }
129
130 [Test]
131 public void SettersRejectNull()
132 {
133 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
134 TestUtil.AssertArgumentNullException(() => builder.SetOptionalString(null));
135 TestUtil.AssertArgumentNullException(() => builder.SetOptionalBytes(null));
136 TestUtil.AssertArgumentNullException(
137 () => builder.SetOptionalNestedMessage((TestAllTypes.Types.NestedMessage) null));
138 TestUtil.AssertArgumentNullException(
139 () => builder.SetOptionalNestedMessage((TestAllTypes.Types.NestedMessage.Builder) null));
140 TestUtil.AssertArgumentNullException(() => builder.AddRepeatedString(null));
141 TestUtil.AssertArgumentNullException(() => builder.AddRepeatedBytes(null));
142 TestUtil.AssertArgumentNullException(
143 () => builder.AddRepeatedNestedMessage((TestAllTypes.Types.NestedMessage) null));
144 TestUtil.AssertArgumentNullException(
145 () => builder.AddRepeatedNestedMessage((TestAllTypes.Types.NestedMessage.Builder) null));
146 }
147
148 [Test]
149 public void RepeatedSetters()
150 {
151 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
152 TestUtil.SetAllFields(builder);
153 TestUtil.ModifyRepeatedFields(builder);
154 TestAllTypes message = builder.Build();
155 TestUtil.AssertRepeatedFieldsModified(message);
156 }
157
158 [Test]
159 public void RepeatedAppend()
160 {
161 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
162
163 builder.AddRangeRepeatedInt32(new int[] {1, 2, 3, 4});
164 builder.AddRangeRepeatedForeignEnum((new ForeignEnum[] {ForeignEnum.FOREIGN_BAZ}));
165
166 ForeignMessage foreignMessage = ForeignMessage.CreateBuilder().SetC(12).Build();
167 builder.AddRangeRepeatedForeignMessage(new ForeignMessage[] {foreignMessage});
168
169 TestAllTypes message = builder.Build();
170 TestUtil.AssertEqual(message.RepeatedInt32List, new int[] {1, 2, 3, 4});
171 TestUtil.AssertEqual(message.RepeatedForeignEnumList, new ForeignEnum[] {ForeignEnum.FOREIGN_BAZ});
172 Assert.AreEqual(1, message.RepeatedForeignMessageCount);
173 Assert.AreEqual(12, message.GetRepeatedForeignMessage(0).C);
174 }
175
176 [Test]
177 public void RepeatedAppendRejectsNull()
178 {
179 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
180
181 ForeignMessage foreignMessage = ForeignMessage.CreateBuilder().SetC(12).Build();
182 TestUtil.AssertArgumentNullException(
183 () => builder.AddRangeRepeatedForeignMessage(new[] {foreignMessage, null}));
184 TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedForeignMessage(null));
185 TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedForeignEnum(null));
186 TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedString(new[] {"one", null}));
187 TestUtil.AssertArgumentNullException(
188 () => builder.AddRangeRepeatedBytes(new[] {TestUtil.ToBytes("one"), null}));
189 }
190
191 [Test]
192 public void SettingForeignMessageUsingBuilder()
193 {
194 TestAllTypes message = TestAllTypes.CreateBuilder()
195 // Pass builder for foreign message instance.
196 .SetOptionalForeignMessage(ForeignMessage.CreateBuilder().SetC(123))
197 .Build();
198 TestAllTypes expectedMessage = TestAllTypes.CreateBuilder()
199 // Create expected version passing foreign message instance explicitly.
200 .SetOptionalForeignMessage(ForeignMessage.CreateBuilder().SetC(123).Build())
201 .Build();
202 Assert.AreEqual(expectedMessage, message);
203 }
204
205 [Test]
206 public void SettingRepeatedForeignMessageUsingBuilder()
207 {
208 TestAllTypes message = TestAllTypes.CreateBuilder()
209 // Pass builder for foreign message instance.
210 .AddRepeatedForeignMessage(ForeignMessage.CreateBuilder().SetC(456))
211 .Build();
212 TestAllTypes expectedMessage = TestAllTypes.CreateBuilder()
213 // Create expected version passing foreign message instance explicitly.
214 .AddRepeatedForeignMessage(ForeignMessage.CreateBuilder().SetC(456).Build())
215 .Build();
216 Assert.AreEqual(expectedMessage, message);
217 }
218
219 [Test]
220 public void SettingRepeatedValuesUsingRangeInCollectionInitializer()
221 {
222 int[] values = {1, 2, 3};
223 TestAllTypes message = new TestAllTypes.Builder
224 {
225 RepeatedSint32List = {values}
226 }.Build();
227 Assert.IsTrue(Lists.Equals(values, message.RepeatedSint32List));
228 }
229
230 [Test]
231 public void SettingRepeatedValuesUsingIndividualValuesInCollectionInitializer()
232 {
233 TestAllTypes message = new TestAllTypes.Builder
234 {
235 RepeatedSint32List = {6, 7}
236 }.Build();
237 Assert.IsTrue(Lists.Equals(new int[] {6, 7}, message.RepeatedSint32List));
238 }
239
240 [Test]
241 public void Defaults()
242 {
243 TestUtil.AssertClear(TestAllTypes.DefaultInstance);
244 TestUtil.AssertClear(TestAllTypes.CreateBuilder().Build());
245
246 Assert.AreEqual("\u1234", TestExtremeDefaultValues.DefaultInstance.Utf8String);
247 }
248
249 [Test]
250 public void ReflectionGetters()
251 {
252 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
253 TestUtil.SetAllFields(builder);
254 TestAllTypes message = builder.Build();
255 reflectionTester.AssertAllFieldsSetViaReflection(message);
256 }
257
258 [Test]
259 public void ReflectionSetters()
260 {
261 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
262 reflectionTester.SetAllFieldsViaReflection(builder);
263 TestAllTypes message = builder.Build();
264 TestUtil.AssertAllFieldsSet(message);
265 }
266
267 [Test]
268 public void ReflectionSettersRejectNull()
269 {
270 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
271 reflectionTester.AssertReflectionSettersRejectNull(builder);
272 }
273
274 [Test]
275 public void ReflectionRepeatedSetters()
276 {
277 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
278 reflectionTester.SetAllFieldsViaReflection(builder);
279 reflectionTester.ModifyRepeatedFieldsViaReflection(builder);
280 TestAllTypes message = builder.Build();
281 TestUtil.AssertRepeatedFieldsModified(message);
282 }
283
284 [Test]
285 public void TestReflectionRepeatedSettersRejectNull()
286 {
287 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
288 reflectionTester.AssertReflectionRepeatedSettersRejectNull(builder);
289 }
290
291 [Test]
292 public void ReflectionDefaults()
293 {
294 TestUtil.TestInMultipleCultures(() =>
295 {
296 reflectionTester.AssertClearViaReflection(
297 TestAllTypes.DefaultInstance);
298 reflectionTester.AssertClearViaReflection(
299 TestAllTypes.CreateBuilder().Build());
300 });
301 }
302
303 // =================================================================
304 // Extensions.
305
306 [Test]
307 public void ExtensionAccessors()
308 {
309 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
310 TestUtil.SetAllExtensions(builder);
311 TestAllExtensions message = builder.Build();
312 TestUtil.AssertAllExtensionsSet(message);
313 }
314
315 [Test]
316 public void ExtensionRepeatedSetters()
317 {
318 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
319 TestUtil.SetAllExtensions(builder);
320 TestUtil.ModifyRepeatedExtensions(builder);
321 TestAllExtensions message = builder.Build();
322 TestUtil.AssertRepeatedExtensionsModified(message);
323 }
324
325 [Test]
326 public void ExtensionDefaults()
327 {
328 TestUtil.AssertExtensionsClear(TestAllExtensions.DefaultInstance);
329 TestUtil.AssertExtensionsClear(TestAllExtensions.CreateBuilder().Build());
330 }
331
332 [Test]
333 public void ExtensionReflectionGetters()
334 {
335 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
336 TestUtil.SetAllExtensions(builder);
337 TestAllExtensions message = builder.Build();
338 extensionsReflectionTester.AssertAllFieldsSetViaReflection(message);
339 }
340
341 [Test]
342 public void ExtensionReflectionSetters()
343 {
344 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
345 extensionsReflectionTester.SetAllFieldsViaReflection(builder);
346 TestAllExtensions message = builder.Build();
347 TestUtil.AssertAllExtensionsSet(message);
348 }
349
350 [Test]
351 public void ExtensionReflectionSettersRejectNull()
352 {
353 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
354 extensionsReflectionTester.AssertReflectionSettersRejectNull(builder);
355 }
356
357 [Test]
358 public void ExtensionReflectionRepeatedSetters()
359 {
360 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
361 extensionsReflectionTester.SetAllFieldsViaReflection(builder);
362 extensionsReflectionTester.ModifyRepeatedFieldsViaReflection(builder);
363 TestAllExtensions message = builder.Build();
364 TestUtil.AssertRepeatedExtensionsModified(message);
365 }
366
367 [Test]
368 public void ExtensionReflectionRepeatedSettersRejectNull()
369 {
370 TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
371 extensionsReflectionTester.AssertReflectionRepeatedSettersRejectNull(builder);
372 }
373
374 [Test]
375 public void ExtensionReflectionDefaults()
376 {
377 TestUtil.TestInMultipleCultures(() =>
378 {
379 extensionsReflectionTester.AssertClearViaReflection(
380 TestAllExtensions.DefaultInstance);
381 extensionsReflectionTester.AssertClearViaReflection(
382 TestAllExtensions.CreateBuilder().Build());
383 });
384 }
385
386 [Test]
387 public void ClearExtension()
388 {
389 // ClearExtension() is not actually used in TestUtil, so try it manually.
390 Assert.IsFalse(TestAllExtensions.CreateBuilder()
391 .SetExtension(UnitTestProtoFile.OptionalInt32Extension, 1)
392 .ClearExtension(UnitTestProtoFile.OptionalInt32Extension)
393 .HasExtension(UnitTestProtoFile.OptionalInt32Extension));
394 Assert.AreEqual(0, TestAllExtensions.CreateBuilder()
395 .AddExtension(UnitTestProtoFile.RepeatedInt32Extension, 1)
396 .ClearExtension(UnitTestProtoFile.RepeatedInt32Extension)
397 .GetExtensionCount(UnitTestProtoFile.RepeatedInt32Extension));
398 }
399
400 [Test]
401 public void ExtensionMergeFrom()
402 {
403 TestAllExtensions original = TestAllExtensions.CreateBuilder()
404 .SetExtension(UnitTestProtoFile.OptionalInt32Extension, 1).Build();
405 TestAllExtensions merged =
406 TestAllExtensions.CreateBuilder().MergeFrom(original).Build();
407 Assert.IsTrue((merged.HasExtension(UnitTestProtoFile.OptionalInt32Extension)));
408 Assert.AreEqual(1, (int) merged.GetExtension(UnitTestProtoFile.OptionalInt32Extension));
409 }
410
411 /* Removed multiple files option for the moment
412 [Test]
413 public void MultipleFilesOption() {
414 // We mostly just want to check that things compile.
415 MessageWithNoOuter message = MessageWithNoOuter.CreateBuilder()
416 .SetNested(MessageWithNoOuter.Types.NestedMessage.CreateBuilder().SetI(1))
417 .AddForeign(TestAllTypes.CreateBuilder().SetOptionalInt32(1))
418 .SetNestedEnum(MessageWithNoOuter.Types.NestedEnum.BAZ)
419 .SetForeignEnum(EnumWithNoOuter.BAR)
420 .Build();
421 Assert.AreEqual(message, MessageWithNoOuter.ParseFrom(message.ToByteString()));
422
423 Assert.AreEqual(MultiFileProto.Descriptor, MessageWithNoOuter.Descriptor.File);
424
425 FieldDescriptor field = MessageWithNoOuter.Descriptor.FindDescriptor<FieldDescriptor>("foreign_enum");
426 Assert.AreEqual(MultiFileProto.Descriptor.FindTypeByName<EnumDescriptor>("EnumWithNoOuter")
427 .FindValueByNumber((int)EnumWithNoOuter.BAR), message[field]);
428
429 Assert.AreEqual(MultiFileProto.Descriptor, ServiceWithNoOuter.Descriptor.File);
430
431 Assert.IsFalse(TestAllExtensions.DefaultInstance.HasExtension(MultiFileProto.ExtensionWithOuter));
432 }*/
433
434 [Test]
435 public void OptionalFieldWithRequiredSubfieldsOptimizedForSize()
436 {
437 TestOptionalOptimizedForSize message = TestOptionalOptimizedForSize.DefaultInstance;
438 Assert.IsTrue(message.IsInitialized);
439
440 message = TestOptionalOptimizedForSize.CreateBuilder().SetO(
441 TestRequiredOptimizedForSize.CreateBuilder().BuildPartial()
442 ).BuildPartial();
443 Assert.IsFalse(message.IsInitialized);
444
445 message = TestOptionalOptimizedForSize.CreateBuilder().SetO(
446 TestRequiredOptimizedForSize.CreateBuilder().SetX(5).BuildPartial()
447 ).BuildPartial();
448 Assert.IsTrue(message.IsInitialized);
449 }
450
451 [Test]
452 public void OptimizedForSizeMergeUsesAllFieldsFromTarget()
453 {
454 TestOptimizedForSize withFieldSet = new TestOptimizedForSize.Builder {I = 10}.Build();
455 TestOptimizedForSize.Builder builder = new TestOptimizedForSize.Builder();
456 builder.MergeFrom(withFieldSet);
457 TestOptimizedForSize built = builder.Build();
458 Assert.AreEqual(10, built.I);
459 }
460
461 [Test]
462 public void UninitializedExtensionInOptimizedForSizeMakesMessageUninitialized()
463 {
464 TestOptimizedForSize.Builder builder = new TestOptimizedForSize.Builder();
465 builder.SetExtension(TestOptimizedForSize.TestExtension2,
466 new TestRequiredOptimizedForSize.Builder().BuildPartial());
467 Assert.IsFalse(builder.IsInitialized);
468 Assert.IsFalse(builder.BuildPartial().IsInitialized);
469
470 builder = new TestOptimizedForSize.Builder();
471 builder.SetExtension(TestOptimizedForSize.TestExtension2,
472 new TestRequiredOptimizedForSize.Builder {X = 10}.BuildPartial());
473 Assert.IsTrue(builder.IsInitialized);
474 Assert.IsTrue(builder.BuildPartial().IsInitialized);
475 }
476
477 [Test]
478 public void ToBuilder()
479 {
480 TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
481 TestUtil.SetAllFields(builder);
482 TestAllTypes message = builder.Build();
483 TestUtil.AssertAllFieldsSet(message.ToBuilder().Build());
484 }
485
486 [Test]
487 public void FieldConstantValues()
488 {
489 Assert.AreEqual(TestAllTypes.Types.NestedMessage.BbFieldNumber, 1);
490 Assert.AreEqual(TestAllTypes.OptionalInt32FieldNumber, 1);
491 Assert.AreEqual(TestAllTypes.OptionalGroupFieldNumber, 16);
492 Assert.AreEqual(TestAllTypes.OptionalNestedMessageFieldNumber, 18);
493 Assert.AreEqual(TestAllTypes.OptionalNestedEnumFieldNumber, 21);
494 Assert.AreEqual(TestAllTypes.RepeatedInt32FieldNumber, 31);
495 Assert.AreEqual(TestAllTypes.RepeatedGroupFieldNumber, 46);
496 Assert.AreEqual(TestAllTypes.RepeatedNestedMessageFieldNumber, 48);
497 Assert.AreEqual(TestAllTypes.RepeatedNestedEnumFieldNumber, 51);
498 }
499
500 [Test]
501 public void ExtensionConstantValues()
502 {
503 Assert.AreEqual(TestRequired.SingleFieldNumber, 1000);
504 Assert.AreEqual(TestRequired.MultiFieldNumber, 1001);
505 Assert.AreEqual(UnitTestProtoFile.OptionalInt32ExtensionFieldNumber, 1);
506 Assert.AreEqual(UnitTestProtoFile.OptionalGroupExtensionFieldNumber, 16);
507 Assert.AreEqual(UnitTestProtoFile.OptionalNestedMessageExtensionFieldNumber, 18);
508 Assert.AreEqual(UnitTestProtoFile.OptionalNestedEnumExtensionFieldNumber, 21);
509 Assert.AreEqual(UnitTestProtoFile.RepeatedInt32ExtensionFieldNumber, 31);
510 Assert.AreEqual(UnitTestProtoFile.RepeatedGroupExtensionFieldNumber, 46);
511 Assert.AreEqual(UnitTestProtoFile.RepeatedNestedMessageExtensionFieldNumber, 48);
512 Assert.AreEqual(UnitTestProtoFile.RepeatedNestedEnumExtensionFieldNumber, 51);
513 }
514
515 [Test]
516 public void EmptyPackedValue()
517 {
518 TestPackedTypes empty = new TestPackedTypes.Builder().Build();
519 Assert.AreEqual(0, empty.SerializedSize);
520 }
521 }
522}