diff --git a/Src/Newtonsoft.Json.Tests/Bson/BsonReaderTests.cs b/Src/Newtonsoft.Json.Tests/Bson/BsonReaderTests.cs index 255f7785..73aa7d34 100644 --- a/Src/Newtonsoft.Json.Tests/Bson/BsonReaderTests.cs +++ b/Src/Newtonsoft.Json.Tests/Bson/BsonReaderTests.cs @@ -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(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(new BsonReader(new MemoryStream(bytes))); + CollectionAssert.AreEquivalent(g.ToByteArray(), b.TheGuid); + } + public class BytesTestClass { public byte[] TheGuid { get; set; } diff --git a/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs b/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs index 9dafc78f..02abeb2b 100644 --- a/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs +++ b/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs @@ -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")] diff --git a/Src/Newtonsoft.Json.Tests/Serialization/JsonSerializerTest.cs b/Src/Newtonsoft.Json.Tests/Serialization/JsonSerializerTest.cs index 81320c06..6015a361 100644 --- a/Src/Newtonsoft.Json.Tests/Serialization/JsonSerializerTest.cs +++ b/Src/Newtonsoft.Json.Tests/Serialization/JsonSerializerTest.cs @@ -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 + { + { dt, "123" } + }, settings); + + Assert.AreEqual(@"{ + ""2000-pie-Dec-Friday-22"": ""123"" +}", json); + + Dictionary d = JsonConvert.DeserializeObject>(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 + { + { dt, "123" } + }, settings); + + Assert.AreEqual(@"{ + ""2000-pie-Dec-Friday-22!+00:00"": ""123"" +}", json); + + Dictionary d = JsonConvert.DeserializeObject>(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 + { + { dt, "123" } + }, settings); + + Assert.AreEqual(@"{ + ""2000-pie-Dec-Friday-22!+00:00"": ""123"" +}", json); + + Dictionary d = JsonConvert.DeserializeObject>(json, settings); + + Assert.AreEqual(dt, d.Keys.ElementAt(0)); + } + [Test] public void DateFormatStringWithDateTimeOffset() { diff --git a/Src/Newtonsoft.Json.Tests/Serialization/TraceWriterTests.cs b/Src/Newtonsoft.Json.Tests/Serialization/TraceWriterTests.cs index 278c76c5..dd1e2701 100644 --- a/Src/Newtonsoft.Json.Tests/Serialization/TraceWriterTests.cs +++ b/Src/Newtonsoft.Json.Tests/Serialization/TraceWriterTests.cs @@ -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); diff --git a/Src/Newtonsoft.Json/JsonReader.cs b/Src/Newtonsoft.Json/JsonReader.cs index 1d028e0e..62a675d7 100644 --- a/Src/Newtonsoft.Json/JsonReader.cs +++ b/Src/Newtonsoft.Json/JsonReader.cs @@ -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; } diff --git a/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs b/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs index bf1a0990..ea2b6524 100644 --- a/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs +++ b/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs @@ -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)] diff --git a/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs b/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs index fc7c7f1f..d5019736 100644 --- a/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs +++ b/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs @@ -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); } diff --git a/Src/Newtonsoft.Json/Utilities/ConvertUtils.cs b/Src/Newtonsoft.Json/Utilities/ConvertUtils.cs index 3bedfc56..3fbb3849 100644 --- a/Src/Newtonsoft.Json/Utilities/ConvertUtils.cs +++ b/Src/Newtonsoft.Json/Utilities/ConvertUtils.cs @@ -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 + } } } \ No newline at end of file