MessageTest.cs 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Text;
  4. using Google.ProtocolBuffers.Descriptors;
  5. using Google.ProtocolBuffers.TestProtos;
  6. using NUnit.Framework;
  7. namespace Google.ProtocolBuffers {
  8. /// <summary>
  9. /// Miscellaneous tests for message operations that apply to both
  10. /// generated and dynamic messages.
  11. /// </summary>
  12. [TestFixture]
  13. public class MessageTest {
  14. // =================================================================
  15. // Message-merging tests.
  16. private static readonly TestAllTypes MergeSource = new TestAllTypes.Builder {
  17. OptionalInt32 = 1,
  18. OptionalString = "foo",
  19. OptionalForeignMessage = ForeignMessage.DefaultInstance,
  20. }.AddRepeatedString("bar").Build();
  21. private static readonly TestAllTypes MergeDest = new TestAllTypes.Builder {
  22. OptionalInt64 = 2,
  23. OptionalString = "baz",
  24. OptionalForeignMessage = new ForeignMessage.Builder { C=3 }.Build(),
  25. }.AddRepeatedString("qux").Build();
  26. private const string MergeResultText =
  27. "optional_int32: 1\n" +
  28. "optional_int64: 2\n" +
  29. "optional_string: \"foo\"\n" +
  30. "optional_foreign_message {\n" +
  31. " c: 3\n" +
  32. "}\n" +
  33. "repeated_string: \"qux\"\n" +
  34. "repeated_string: \"bar\"\n";
  35. [Test]
  36. public void MergeFrom() {
  37. TestAllTypes result = TestAllTypes.CreateBuilder(MergeDest).MergeFrom(MergeSource).Build();
  38. Assert.AreEqual(MergeResultText, result.ToString());
  39. }
  40. /// <summary>
  41. /// Test merging a DynamicMessage into a GeneratedMessage.
  42. /// As long as they have the same descriptor, this should work, but it is an
  43. /// entirely different code path.
  44. /// </summary>
  45. [Test]
  46. public void MergeFromDynamic() {
  47. TestAllTypes result = (TestAllTypes) TestAllTypes.CreateBuilder(MergeDest)
  48. .MergeFrom(DynamicMessage.CreateBuilder(MergeSource).Build())
  49. .Build();
  50. Assert.AreEqual(MergeResultText, result.ToString());
  51. }
  52. /// <summary>
  53. /// Test merging two DynamicMessages.
  54. /// </summary>
  55. [Test]
  56. public void DynamicMergeFrom() {
  57. DynamicMessage result = (DynamicMessage) DynamicMessage.CreateBuilder(MergeDest)
  58. .MergeFrom((DynamicMessage) DynamicMessage.CreateBuilder(MergeSource).Build())
  59. .Build();
  60. Assert.AreEqual(MergeResultText, result.ToString());
  61. }
  62. // =================================================================
  63. // Required-field-related tests.
  64. private static readonly TestRequired TestRequiredUninitialized = TestRequired.DefaultInstance;
  65. private static readonly TestRequired TestRequiredInitialized = new TestRequired.Builder {
  66. A = 1, B = 2, C = 3
  67. }.Build();
  68. [Test]
  69. public void Initialization() {
  70. TestRequired.Builder builder = TestRequired.CreateBuilder();
  71. Assert.IsFalse(builder.IsInitialized);
  72. builder.A = 1;
  73. Assert.IsFalse(builder.IsInitialized);
  74. builder.B = 1;
  75. Assert.IsFalse(builder.IsInitialized);
  76. builder.C = 1;
  77. Assert.IsTrue(builder.IsInitialized);
  78. }
  79. [Test]
  80. public void RequiredForeign() {
  81. TestRequiredForeign.Builder builder = TestRequiredForeign.CreateBuilder();
  82. Assert.IsTrue(builder.IsInitialized);
  83. builder.SetOptionalMessage(TestRequiredUninitialized);
  84. Assert.IsFalse(builder.IsInitialized);
  85. builder.SetOptionalMessage(TestRequiredInitialized);
  86. Assert.IsTrue(builder.IsInitialized);
  87. builder.AddRepeatedMessage(TestRequiredUninitialized);
  88. Assert.IsFalse(builder.IsInitialized);
  89. builder.SetRepeatedMessage(0, TestRequiredInitialized);
  90. Assert.IsTrue(builder.IsInitialized);
  91. }
  92. [Test]
  93. public void RequiredExtension() {
  94. TestAllExtensions.Builder builder = TestAllExtensions.CreateBuilder();
  95. Assert.IsTrue(builder.IsInitialized);
  96. builder.SetExtension(TestRequired.Types.Single, TestRequiredUninitialized);
  97. Assert.IsFalse(builder.IsInitialized);
  98. builder.SetExtension(TestRequired.Types.Single, TestRequiredInitialized);
  99. Assert.IsTrue(builder.IsInitialized);
  100. builder.AddExtension(TestRequired.Types.Multi, TestRequiredUninitialized);
  101. Assert.IsFalse(builder.IsInitialized);
  102. builder.SetExtension(TestRequired.Types.Multi, 0, TestRequiredInitialized);
  103. Assert.IsTrue(builder.IsInitialized);
  104. }
  105. [Test]
  106. public void RequiredDynamic() {
  107. MessageDescriptor descriptor = TestRequired.Descriptor;
  108. DynamicMessage.Builder builder = DynamicMessage.CreateBuilder(descriptor);
  109. Assert.IsFalse(builder.IsInitialized);
  110. builder[descriptor.FindDescriptor<FieldDescriptor>("a")] = 1;
  111. Assert.IsFalse(builder.IsInitialized);
  112. builder[descriptor.FindDescriptor<FieldDescriptor>("b")] = 1;
  113. Assert.IsFalse(builder.IsInitialized);
  114. builder[descriptor.FindDescriptor<FieldDescriptor>("c")] = 1;
  115. Assert.IsTrue(builder.IsInitialized);
  116. }
  117. [Test]
  118. public void RequiredDynamicForeign() {
  119. MessageDescriptor descriptor = TestRequiredForeign.Descriptor;
  120. DynamicMessage.Builder builder = DynamicMessage.CreateBuilder(descriptor);
  121. Assert.IsTrue(builder.IsInitialized);
  122. builder[descriptor.FindDescriptor<FieldDescriptor>("optional_message")] = TestRequiredUninitialized;
  123. Assert.IsFalse(builder.IsInitialized);
  124. builder[descriptor.FindDescriptor<FieldDescriptor>("optional_message")] = TestRequiredInitialized;
  125. Assert.IsTrue(builder.IsInitialized);
  126. builder.AddRepeatedField(descriptor.FindDescriptor<FieldDescriptor>("repeated_message"), TestRequiredUninitialized);
  127. Assert.IsFalse(builder.IsInitialized);
  128. builder.SetRepeatedField(descriptor.FindDescriptor<FieldDescriptor>("repeated_message"), 0, TestRequiredInitialized);
  129. Assert.IsTrue(builder.IsInitialized);
  130. }
  131. [Test]
  132. public void UninitializedException() {
  133. try {
  134. TestRequired.CreateBuilder().Build();
  135. Assert.Fail("Should have thrown an exception.");
  136. } catch (UninitializedMessageException e) {
  137. Assert.AreEqual("Message missing required fields: a, b, c", e.Message);
  138. }
  139. }
  140. [Test]
  141. public void BuildPartial() {
  142. // We're mostly testing that no exception is thrown.
  143. TestRequired message = TestRequired.CreateBuilder().BuildPartial();
  144. Assert.IsFalse(message.IsInitialized);
  145. }
  146. [Test]
  147. public void NestedUninitializedException() {
  148. try {
  149. TestRequiredForeign.CreateBuilder()
  150. .SetOptionalMessage(TestRequiredUninitialized)
  151. .AddRepeatedMessage(TestRequiredUninitialized)
  152. .AddRepeatedMessage(TestRequiredUninitialized)
  153. .Build();
  154. Assert.Fail("Should have thrown an exception.");
  155. } catch (UninitializedMessageException e) {
  156. Assert.AreEqual(
  157. "Message missing required fields: " +
  158. "optional_message.a, " +
  159. "optional_message.b, " +
  160. "optional_message.c, " +
  161. "repeated_message[0].a, " +
  162. "repeated_message[0].b, " +
  163. "repeated_message[0].c, " +
  164. "repeated_message[1].a, " +
  165. "repeated_message[1].b, " +
  166. "repeated_message[1].c",
  167. e.Message);
  168. }
  169. }
  170. [Test]
  171. public void BuildNestedPartial() {
  172. // We're mostly testing that no exception is thrown.
  173. TestRequiredForeign message =
  174. TestRequiredForeign.CreateBuilder()
  175. .SetOptionalMessage(TestRequiredUninitialized)
  176. .AddRepeatedMessage(TestRequiredUninitialized)
  177. .AddRepeatedMessage(TestRequiredUninitialized)
  178. .BuildPartial();
  179. Assert.IsFalse(message.IsInitialized);
  180. }
  181. [Test]
  182. public void ParseUnititialized() {
  183. try {
  184. TestRequired.ParseFrom(ByteString.Empty);
  185. Assert.Fail("Should have thrown an exception.");
  186. } catch (InvalidProtocolBufferException e) {
  187. Assert.AreEqual("Message missing required fields: a, b, c", e.Message);
  188. }
  189. }
  190. [Test]
  191. public void ParseNestedUnititialized() {
  192. ByteString data =
  193. TestRequiredForeign.CreateBuilder()
  194. .SetOptionalMessage(TestRequiredUninitialized)
  195. .AddRepeatedMessage(TestRequiredUninitialized)
  196. .AddRepeatedMessage(TestRequiredUninitialized)
  197. .BuildPartial().ToByteString();
  198. try {
  199. TestRequiredForeign.ParseFrom(data);
  200. Assert.Fail("Should have thrown an exception.");
  201. } catch (InvalidProtocolBufferException e) {
  202. Assert.AreEqual(
  203. "Message missing required fields: " +
  204. "optional_message.a, " +
  205. "optional_message.b, " +
  206. "optional_message.c, " +
  207. "repeated_message[0].a, " +
  208. "repeated_message[0].b, " +
  209. "repeated_message[0].c, " +
  210. "repeated_message[1].a, " +
  211. "repeated_message[1].b, " +
  212. "repeated_message[1].c",
  213. e.Message);
  214. }
  215. }
  216. [Test]
  217. public void DynamicUninitializedException() {
  218. try {
  219. DynamicMessage.CreateBuilder(TestRequired.Descriptor).Build();
  220. Assert.Fail("Should have thrown an exception.");
  221. } catch (UninitializedMessageException e) {
  222. Assert.AreEqual("Message missing required fields: a, b, c", e.Message);
  223. }
  224. }
  225. [Test]
  226. public void DynamicBuildPartial() {
  227. // We're mostly testing that no exception is thrown.
  228. DynamicMessage message = DynamicMessage.CreateBuilder(TestRequired.Descriptor).BuildPartial();
  229. Assert.IsFalse(message.Initialized);
  230. }
  231. [Test]
  232. public void DynamicParseUnititialized() {
  233. try {
  234. MessageDescriptor descriptor = TestRequired.Descriptor;
  235. DynamicMessage.ParseFrom(descriptor, ByteString.Empty);
  236. Assert.Fail("Should have thrown an exception.");
  237. } catch (InvalidProtocolBufferException e) {
  238. Assert.AreEqual("Message missing required fields: a, b, c", e.Message);
  239. }
  240. }
  241. }
  242. }