-Fixed MetadataHandling.ReadAhead bugs

This commit is contained in:
James Newton-King
2014-07-20 12:26:00 +12:00
parent 6b5356ed51
commit 07baae515a
8 changed files with 163 additions and 6 deletions
@@ -1632,6 +1632,7 @@ namespace Newtonsoft.Json.Tests.Bson
Assert.IsFalse(reader.Read());
JsonSerializer serializer = new JsonSerializer();
serializer.MetadataPropertyHandling = MetadataPropertyHandling.Default;
ObjectTestClass b = serializer.Deserialize<ObjectTestClass>(new BsonReader(new MemoryStream(bytes)));
Assert.AreEqual(typeof(Guid), b.TheGuid.GetType());
Assert.AreEqual(g, (Guid)b.TheGuid);
@@ -1669,6 +1670,39 @@ namespace Newtonsoft.Json.Tests.Bson
CollectionAssert.AreEquivalent(g.ToByteArray(), b.TheGuid);
}
[Test]
public void GuidsShouldBeProperlyDeserialised_AsBytes_ReadAhead()
{
Guid g = new Guid("822C0CE6-CC42-4753-A3C3-26F0684A4B88");
MemoryStream ms = new MemoryStream();
BsonWriter writer = new BsonWriter(ms);
writer.WriteStartObject();
writer.WritePropertyName("TheGuid");
writer.WriteValue(g);
writer.WriteEndObject();
writer.Flush();
byte[] bytes = ms.ToArray();
BsonReader reader = new BsonReader(new MemoryStream(bytes));
Assert.IsTrue(reader.Read());
Assert.IsTrue(reader.Read());
CollectionAssert.AreEquivalent(g.ToByteArray(), reader.ReadAsBytes());
Assert.AreEqual(JsonToken.Bytes, reader.TokenType);
Assert.AreEqual(typeof(byte[]), reader.ValueType);
CollectionAssert.AreEquivalent(g.ToByteArray(), (byte[])reader.Value);
Assert.IsTrue(reader.Read());
Assert.IsFalse(reader.Read());
JsonSerializer serializer = new JsonSerializer();
serializer.MetadataPropertyHandling = MetadataPropertyHandling.ReadAhead;
BytesTestClass b = serializer.Deserialize<BytesTestClass>(new BsonReader(new MemoryStream(bytes)));
CollectionAssert.AreEquivalent(g.ToByteArray(), b.TheGuid);
}
public class BytesTestClass
{
public byte[] TheGuid { get; set; }
@@ -75,4 +75,4 @@ using System.Security;
// by using the '*' as shown below:
[assembly: AssemblyVersion("6.0.0.0")]
[assembly: AssemblyFileVersion("6.0.3.17429")]
[assembly: AssemblyFileVersion("6.0.3.17520")]
@@ -7990,7 +7990,7 @@ Parameter name: value",
}
[Test]
public void DateFormatStringWithDictionaryKey()
public void DateFormatStringWithDictionaryKey_DateTime()
{
DateTime dt = new DateTime(2000, 12, 22);
string dateFormatString = "yyyy'-pie-'MMM'-'dddd'-'dd";
@@ -8014,7 +8014,84 @@ Parameter name: value",
Assert.AreEqual(dt, d.Keys.ElementAt(0));
}
[Test]
public void DateFormatStringWithDictionaryKey_DateTime_ReadAhead()
{
DateTime dt = new DateTime(2000, 12, 22);
string dateFormatString = "yyyy'-pie-'MMM'-'dddd'-'dd";
JsonSerializerSettings settings = new JsonSerializerSettings
{
DateFormatString = dateFormatString,
MetadataPropertyHandling = MetadataPropertyHandling.ReadAhead,
Formatting = Formatting.Indented
};
string json = JsonConvert.SerializeObject(new Dictionary<DateTime, string>
{
{ dt, "123" }
}, settings);
Assert.AreEqual(@"{
""2000-pie-Dec-Friday-22"": ""123""
}", json);
Dictionary<DateTime, string> d = JsonConvert.DeserializeObject<Dictionary<DateTime, string>>(json, settings);
Assert.AreEqual(dt, d.Keys.ElementAt(0));
}
#if !NET20
[Test]
public void DateFormatStringWithDictionaryKey_DateTimeOffset()
{
DateTimeOffset dt = new DateTimeOffset(2000, 12, 22, 0, 0, 0, TimeSpan.Zero);
string dateFormatString = "yyyy'-pie-'MMM'-'dddd'-'dd'!'K";
JsonSerializerSettings settings = new JsonSerializerSettings
{
DateFormatString = dateFormatString,
Formatting = Formatting.Indented
};
string json = JsonConvert.SerializeObject(new Dictionary<DateTimeOffset, string>
{
{ dt, "123" }
}, settings);
Assert.AreEqual(@"{
""2000-pie-Dec-Friday-22!+00:00"": ""123""
}", json);
Dictionary<DateTimeOffset, string> d = JsonConvert.DeserializeObject<Dictionary<DateTimeOffset, string>>(json, settings);
Assert.AreEqual(dt, d.Keys.ElementAt(0));
}
[Test]
public void DateFormatStringWithDictionaryKey_DateTimeOffset_ReadAhead()
{
DateTimeOffset dt = new DateTimeOffset(2000, 12, 22, 0, 0, 0, TimeSpan.Zero);
string dateFormatString = "yyyy'-pie-'MMM'-'dddd'-'dd'!'K";
JsonSerializerSettings settings = new JsonSerializerSettings
{
DateFormatString = dateFormatString,
MetadataPropertyHandling = MetadataPropertyHandling.ReadAhead,
Formatting = Formatting.Indented
};
string json = JsonConvert.SerializeObject(new Dictionary<DateTimeOffset, string>
{
{ dt, "123" }
}, settings);
Assert.AreEqual(@"{
""2000-pie-Dec-Friday-22!+00:00"": ""123""
}", json);
Dictionary<DateTimeOffset, string> d = JsonConvert.DeserializeObject<Dictionary<DateTimeOffset, string>>(json, settings);
Assert.AreEqual(dt, d.Keys.ElementAt(0));
}
[Test]
public void DateFormatStringWithDateTimeOffset()
{
@@ -325,7 +325,8 @@ Newtonsoft.Json Error: 0 : Error!
o2,
new JsonSerializerSettings
{
TraceWriter = traceWriter
TraceWriter = traceWriter,
MetadataPropertyHandling = MetadataPropertyHandling.Default
});
Assert.AreEqual(2, o2.IntList.Count);
+15 -1
View File
@@ -504,7 +504,21 @@ namespace Newtonsoft.Json
if (t == JsonToken.String)
{
string s = (string)Value;
byte[] data = (s.Length == 0) ? new byte[0] : Convert.FromBase64String(s);
if (s.Length == 0)
return new byte[0];
byte[] data;
Guid g;
if (ConvertUtils.TryConvertGuid(s, out g))
{
data = g.ToByteArray();
SetToken(JsonToken.Bytes, data, false);
return data;
}
data = Convert.FromBase64String(s);
SetToken(JsonToken.Bytes, data, false);
return data;
}
@@ -91,5 +91,5 @@ using System.Security;
// by using the '*' as shown below:
[assembly: AssemblyVersion("6.0.0.0")]
[assembly: AssemblyFileVersion("6.0.3.17429")]
[assembly: AssemblyFileVersion("6.0.3.17520")]
[assembly: CLSCompliant(true)]
@@ -390,6 +390,12 @@ namespace Newtonsoft.Json.Serialization
{
JToken t = JToken.ReadFrom(reader);
tokenReader = (JTokenReader)t.CreateReader();
tokenReader.Culture = reader.Culture;
tokenReader.DateFormatString = reader.DateFormatString;
tokenReader.DateParseHandling = reader.DateParseHandling;
tokenReader.DateTimeZoneHandling = reader.DateTimeZoneHandling;
tokenReader.FloatParseHandling = reader.FloatParseHandling;
tokenReader.SupportMultipleContent = reader.SupportMultipleContent;
// start
CheckedRead(tokenReader);
@@ -841,7 +847,7 @@ To fix this error either change the JSON to a {1} or change the deserialized typ
{
if (value is string)
return Enum.Parse(contract.NonNullableUnderlyingType, value.ToString(), true);
else if (ConvertUtils.IsInteger(primitiveContract.TypeCode))
if (ConvertUtils.IsInteger(primitiveContract.TypeCode))
return Enum.ToObject(contract.NonNullableUnderlyingType, value);
}
@@ -31,6 +31,7 @@ using System.ComponentModel;
using System.Numerics;
#endif
using System.Text;
using System.Text.RegularExpressions;
using Newtonsoft.Json.Serialization;
using System.Reflection;
#if NET20
@@ -767,5 +768,29 @@ namespace Newtonsoft.Json.Utilities
return ParseResult.Success;
}
public static bool TryConvertGuid(string s, out Guid g)
{
#if NET20 || NET35
if (s == null)
throw new ArgumentNullException("s");
Regex format = new Regex(
"^[A-Fa-f0-9]{32}$|" +
"^({|\\()?[A-Fa-f0-9]{8}-([A-Fa-f0-9]{4}-){3}[A-Fa-f0-9]{12}(}|\\))?$|" +
"^({)?[0xA-Fa-f0-9]{3,10}(, {0,1}[0xA-Fa-f0-9]{3,6}){2}, {0,1}({)([0xA-Fa-f0-9]{3,4}, {0,1}){7}[0xA-Fa-f0-9]{3,4}(}})$");
Match match = format.Match(s);
if (match.Success)
{
g = new Guid(s);
return true;
}
g = Guid.Empty;
return false;
#else
return Guid.TryParse(s, out g);
#endif
}
}
}