diff --git a/Src/Newtonsoft.Json.Tests/Bson/BsonWriterTests.cs b/Src/Newtonsoft.Json.Tests/Bson/BsonWriterTests.cs
index edbaae08..4752121a 100644
--- a/Src/Newtonsoft.Json.Tests/Bson/BsonWriterTests.cs
+++ b/Src/Newtonsoft.Json.Tests/Bson/BsonWriterTests.cs
@@ -711,7 +711,7 @@ namespace Newtonsoft.Json.Tests.Bson
Assert.IsTrue(reader.Read());
Assert.AreEqual(JsonToken.Bytes, reader.TokenType);
- Assert.AreEqual(new byte[] { 246, 255, 255, 255, 255, 255, 255, 31, 178, 33, 203, 40, 89, 132, 196, 174, 3, 138, 68, 52, 47, 76, 78, 158, 62, 1 }, reader.Value);
+ CollectionAssert.AreEqual(new byte[] { 246, 255, 255, 255, 255, 255, 255, 31, 178, 33, 203, 40, 89, 132, 196, 174, 3, 138, 68, 52, 47, 76, 78, 158, 62, 1 }, (byte[])reader.Value);
Assert.AreEqual(i, new BigInteger((byte[])reader.Value));
Assert.IsTrue(reader.Read());
diff --git a/Src/Newtonsoft.Json.Tests/Converters/XmlNodeConverterTest.cs b/Src/Newtonsoft.Json.Tests/Converters/XmlNodeConverterTest.cs
index 610d9343..f3cc600d 100644
--- a/Src/Newtonsoft.Json.Tests/Converters/XmlNodeConverterTest.cs
+++ b/Src/Newtonsoft.Json.Tests/Converters/XmlNodeConverterTest.cs
@@ -1902,6 +1902,27 @@ namespace Newtonsoft.Json.Tests.Converters
Assert.AreEqual(@"{""root"":{""@xmlns"":""http://www.example.com/ns"",""a"":null,""bns:b"":{""@xmlns:bns"":""http://www.example.com/ns""},""c"":null}}", json2);
#endif
}
+
+#if !NET20
+ class NullableXml
+ {
+ public string Name;
+ public XElement notNull;
+ public XElement isNull;
+ }
+
+ [Test]
+ public void SerializeAndDeserializeNullableXml()
+ {
+ var xml = new NullableXml { Name = "test", notNull = XElement.Parse("test") };
+ var json = JsonConvert.SerializeObject(xml);
+
+ var w2 = JsonConvert.DeserializeObject(json);
+ Assert.AreEqual(xml.Name, w2.Name);
+ Assert.AreEqual(xml.isNull, w2.isNull);
+ Assert.AreEqual(xml.notNull.ToString(), w2.notNull.ToString());
+ }
+#endif
}
}
#endif
\ No newline at end of file
diff --git a/Src/Newtonsoft.Json.Tests/Linq/JTokenTests.cs b/Src/Newtonsoft.Json.Tests/Linq/JTokenTests.cs
index cb1fd690..64fcc7ed 100644
--- a/Src/Newtonsoft.Json.Tests/Linq/JTokenTests.cs
+++ b/Src/Newtonsoft.Json.Tests/Linq/JTokenTests.cs
@@ -368,7 +368,7 @@ namespace Newtonsoft.Json.Tests.Linq
Assert.AreEqual("9223372036854775807", (string)(new JValue(new BigInteger(long.MaxValue))));
intData = (byte[]) (new JValue(new BigInteger(long.MaxValue)));
- Assert.AreEqual(new byte[] { 255, 255, 255, 255, 255, 255, 255, 127 }, intData);
+ CollectionAssert.AreEqual(new byte[] { 255, 255, 255, 255, 255, 255, 255, 127 }, intData);
#endif
}
diff --git a/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs b/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs
index b5155b54..be053098 100644
--- a/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs
+++ b/Src/Newtonsoft.Json.Tests/Properties/AssemblyInfo.cs
@@ -75,4 +75,4 @@ using System.Security;
// You can specify all the values or you can default the Revision and Build Numbers
// by using the '*' as shown below:
[assembly: AssemblyVersion("4.5.0.0")]
-[assembly: AssemblyFileVersion("5.0.1.15916")]
+[assembly: AssemblyFileVersion("5.0.1.15917")]
diff --git a/Src/Newtonsoft.Json.sln.DotSettings b/Src/Newtonsoft.Json.sln.DotSettings
new file mode 100644
index 00000000..6a89a056
--- /dev/null
+++ b/Src/Newtonsoft.Json.sln.DotSettings
@@ -0,0 +1,5 @@
+
+ False
+ True
+ False
+
\ No newline at end of file
diff --git a/Src/Newtonsoft.Json.vssettings b/Src/Newtonsoft.Json.vssettings
new file mode 100644
index 00000000..8990c0c9
--- /dev/null
+++ b/Src/Newtonsoft.Json.vssettings
@@ -0,0 +1,13 @@
+
+
+
+
+
+ 2
+ 2
+ false
+ 2
+
+
+
+
\ No newline at end of file
diff --git a/Src/Newtonsoft.Json/Converters/XmlNodeConverter.cs b/Src/Newtonsoft.Json/Converters/XmlNodeConverter.cs
index 7d8322bc..682cbdd1 100644
--- a/Src/Newtonsoft.Json/Converters/XmlNodeConverter.cs
+++ b/Src/Newtonsoft.Json/Converters/XmlNodeConverter.cs
@@ -1082,6 +1082,9 @@ namespace Newtonsoft.Json.Converters
/// The object value.
public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
+ if (reader.TokenType == JsonToken.Null)
+ return null;
+
XmlNamespaceManager manager = new XmlNamespaceManager(new NameTable());
IXmlDocument document = null;
IXmlNode rootNode = null;
diff --git a/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs b/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs
index c601b7f3..2ce4f0e4 100644
--- a/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs
+++ b/Src/Newtonsoft.Json/Properties/AssemblyInfo.cs
@@ -90,6 +90,6 @@ using System.Security;
// You can specify all the values or you can default the Revision and Build Numbers
// by using the '*' as shown below:
[assembly: AssemblyVersion("4.5.0.0")]
-[assembly: AssemblyFileVersion("5.0.1.15916")]
+[assembly: AssemblyFileVersion("5.0.1.15917")]
[assembly: CLSCompliant(true)]
diff --git a/Src/Newtonsoft.Json/Serialization/DefaultContractResolver.cs b/Src/Newtonsoft.Json/Serialization/DefaultContractResolver.cs
index 48872a7f..864e0229 100644
--- a/Src/Newtonsoft.Json/Serialization/DefaultContractResolver.cs
+++ b/Src/Newtonsoft.Json/Serialization/DefaultContractResolver.cs
@@ -547,11 +547,11 @@ namespace Newtonsoft.Json.Serialization
private void ResolveCallbackMethods(JsonContract contract, Type t)
{
- List onSerializing;
- List onSerialized;
- List onDeserializing;
- List onDeserialized;
- List onError;
+ List onSerializing;
+ List onSerialized;
+ List onDeserializing;
+ List onDeserialized;
+ List onError;
GetCallbackMethodsForType(t, out onSerializing, out onSerialized, out onDeserializing, out onDeserialized, out onError);
@@ -559,34 +559,34 @@ namespace Newtonsoft.Json.Serialization
{
#if NETFX_CORE
if (!t.IsGenericType() || (t.GetGenericTypeDefinition() != typeof(ConcurrentDictionary<,>)))
- contract.OnSerializingMethods.AddRange(onSerializing);
+ contract.OnSerializingCallbacks.AddRange(onSerializing);
#else
- contract.OnSerializingMethods.AddRange(onSerializing);
+ contract.OnSerializingCallbacks.AddRange(onSerializing);
#endif
}
if (onSerialized != null)
- contract.OnSerializedMethods.AddRange(onSerialized);
+ contract.OnSerializedCallbacks.AddRange(onSerialized);
if (onDeserializing != null)
- contract.OnDeserializingMethods.AddRange(onDeserializing);
+ contract.OnDeserializingCallbacks.AddRange(onDeserializing);
if (onDeserialized != null)
{
// ConcurrentDictionary throws an error here so don't use its OnDeserialized - http://json.codeplex.com/discussions/257093
#if !(NET35 || NET20 || SILVERLIGHT || WINDOWS_PHONE || PORTABLE)
if (!t.IsGenericType() || (t.GetGenericTypeDefinition() != typeof(ConcurrentDictionary<,>)))
- contract.OnDeserializedMethods.AddRange(onDeserialized);
+ contract.OnDeserializedCallbacks.AddRange(onDeserialized);
#else
- contract.OnDeserializedMethods.AddRange(onDeserialized);
+ contract.OnDeserializedCallbacks.AddRange(onDeserialized);
#endif
}
if (onError != null)
- contract.OnErrorMethods.AddRange(onError);
+ contract.OnErrorCallbacks.AddRange(onError);
}
- private void GetCallbackMethodsForType(Type type, out List onSerializing, out List onSerialized, out List onDeserializing, out List onDeserialized, out List onError)
+ private void GetCallbackMethodsForType(Type type, out List onSerializing, out List onSerialized, out List onDeserializing, out List onDeserialized, out List onError)
{
onSerializing = null;
onSerialized = null;
@@ -616,32 +616,32 @@ namespace Newtonsoft.Json.Serialization
if (IsValidCallback(method, parameters, typeof(OnSerializingAttribute), currentOnSerializing, ref prevAttributeType))
{
- onSerializing = onSerializing ?? new List();
- onSerializing.Add(method);
+ onSerializing = onSerializing ?? new List();
+ onSerializing.Add(JsonContract.CreateSerializationCallback(method));
currentOnSerializing = method;
}
if (IsValidCallback(method, parameters, typeof(OnSerializedAttribute), currentOnSerialized, ref prevAttributeType))
{
- onSerialized = onSerialized ?? new List();
- onSerialized.Add(method);
+ onSerialized = onSerialized ?? new List();
+ onSerialized.Add(JsonContract.CreateSerializationCallback(method));
currentOnSerialized = method;
}
if (IsValidCallback(method, parameters, typeof(OnDeserializingAttribute), currentOnDeserializing, ref prevAttributeType))
{
- onDeserializing = onDeserializing ?? new List();
- onDeserializing.Add(method);
+ onDeserializing = onDeserializing ?? new List();
+ onDeserializing.Add(JsonContract.CreateSerializationCallback(method));
currentOnDeserializing = method;
}
if (IsValidCallback(method, parameters, typeof(OnDeserializedAttribute), currentOnDeserialized, ref prevAttributeType))
{
- onDeserialized = onDeserialized ?? new List();
- onDeserialized.Add(method);
+ onDeserialized = onDeserialized ?? new List();
+ onDeserialized.Add(JsonContract.CreateSerializationCallback(method));
currentOnDeserialized = method;
}
if (IsValidCallback(method, parameters, typeof(OnErrorAttribute), currentOnError, ref prevAttributeType))
{
- onError = onError ?? new List();
- onError.Add(method);
+ onError = onError ?? new List();
+ onError.Add(JsonContract.CreateSerializationErrorCallback(method));
currentOnError = method;
}
}
diff --git a/Src/Newtonsoft.Json/Serialization/JsonContract.cs b/Src/Newtonsoft.Json/Serialization/JsonContract.cs
index 04b97c59..e6d47030 100644
--- a/Src/Newtonsoft.Json/Serialization/JsonContract.cs
+++ b/Src/Newtonsoft.Json/Serialization/JsonContract.cs
@@ -51,6 +51,10 @@ namespace Newtonsoft.Json.Serialization
Linq
}
+ public delegate void SerializationCallback(object o, StreamingContext context);
+
+ public delegate void SerializationErrorCallback(object o, StreamingContext context, ErrorContext errorContext);
+
///
/// Contract details for a used by the .
///
@@ -94,37 +98,44 @@ namespace Newtonsoft.Json.Serialization
/// Gets or sets all methods called immediately after deserialization of the object.
///
/// The methods called immediately after deserialization of the object.
- public IList OnDeserializedMethods { get; private set; }
+ public IList OnDeserializedCallbacks { get; private set; }
///
/// Gets or sets all methods called during deserialization of the object.
///
/// The methods called during deserialization of the object.
- public IList OnDeserializingMethods { get; private set; }
+ public IList OnDeserializingCallbacks { get; private set; }
///
/// Gets or sets all methods called after serialization of the object graph.
///
/// The methods called after serialization of the object graph.
- public IList OnSerializedMethods { get; private set; }
+ public IList OnSerializedCallbacks { get; private set; }
///
/// Gets or sets all methods called before serialization of the object.
///
/// The methods called before serialization of the object.
- public IList OnSerializingMethods { get; private set; }
+ public IList OnSerializingCallbacks { get; private set; }
+
+ ///
+ /// Gets or sets all method called when an error is thrown during the serialization of the object.
+ ///
+ /// The methods called when an error is thrown during the serialization of the object.
+ public IList OnErrorCallbacks { get; private set; }
///
/// Gets or sets the method called immediately after deserialization of the object.
///
/// The method called immediately after deserialization of the object.
+ [Obsolete("This property is obsolete and has been replaced by the OnDeserializedCallbacks collection.")]
public MethodInfo OnDeserialized
{
- get { return (OnDeserializedMethods.Count > 0) ? OnDeserializedMethods[0] : null; }
- set
+ get { return (OnDeserializedCallbacks.Count > 0) ? OnDeserializedCallbacks[0].Method() : null; }
+ set
{
- OnDeserializedMethods.Clear();
- OnDeserializedMethods.Add(value);
+ OnDeserializedCallbacks.Clear();
+ OnDeserializedCallbacks.Add(CreateSerializationCallback(value));
}
}
@@ -132,13 +143,14 @@ namespace Newtonsoft.Json.Serialization
/// Gets or sets the method called during deserialization of the object.
///
/// The method called during deserialization of the object.
+ [Obsolete("This property is obsolete and has been replaced by the OnDeserializingCallbacks collection.")]
public MethodInfo OnDeserializing
{
- get { return (OnDeserializingMethods.Count > 0) ? OnDeserializingMethods[0] : null; }
+ get { return (OnDeserializingCallbacks.Count > 0) ? OnDeserializingCallbacks[0].Method() : null; }
set
{
- OnDeserializingMethods.Clear();
- OnDeserializingMethods.Add(value);
+ OnDeserializingCallbacks.Clear();
+ OnDeserializingCallbacks.Add(CreateSerializationCallback(value));
}
}
@@ -146,13 +158,14 @@ namespace Newtonsoft.Json.Serialization
/// Gets or sets the method called after serialization of the object graph.
///
/// The method called after serialization of the object graph.
+ [Obsolete("This property is obsolete and has been replaced by the OnSerializedCallbacks collection.")]
public MethodInfo OnSerialized
{
- get { return (OnSerializedMethods.Count > 0) ? OnSerializedMethods[0] : null; }
+ get { return (OnSerializedCallbacks.Count > 0) ? OnSerializedCallbacks[0].Method() : null; }
set
{
- OnSerializedMethods.Clear();
- OnSerializedMethods.Add(value);
+ OnSerializedCallbacks.Clear();
+ OnSerializedCallbacks.Add(CreateSerializationCallback(value));
}
}
@@ -160,13 +173,29 @@ namespace Newtonsoft.Json.Serialization
/// Gets or sets the method called before serialization of the object.
///
/// The method called before serialization of the object.
+ [Obsolete("This property is obsolete and has been replaced by the OnSerializingCallbacks collection.")]
public MethodInfo OnSerializing
{
- get { return (OnSerializingMethods.Count > 0) ? OnSerializingMethods[0] : null; }
+ get { return (OnSerializingCallbacks.Count > 0) ? OnSerializingCallbacks[0].Method() : null; }
set
{
- OnSerializingMethods.Clear();
- OnSerializingMethods.Add(value);
+ OnSerializingCallbacks.Clear();
+ OnSerializingCallbacks.Add(CreateSerializationCallback(value));
+ }
+ }
+
+ ///
+ /// Gets or sets the method called when an error is thrown during the serialization of the object.
+ ///
+ /// The method called when an error is thrown during the serialization of the object.
+ [Obsolete("This property is obsolete and has been replaced by the OnErrorCallbacks collection.")]
+ public MethodInfo OnError
+ {
+ get { return (OnErrorCallbacks.Count > 0) ? OnErrorCallbacks[0].Method() : null; }
+ set
+ {
+ OnErrorCallbacks.Clear();
+ OnErrorCallbacks.Add(CreateSerializationErrorCallback(value));
}
}
@@ -182,66 +211,6 @@ namespace Newtonsoft.Json.Serialization
/// true if the default object creator is non-public; otherwise, false.
public bool DefaultCreatorNonPublic { get; set; }
- ///
- /// Gets or sets all method called when an error is thrown during the serialization of the object.
- ///
- /// The methods called when an error is thrown during the serialization of the object.
- public IList OnErrorMethods { get; private set; }
-
- ///
- /// Gets or sets the method called when an error is thrown during the serialization of the object.
- ///
- /// The method called when an error is thrown during the serialization of the object.
- public MethodInfo OnError
- {
- get { return (OnErrorMethods.Count > 0) ? OnErrorMethods[0] : null; }
- set
- {
- OnErrorMethods.Clear();
- OnErrorMethods.Add(value);
- }
- }
-
- internal void InvokeOnSerializing(object o, StreamingContext context)
- {
- foreach (MethodInfo mi in OnSerializingMethods)
- {
- mi.Invoke(o, new object[] {context});
- }
- }
-
- internal void InvokeOnSerialized(object o, StreamingContext context)
- {
- foreach (MethodInfo mi in OnSerializedMethods)
- {
- mi.Invoke(o, new object[] {context});
- }
- }
-
- internal void InvokeOnDeserializing(object o, StreamingContext context)
- {
- foreach (MethodInfo mi in OnDeserializingMethods)
- {
- mi.Invoke(o, new object[] {context});
- }
- }
-
- internal void InvokeOnDeserialized(object o, StreamingContext context)
- {
- foreach (MethodInfo mi in OnDeserializedMethods)
- {
- mi.Invoke(o, new object[] {context});
- }
- }
-
- internal void InvokeOnError(object o, StreamingContext context, ErrorContext errorContext)
- {
- foreach (MethodInfo mi in OnErrorMethods)
- {
- mi.Invoke(o, new object[] {context, errorContext});
- }
- }
-
internal JsonContract(Type underlyingType)
{
ValidationUtils.ArgumentNotNull(underlyingType, "underlyingType");
@@ -286,11 +255,61 @@ namespace Newtonsoft.Json.Serialization
InternalReadType = ReadType.Read;
}
- OnErrorMethods = new List();
- OnSerializedMethods = new List();
- OnSerializingMethods = new List();
- OnDeserializedMethods = new List();
- OnDeserializingMethods = new List();
+ OnErrorCallbacks = new List();
+ OnSerializedCallbacks = new List();
+ OnSerializingCallbacks = new List();
+ OnDeserializedCallbacks = new List();
+ OnDeserializingCallbacks = new List();
+ }
+
+ internal void InvokeOnSerializing(object o, StreamingContext context)
+ {
+ foreach (SerializationCallback callback in OnSerializingCallbacks)
+ {
+ callback(o, context);
+ }
+ }
+
+ internal void InvokeOnSerialized(object o, StreamingContext context)
+ {
+ foreach (SerializationCallback callback in OnSerializedCallbacks)
+ {
+ callback(o, context);
+ }
+ }
+
+ internal void InvokeOnDeserializing(object o, StreamingContext context)
+ {
+ foreach (SerializationCallback callback in OnDeserializingCallbacks)
+ {
+ callback(o, context);
+ }
+ }
+
+ internal void InvokeOnDeserialized(object o, StreamingContext context)
+ {
+ foreach (SerializationCallback callback in OnDeserializedCallbacks)
+ {
+ callback(o, context);
+ }
+ }
+
+ internal void InvokeOnError(object o, StreamingContext context, ErrorContext errorContext)
+ {
+ foreach (SerializationErrorCallback callback in OnErrorCallbacks)
+ {
+ callback(o, context, errorContext);
+ }
+ }
+
+ internal static SerializationCallback CreateSerializationCallback(MethodInfo callbackMethodInfo)
+ {
+ return (o, context) => callbackMethodInfo.Invoke(o, new object[] { context });
+ }
+
+ internal static SerializationErrorCallback CreateSerializationErrorCallback(MethodInfo callbackMethodInfo)
+ {
+ return (o, context, econtext) => callbackMethodInfo.Invoke(o, new object[] { context, econtext });
}
}
}
\ No newline at end of file
diff --git a/Src/Newtonsoft.Json/Serialization/JsonDictionaryContract.cs b/Src/Newtonsoft.Json/Serialization/JsonDictionaryContract.cs
index 47619d94..b0062ae2 100644
--- a/Src/Newtonsoft.Json/Serialization/JsonDictionaryContract.cs
+++ b/Src/Newtonsoft.Json/Serialization/JsonDictionaryContract.cs
@@ -168,6 +168,6 @@ namespace Newtonsoft.Json.Serialization
}
#endif
- public bool IsReadOnlyDictionary { get; set; }
+ internal bool IsReadOnlyDictionary { get; set; }
}
}
\ No newline at end of file
diff --git a/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs b/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs
index 1460e10e..6a14fde7 100644
--- a/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs
+++ b/Src/Newtonsoft.Json/Serialization/JsonSerializerInternalReader.cs
@@ -578,10 +578,10 @@ To fix this error either change the JSON to a {1} or change the deserialized typ
if (id != null && isTemporaryListReference)
throw JsonSerializationException.Create(reader, "Cannot preserve reference to array or readonly list: {0}.".FormatWith(CultureInfo.InvariantCulture, contract.UnderlyingType));
- if (contract.OnSerializingMethods.Count > 0 && isTemporaryListReference)
+ if (contract.OnSerializingCallbacks.Count > 0 && isTemporaryListReference)
throw JsonSerializationException.Create(reader, "Cannot call OnSerializing on an array or readonly list: {0}.".FormatWith(CultureInfo.InvariantCulture, contract.UnderlyingType));
- if (contract.OnErrorMethods.Count > 0 && isTemporaryListReference)
+ if (contract.OnErrorCallbacks.Count > 0 && isTemporaryListReference)
throw JsonSerializationException.Create(reader, "Cannot call OnError on an array or readonly list: {0}.".FormatWith(CultureInfo.InvariantCulture, contract.UnderlyingType));
if (!arrayContract.IsMultidimensionalArray)
diff --git a/Src/Newtonsoft.Json/Utilities/TypeExtensions.cs b/Src/Newtonsoft.Json/Utilities/TypeExtensions.cs
index e2a3ab8c..5d92f745 100644
--- a/Src/Newtonsoft.Json/Utilities/TypeExtensions.cs
+++ b/Src/Newtonsoft.Json/Utilities/TypeExtensions.cs
@@ -78,6 +78,15 @@ namespace Newtonsoft.Json.Utilities
}
#endif
+ public static MethodInfo Method(this Delegate d)
+ {
+#if NETFX_CORE
+ return d.GetMethodInfo();
+#else
+ return d.Method;
+#endif
+ }
+
public static MemberTypes MemberType(this MemberInfo memberInfo)
{
#if !(NETFX_CORE || PORTABLE)