Skip to content

Commit a988b76

Browse files
committed
CSHARP-1351: Change ObjectSerializer to not be dependent on the order of the discriminator and value elements.
1 parent c916abb commit a988b76

File tree

2 files changed

+61
-6
lines changed

2 files changed

+61
-6
lines changed

src/MongoDB.Bson.Tests/Serialization/Serializers/ObjectSerializerTests.cs

Lines changed: 34 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* Copyright 2010-2014 MongoDB Inc.
1+
/* Copyright 2010-2015 MongoDB Inc.
22
*
33
* Licensed under the Apache License, Version 2.0 (the "License");
44
* you may not use this file except in compliance with the License.
@@ -13,6 +13,7 @@
1313
* limitations under the License.
1414
*/
1515

16+
using System;
1617
using System.Dynamic;
1718
using System.Linq;
1819
using MongoDB.Bson;
@@ -138,6 +139,20 @@ public void TestInt64()
138139
Assert.IsTrue(bson.SequenceEqual(rehydrated.ToBson()));
139140
}
140141

142+
[TestCase("{ Obj : { _v : \"01020304-0506-0708-090a-0b0c0d0e0f10\" } }")]
143+
public void TestMissingDiscriminator(string json)
144+
{
145+
var result = BsonSerializer.Deserialize<C>(json);
146+
147+
Assert.IsInstanceOf<ExpandoObject>(result.Obj);
148+
}
149+
150+
[TestCase("{ Obj : { _t : \"System.Guid\" } }")]
151+
public void TestMissingValue(string json)
152+
{
153+
Assert.Throws<FormatException>(() => BsonSerializer.Deserialize<C>(json));
154+
}
155+
141156
[Test]
142157
public void TestNull()
143158
{
@@ -164,6 +179,24 @@ public void TestObject()
164179
Assert.IsTrue(bson.SequenceEqual(rehydrated.ToBson()));
165180
}
166181

182+
[TestCase("{ Obj : { _t : \"System.Object[]\", _v : [] } }")]
183+
[TestCase("{ Obj : { _v : [], _t : \"System.Object[]\" } }")]
184+
public void TestOrderOfElementsDoesNotMatter(string json)
185+
{
186+
var result = BsonSerializer.Deserialize<C>(json);
187+
188+
Assert.IsInstanceOf<object[]>(result.Obj);
189+
}
190+
191+
[TestCase("{ Obj : { _t : \"System.Guid\", _v : \"01020304-0506-0708-090a-0b0c0d0e0f10\" } }", "01020304-0506-0708-090a-0b0c0d0e0f10")]
192+
[TestCase("{ Obj : { _v : \"01020304-0506-0708-090a-0b0c0d0e0f10\", _t : \"System.Guid\" } }", "01020304-0506-0708-090a-0b0c0d0e0f10")]
193+
public void TestOrderOfElementsDoesNotMatter(string json, string expectedGuid)
194+
{
195+
var result = BsonSerializer.Deserialize<C>(json);
196+
197+
Assert.AreEqual(Guid.Parse(expectedGuid), result.Obj);
198+
}
199+
167200
[Test]
168201
public void TestString()
169202
{

src/MongoDB.Bson/Serialization/Serializers/ObjectSerializer.cs

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/* Copyright 2010-2014 MongoDB Inc.
1+
/* Copyright 2010-2015 MongoDB Inc.
22
*
33
* Licensed under the Apache License, Version 2.0 (the "License");
44
* you may not use this file except in compliance with the License.
@@ -249,13 +249,35 @@ private object DeserializeDiscriminatedValue(BsonDeserializationContext context,
249249
}
250250
else
251251
{
252+
object value = null;
253+
var wasValuePresent = false;
254+
252255
bsonReader.ReadStartDocument();
253-
bsonReader.ReadName(_discriminatorConvention.ElementName);
254-
bsonReader.SkipValue();
255-
bsonReader.ReadName("_v");
256-
var value = serializer.Deserialize(context);
256+
while (bsonReader.ReadBsonType() != 0)
257+
{
258+
var name = bsonReader.ReadName();
259+
if (name == _discriminatorConvention.ElementName)
260+
{
261+
bsonReader.SkipValue();
262+
}
263+
else if (name == "_v")
264+
{
265+
value = serializer.Deserialize(context);
266+
wasValuePresent = true;
267+
}
268+
else
269+
{
270+
var message = string.Format("Unexpected element name: '{0}'.", name);
271+
throw new FormatException(message);
272+
}
273+
}
257274
bsonReader.ReadEndDocument();
258275

276+
if (!wasValuePresent)
277+
{
278+
throw new FormatException("_v element missing.");
279+
}
280+
259281
return value;
260282
}
261283
}

0 commit comments

Comments
 (0)