GeneratedMessageTest.cs 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391
  1. // Protocol Buffers - Google's data interchange format
  2. // Copyright 2008 Google Inc. All rights reserved.
  3. // http://github.com/jskeet/dotnet-protobufs/
  4. // Original C++/Java/Python code:
  5. // http://code.google.com/p/protobuf/
  6. //
  7. // Redistribution and use in source and binary forms, with or without
  8. // modification, are permitted provided that the following conditions are
  9. // met:
  10. //
  11. // * Redistributions of source code must retain the above copyright
  12. // notice, this list of conditions and the following disclaimer.
  13. // * Redistributions in binary form must reproduce the above
  14. // copyright notice, this list of conditions and the following disclaimer
  15. // in the documentation and/or other materials provided with the
  16. // distribution.
  17. // * Neither the name of Google Inc. nor the names of its
  18. // contributors may be used to endorse or promote products derived from
  19. // this software without specific prior written permission.
  20. //
  21. // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  22. // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  23. // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  24. // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
  25. // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
  26. // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
  27. // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  28. // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  29. // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  30. // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  31. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  32. using System;
  33. using System.Collections.Generic;
  34. using Google.ProtocolBuffers.Descriptors;
  35. using Google.ProtocolBuffers.TestProtos;
  36. using NUnit.Framework;
  37. namespace Google.ProtocolBuffers {
  38. [TestFixture]
  39. public class GeneratedMessageTest {
  40. ReflectionTester reflectionTester;
  41. ReflectionTester extensionsReflectionTester;
  42. [SetUp]
  43. public void SetUp() {
  44. reflectionTester = ReflectionTester.CreateTestAllTypesInstance();
  45. extensionsReflectionTester = ReflectionTester.CreateTestAllExtensionsInstance();
  46. }
  47. [Test]
  48. public void RepeatedAddPrimitiveBeforeBuild() {
  49. TestAllTypes message = new TestAllTypes.Builder { RepeatedInt32List = { 1, 2, 3 } }.Build();
  50. TestUtil.AssertEqual(new int[]{1, 2, 3}, message.RepeatedInt32List);
  51. }
  52. [Test]
  53. public void AddPrimitiveFailsAfterBuild() {
  54. TestAllTypes.Builder builder = new TestAllTypes.Builder();
  55. IList<int> list = builder.RepeatedInt32List;
  56. list.Add(1); // Fine
  57. builder.Build();
  58. try {
  59. list.Add(2);
  60. Assert.Fail("List should be frozen");
  61. } catch (NotSupportedException) {
  62. // Expected
  63. }
  64. }
  65. [Test]
  66. public void RepeatedAddMessageBeforeBuild() {
  67. TestAllTypes message = new TestAllTypes.Builder {
  68. RepeatedNestedMessageList = { new TestAllTypes.Types.NestedMessage.Builder { Bb = 10 }.Build() } }.Build();
  69. Assert.AreEqual(1, message.RepeatedNestedMessageCount);
  70. Assert.AreEqual(10, message.RepeatedNestedMessageList[0].Bb);
  71. }
  72. [Test]
  73. public void AddMessageFailsAfterBuild() {
  74. TestAllTypes.Builder builder = new TestAllTypes.Builder();
  75. IList<TestAllTypes.Types.NestedMessage> list = builder.RepeatedNestedMessageList;
  76. builder.Build();
  77. try {
  78. list.Add(new TestAllTypes.Types.NestedMessage.Builder { Bb = 10 }.Build());
  79. Assert.Fail("List should be frozen");
  80. } catch (NotSupportedException) {
  81. // Expected
  82. }
  83. }
  84. [Test]
  85. public void DefaultInstance() {
  86. Assert.AreSame(TestAllTypes.DefaultInstance, TestAllTypes.DefaultInstance.DefaultInstanceForType);
  87. Assert.AreSame(TestAllTypes.DefaultInstance, TestAllTypes.CreateBuilder().DefaultInstanceForType);
  88. }
  89. [Test]
  90. public void Accessors() {
  91. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  92. TestUtil.SetAllFields(builder);
  93. TestAllTypes message = builder.Build();
  94. TestUtil.AssertAllFieldsSet(message);
  95. }
  96. [Test]
  97. public void SettersRejectNull() {
  98. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  99. TestUtil.AssertArgumentNullException(() => builder.SetOptionalString(null));
  100. TestUtil.AssertArgumentNullException(() => builder.SetOptionalBytes(null));
  101. TestUtil.AssertArgumentNullException(() => builder.SetOptionalNestedMessage((TestAllTypes.Types.NestedMessage)null));
  102. TestUtil.AssertArgumentNullException(() => builder.SetOptionalNestedMessage((TestAllTypes.Types.NestedMessage.Builder)null));
  103. TestUtil.AssertArgumentNullException(() => builder.AddRepeatedString(null));
  104. TestUtil.AssertArgumentNullException(() => builder.AddRepeatedBytes(null));
  105. TestUtil.AssertArgumentNullException(() => builder.AddRepeatedNestedMessage((TestAllTypes.Types.NestedMessage)null));
  106. TestUtil.AssertArgumentNullException(() => builder.AddRepeatedNestedMessage((TestAllTypes.Types.NestedMessage.Builder)null));
  107. }
  108. [Test]
  109. public void RepeatedSetters() {
  110. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  111. TestUtil.SetAllFields(builder);
  112. TestUtil.ModifyRepeatedFields(builder);
  113. TestAllTypes message = builder.Build();
  114. TestUtil.AssertRepeatedFieldsModified(message);
  115. }
  116. [Test]
  117. public void RepeatedAppend() {
  118. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  119. builder.AddRangeRepeatedInt32(new int[]{1, 2, 3, 4});
  120. builder.AddRangeRepeatedForeignEnum((new ForeignEnum[] { ForeignEnum.FOREIGN_BAZ }));
  121. ForeignMessage foreignMessage = ForeignMessage.CreateBuilder().SetC(12).Build();
  122. builder.AddRangeRepeatedForeignMessage(new ForeignMessage[] {foreignMessage});
  123. TestAllTypes message = builder.Build();
  124. TestUtil.AssertEqual(message.RepeatedInt32List, new int[]{1, 2, 3, 4});
  125. TestUtil.AssertEqual(message.RepeatedForeignEnumList, new ForeignEnum[] {ForeignEnum.FOREIGN_BAZ});
  126. Assert.AreEqual(1, message.RepeatedForeignMessageCount);
  127. Assert.AreEqual(12, message.GetRepeatedForeignMessage(0).C);
  128. }
  129. [Test]
  130. public void RepeatedAppendRejectsNull() {
  131. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  132. ForeignMessage foreignMessage = ForeignMessage.CreateBuilder().SetC(12).Build();
  133. TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedForeignMessage(new[] { foreignMessage, null }));
  134. TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedForeignMessage(null));
  135. TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedForeignEnum(null));
  136. TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedString(new[] { "one", null }));
  137. TestUtil.AssertArgumentNullException(() => builder.AddRangeRepeatedBytes(new[] { TestUtil.ToBytes("one"), null }));
  138. }
  139. [Test]
  140. public void SettingForeignMessageUsingBuilder() {
  141. TestAllTypes message = TestAllTypes.CreateBuilder()
  142. // Pass builder for foreign message instance.
  143. .SetOptionalForeignMessage(ForeignMessage.CreateBuilder().SetC(123))
  144. .Build();
  145. TestAllTypes expectedMessage = TestAllTypes.CreateBuilder()
  146. // Create expected version passing foreign message instance explicitly.
  147. .SetOptionalForeignMessage(ForeignMessage.CreateBuilder().SetC(123).Build())
  148. .Build();
  149. Assert.AreEqual(expectedMessage, message);
  150. }
  151. [Test]
  152. public void SettingRepeatedForeignMessageUsingBuilder() {
  153. TestAllTypes message = TestAllTypes.CreateBuilder()
  154. // Pass builder for foreign message instance.
  155. .AddRepeatedForeignMessage(ForeignMessage.CreateBuilder().SetC(456))
  156. .Build();
  157. TestAllTypes expectedMessage = TestAllTypes.CreateBuilder()
  158. // Create expected version passing foreign message instance explicitly.
  159. .AddRepeatedForeignMessage(ForeignMessage.CreateBuilder().SetC(456).Build())
  160. .Build();
  161. Assert.AreEqual(expectedMessage, message);
  162. }
  163. [Test]
  164. public void Defaults() {
  165. TestUtil.AssertClear(TestAllTypes.DefaultInstance);
  166. TestUtil.AssertClear(TestAllTypes.CreateBuilder().Build());
  167. Assert.AreEqual("\u1234", TestExtremeDefaultValues.DefaultInstance.Utf8String);
  168. }
  169. [Test]
  170. public void ReflectionGetters() {
  171. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  172. TestUtil.SetAllFields(builder);
  173. TestAllTypes message = builder.Build();
  174. reflectionTester.AssertAllFieldsSetViaReflection(message);
  175. }
  176. [Test]
  177. public void ReflectionSetters() {
  178. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  179. reflectionTester.SetAllFieldsViaReflection(builder);
  180. TestAllTypes message = builder.Build();
  181. TestUtil.AssertAllFieldsSet(message);
  182. }
  183. [Test]
  184. public void ReflectionSettersRejectNull() {
  185. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  186. reflectionTester.AssertReflectionSettersRejectNull(builder);
  187. }
  188. [Test]
  189. public void ReflectionRepeatedSetters() {
  190. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  191. reflectionTester.SetAllFieldsViaReflection(builder);
  192. reflectionTester.ModifyRepeatedFieldsViaReflection(builder);
  193. TestAllTypes message = builder.Build();
  194. TestUtil.AssertRepeatedFieldsModified(message);
  195. }
  196. [Test]
  197. public void TestReflectionRepeatedSettersRejectNull() {
  198. TestAllTypes.Builder builder = TestAllTypes.CreateBuilder();
  199. reflectionTester.AssertReflectionRepeatedSettersRejectNull(builder);
  200. }
  201. [Test]
  202. public void ReflectionDefaults() {
  203. reflectionTester.AssertClearViaReflection(TestAllTypes.DefaultInstance);
  204. reflectionTester.AssertClearViaReflection(TestAllTypes.CreateBuilder().Build());
  205. }
  206. // =================================================================
  207. // Extensions.
  208. [Test]
  209. public void ExtensionAccessors() {
  210. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  211. TestUtil.SetAllExtensions(builder);
  212. TestAllExtensions message = builder.Build();
  213. TestUtil.AssertAllExtensionsSet(message);
  214. }
  215. [Test]
  216. public void ExtensionRepeatedSetters() {
  217. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  218. TestUtil.SetAllExtensions(builder);
  219. TestUtil.ModifyRepeatedExtensions(builder);
  220. TestAllExtensions message = builder.Build();
  221. TestUtil.AssertRepeatedExtensionsModified(message);
  222. }
  223. [Test]
  224. public void ExtensionDefaults() {
  225. TestUtil.AssertExtensionsClear(TestAllExtensions.DefaultInstance);
  226. TestUtil.AssertExtensionsClear(TestAllExtensions.CreateBuilder().Build());
  227. }
  228. [Test]
  229. public void ExtensionReflectionGetters() {
  230. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  231. TestUtil.SetAllExtensions(builder);
  232. TestAllExtensions message = builder.Build();
  233. extensionsReflectionTester.AssertAllFieldsSetViaReflection(message);
  234. }
  235. [Test]
  236. public void ExtensionReflectionSetters() {
  237. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  238. extensionsReflectionTester.SetAllFieldsViaReflection(builder);
  239. TestAllExtensions message = builder.Build();
  240. TestUtil.AssertAllExtensionsSet(message);
  241. }
  242. [Test]
  243. public void ExtensionReflectionSettersRejectNull() {
  244. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  245. extensionsReflectionTester.AssertReflectionSettersRejectNull(builder);
  246. }
  247. [Test]
  248. public void ExtensionReflectionRepeatedSetters() {
  249. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  250. extensionsReflectionTester.SetAllFieldsViaReflection(builder);
  251. extensionsReflectionTester.ModifyRepeatedFieldsViaReflection(builder);
  252. TestAllExtensions message = builder.Build();
  253. TestUtil.AssertRepeatedExtensionsModified(message);
  254. }
  255. [Test]
  256. public void ExtensionReflectionRepeatedSettersRejectNull() {
  257. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  258. extensionsReflectionTester.AssertReflectionRepeatedSettersRejectNull(builder);
  259. }
  260. [Test]
  261. public void ExtensionReflectionDefaults() {
  262. extensionsReflectionTester.AssertClearViaReflection(TestAllExtensions.DefaultInstance);
  263. extensionsReflectionTester.AssertClearViaReflection(TestAllExtensions.CreateBuilder().Build());
  264. }
  265. [Test]
  266. public void ClearExtension() {
  267. // ClearExtension() is not actually used in TestUtil, so try it manually.
  268. Assert.IsFalse(TestAllExtensions.CreateBuilder()
  269. .SetExtension(UnitTestProtoFile.OptionalInt32Extension, 1)
  270. .ClearExtension(UnitTestProtoFile.OptionalInt32Extension)
  271. .HasExtension(UnitTestProtoFile.OptionalInt32Extension));
  272. Assert.AreEqual(0, TestAllExtensions.CreateBuilder()
  273. .AddExtension(UnitTestProtoFile.RepeatedInt32Extension, 1)
  274. .ClearExtension(UnitTestProtoFile.RepeatedInt32Extension)
  275. .GetExtensionCount(UnitTestProtoFile.RepeatedInt32Extension));
  276. }
  277. /* Reinstate this test in the commit where it's fixed...
  278. [Test]
  279. public void ExtensionMergeFrom() {
  280. TestAllExtensions original = TestAllExtensions.CreateBuilder()
  281. .SetExtension(UnitTestProtoFile.OptionalInt32Extension, 1).Build();
  282. TestAllExtensions merged =
  283. TestAllExtensions.CreateBuilder().MergeFrom(original).Build();
  284. Assert.IsTrue((merged.HasExtension(UnitTestProtoFile.OptionalInt32Extension)));
  285. Assert.AreEqual(1, (int)merged.GetExtension(UnitTestProtoFile.OptionalInt32Extension));
  286. }
  287. */
  288. /* Removed multiple files option for the moment
  289. [Test]
  290. public void MultipleFilesOption() {
  291. // We mostly just want to check that things compile.
  292. MessageWithNoOuter message = MessageWithNoOuter.CreateBuilder()
  293. .SetNested(MessageWithNoOuter.Types.NestedMessage.CreateBuilder().SetI(1))
  294. .AddForeign(TestAllTypes.CreateBuilder().SetOptionalInt32(1))
  295. .SetNestedEnum(MessageWithNoOuter.Types.NestedEnum.BAZ)
  296. .SetForeignEnum(EnumWithNoOuter.BAR)
  297. .Build();
  298. Assert.AreEqual(message, MessageWithNoOuter.ParseFrom(message.ToByteString()));
  299. Assert.AreEqual(MultiFileProto.Descriptor, MessageWithNoOuter.Descriptor.File);
  300. FieldDescriptor field = MessageWithNoOuter.Descriptor.FindDescriptor<FieldDescriptor>("foreign_enum");
  301. Assert.AreEqual(MultiFileProto.Descriptor.FindTypeByName<EnumDescriptor>("EnumWithNoOuter")
  302. .FindValueByNumber((int)EnumWithNoOuter.BAR), message[field]);
  303. Assert.AreEqual(MultiFileProto.Descriptor, ServiceWithNoOuter.Descriptor.File);
  304. Assert.IsFalse(TestAllExtensions.DefaultInstance.HasExtension(MultiFileProto.ExtensionWithOuter));
  305. }*/
  306. [Test]
  307. public void OptionalFieldWithRequiredSubfieldsOptimizedForSize() {
  308. TestOptionalOptimizedForSize message = TestOptionalOptimizedForSize.DefaultInstance;
  309. Assert.IsTrue(message.IsInitialized);
  310. message = TestOptionalOptimizedForSize.CreateBuilder().SetO(
  311. TestRequiredOptimizedForSize.CreateBuilder().BuildPartial()
  312. ).BuildPartial();
  313. Assert.IsFalse(message.IsInitialized);
  314. message = TestOptionalOptimizedForSize.CreateBuilder().SetO(
  315. TestRequiredOptimizedForSize.CreateBuilder().SetX(5).BuildPartial()
  316. ).BuildPartial();
  317. Assert.IsTrue(message.IsInitialized);
  318. }
  319. [Test]
  320. public void TestOptimizedForSizeMergeUsesAllFieldsFromTarget() {
  321. TestOptimizedForSize withFieldSet = new TestOptimizedForSize.Builder { I = 10 }.Build();
  322. TestOptimizedForSize.Builder builder = new TestOptimizedForSize.Builder();
  323. builder.MergeFrom(withFieldSet);
  324. TestOptimizedForSize built = builder.Build();
  325. Assert.AreEqual(10, built.I);
  326. }
  327. [Test]
  328. public void UninitializedExtensionInOptimizedForSizeMakesMessageUninitialized() {
  329. TestOptimizedForSize.Builder builder = new TestOptimizedForSize.Builder();
  330. builder.SetExtension(TestOptimizedForSize.TestExtension2,
  331. new TestRequiredOptimizedForSize.Builder().BuildPartial());
  332. Assert.IsFalse(builder.IsInitialized);
  333. Assert.IsFalse(builder.BuildPartial().IsInitialized);
  334. builder = new TestOptimizedForSize.Builder();
  335. builder.SetExtension(TestOptimizedForSize.TestExtension2,
  336. new TestRequiredOptimizedForSize.Builder { X = 10 }.BuildPartial());
  337. Assert.IsTrue(builder.IsInitialized);
  338. Assert.IsTrue(builder.BuildPartial().IsInitialized);
  339. }
  340. }
  341. }