GetSerializerModifiers() public method

Gets the serializer modifiers for the specified type. Note that the order is important because the modifiers will be called in the returned order during serialization and in reversed order during deserialization.
The is null.
public GetSerializerModifiers ( Type type ) : ISerializerModifier[]
type System.Type The type.
return ISerializerModifier[]
        /// <summary>
        /// Serializes the specified model.
        /// </summary>
        /// <param name="model">The model.</param>
        /// <param name="context">The context.</param>
        public virtual void Serialize(ModelBase model, TSerializationContext context)
        {
            Argument.IsNotNull("model", model);
            Argument.IsNotNull("context", context);

            using (var finalContext = GetContext(model, context, SerializationContextMode.Serialization))
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(finalContext.ModelType);

                Log.Debug("Using '{0}' serializer modifiers to deserialize type '{1}'", serializerModifiers.Length, finalContext.ModelType.GetSafeFullName());

                var serializingEventArgs = new SerializationEventArgs(finalContext);

                Serializing.SafeInvoke(this, serializingEventArgs);

                foreach (var serializerModifier in serializerModifiers)
                {
                    serializerModifier.OnSerializing(finalContext, model);
                }

                BeforeSerialization(finalContext);

                var members = GetSerializableMembers(model);
                SerializeMembers(finalContext, members);

                AfterSerialization(finalContext);

                foreach (var serializerModifier in serializerModifiers)
                {
                    serializerModifier.OnSerialized(finalContext, model);
                }

                Serialized.SafeInvoke(this, serializingEventArgs);
            }
        }
示例#2
0
        /// <summary>
        /// Returns whether the member value should be serialized as dictionary.
        /// </summary>
        /// <param name="memberType">Type of the member.</param>
        /// <returns><c>true</c> if the member value should be serialized as dictionary, <c>false</c> otherwise.</returns>
        protected virtual bool ShouldSerializeAsDictionary(Type memberType)
        {
            return(_shouldSerializeAsDictionaryCache.GetFromCacheOrFetch(memberType, () =>
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(memberType);
                if (serializerModifiers != null)
                {
                    foreach (var serializerModifier in serializerModifiers)
                    {
                        var shouldSerializeAsDictionary = serializerModifier.ShouldSerializeAsDictionary();
                        if (shouldSerializeAsDictionary.HasValue)
                        {
                            return shouldSerializeAsDictionary.Value;
                        }
                    }
                }

                if (memberType.IsDictionary())
                {
                    return true;
                }

                return false;
            }));
        }
示例#3
0
        /// <summary>
        /// Serializes the specified model.
        /// </summary>
        /// <param name="model">The model.</param>
        /// <param name="context">The context.</param>
        protected virtual void Serialize(object model, ISerializationContext <TSerializationContext> context)
        {
            Argument.IsNotNull("model", model);
            Argument.IsNotNull("context", context);

            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

            Log.Debug("Using '{0}' serializer modifiers to deserialize type '{1}'", serializerModifiers.Length,
                      context.ModelTypeName);

            var serializingEventArgs = new SerializationEventArgs(context);

            Serializing.SafeInvoke(this, serializingEventArgs);

            foreach (var serializerModifier in serializerModifiers)
            {
                serializerModifier.OnSerializing(context, model);
            }

            BeforeSerialization(context);

            var members = GetSerializableMembers(context, model);

            SerializeMembers(context, members);

            AfterSerialization(context);

            foreach (var serializerModifier in serializerModifiers)
            {
                serializerModifier.OnSerialized(context, model);
            }

            Serialized.SafeInvoke(this, serializingEventArgs);
        }
示例#4
0
        /// <summary>
        /// Serializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <param name="membersToSerialize">The members to serialize.</param>
        protected virtual void SerializeMembers(ISerializationContext <TSerializationContext> context, List <MemberValue> membersToSerialize)
        {
            ApiCop.UpdateRule <InitializationApiCopRule>("SerializerBase.WarmupAtStartup",
                                                         x => x.SetInitializationMode(InitializationMode.Lazy, GetType().GetSafeFullName(false)));

            if (membersToSerialize.Count == 0)
            {
                return;
            }

            using (GetCurrentSerializationScopeManager(context.Configuration))
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

                foreach (var member in membersToSerialize)
                {
                    bool skipByModifiers = false;
                    foreach (var serializerModifier in serializerModifiers)
                    {
                        if (serializerModifier.ShouldIgnoreMember(context, context.Model, member))
                        {
                            skipByModifiers = true;
                            break;
                        }
                    }

                    if (skipByModifiers)
                    {
                        continue;
                    }

                    var memberSerializationEventArgs = new MemberSerializationEventArgs(context, member);

                    SerializingMember.SafeInvoke(this, memberSerializationEventArgs);

                    BeforeSerializeMember(context, member);

                    foreach (var serializerModifier in serializerModifiers)
                    {
                        serializerModifier.SerializeMember(context, member);
                    }

                    if (ShouldSerializeUsingParseAndToString(member, true))
                    {
                        var objectToStringValue = SerializeUsingObjectToString(context, member);
                        if (!string.IsNullOrWhiteSpace(objectToStringValue))
                        {
                            member.Value = objectToStringValue;
                        }
                    }

                    SerializeMember(context, member);

                    AfterSerializeMember(context, member);

                    SerializedMember.SafeInvoke(this, memberSerializationEventArgs);
                }
            }
        }
            public void ReturnsRightModifiersInRightOrderForInheritedClasses()
            {
                var serializationManager = new SerializationManager();

                var modifiers = serializationManager.GetSerializerModifiers(typeof(TestModels.ModelC));

                Assert.AreEqual(3, modifiers.Length);
                Assert.AreEqual(typeof(TestModels.ModelASerializerModifier), modifiers[0].GetType());
                Assert.AreEqual(typeof(TestModels.ModelBSerializerModifier), modifiers[1].GetType());
                Assert.AreEqual(typeof(TestModels.ModelCSerializerModifier), modifiers[2].GetType());
            }
示例#6
0
        /// <summary>
        /// Returns whether the member value should be serialized as collection.
        /// </summary>
        /// <param name="memberType">Type of the member.</param>
        /// <returns><c>true</c> if the member value should be serialized as collection, <c>false</c> otherwise.</returns>
        protected virtual bool ShouldSerializeAsCollection(Type memberType)
        {
            return(_shouldSerializeAsCollectionCache.GetFromCacheOrFetch(memberType, () =>
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(memberType);
                if (serializerModifiers != null)
                {
                    foreach (var serializerModifier in serializerModifiers)
                    {
                        var shouldSerializeAsCollection = serializerModifier.ShouldSerializeAsCollection();
                        if (shouldSerializeAsCollection.HasValue)
                        {
                            return shouldSerializeAsCollection.Value;
                        }
                    }
                }

                if (memberType == typeof(byte[]))
                {
                    return false;
                }

                // An exception is ModelBase, we will always serialize ourselves (even when it is a collection)
                if (memberType.IsModelBase())
                {
                    return ShouldSerializeModelAsCollection(memberType);
                }

                if (memberType.IsCollection())
                {
                    return true;
                }

                if (memberType == typeof(IEnumerable))
                {
                    return true;
                }

                if (memberType.IsGenericTypeEx())
                {
                    var genericDefinition = memberType.GetGenericTypeDefinitionEx();
                    if (genericDefinition == typeof(IEnumerable <>) ||
                        typeof(IEnumerable <>).IsAssignableFromEx(genericDefinition))
                    {
                        return true;
                    }
                }

                return false;
            }));
        }
示例#7
0
        /// <summary>
        /// Deserializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <returns>The deserialized list of member values.</returns>
        protected virtual List <MemberValue> DeserializeMembers(ISerializationContext <TSerializationContext> context)
        {
            ApiCop.UpdateRule <InitializationApiCopRule>("SerializerBase.WarmupAtStartup",
                                                         x => x.SetInitializationMode(InitializationMode.Lazy, GetType().GetSafeFullName()));

            var deserializedMemberValues = new List <MemberValue>();

            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType).Reverse();

            var membersToDeserialize = GetSerializableMembers(context.Model);

            foreach (var member in membersToDeserialize)
            {
                var memberSerializationEventArgs = new MemberSerializationEventArgs(context, member);

                DeserializingMember.SafeInvoke(this, memberSerializationEventArgs);

                BeforeDeserializeMember(context, member);

                var serializationObject = DeserializeMember(context, member);
                if (serializationObject.IsSuccessful)
                {
                    // Note that we need to sync the member values every time
                    var memberValue = new MemberValue(member.MemberGroup, member.ModelType, member.Type, member.Name, serializationObject.MemberValue);
                    member.Value = memberValue.Value;

                    deserializedMemberValues.Add(memberValue);

                    foreach (var serializerModifier in serializerModifiers)
                    {
                        serializerModifier.DeserializeMember(context, member);
                        memberValue.Value = member.Value;
                    }

                    AfterDeserializeMember(context, member);
                    memberValue.Value = member.Value;

                    DeserializedMember.SafeInvoke(this, memberSerializationEventArgs);
                    memberValue.Value = member.Value;
                }
            }

            if (deserializedMemberValues.Count > 0)
            {
                PopulateModel(context.Model, deserializedMemberValues.ToArray());
            }

            return(deserializedMemberValues);
        }
示例#8
0
        /// <summary>
        /// Deserializes the specified model.
        /// </summary>
        /// <param name="model">The model.</param>
        /// <param name="serializationContext">The serialization context.</param>
        public virtual void Deserialize(ModelBase model, TSerializationContext serializationContext)
        {
            Argument.IsNotNull("model", model);
            Argument.IsNotNull("context", serializationContext);

            using (var finalContext = GetContext(model, serializationContext, SerializationContextMode.Deserialization))
            {
                bool?previousLeanAndMeanValue = null;
                if (!ModelBase.GlobalLeanAndMeanModel)
                {
                    previousLeanAndMeanValue = model.LeanAndMeanModel;
                    model.LeanAndMeanModel   = true;
                }

                var serializerModifiers = SerializationManager.GetSerializerModifiers(finalContext.ModelType);

                Log.Debug("Using '{0}' serializer modifiers to deserialize type '{1}'", serializerModifiers.Length, finalContext.ModelType.GetSafeFullName());

                var serializingEventArgs = new SerializationEventArgs(finalContext);

                Deserializing.SafeInvoke(this, serializingEventArgs);

                foreach (var serializerModifier in serializerModifiers)
                {
                    serializerModifier.OnDeserializing(finalContext, model);
                }

                BeforeDeserialization(finalContext);

                DeserializeMembers(finalContext);

                AfterDeserialization(finalContext);

                foreach (var serializerModifier in serializerModifiers)
                {
                    serializerModifier.OnDeserialized(finalContext, model);
                }

                Deserialized.SafeInvoke(this, serializingEventArgs);

                model.FinishDeserialization();

                if (previousLeanAndMeanValue.HasValue)
                {
                    model.LeanAndMeanModel = previousLeanAndMeanValue.Value;
                }
            }
        }
示例#9
0
        /// <summary>
        /// Serializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <param name="membersToSerialize">The members to serialize.</param>
        protected virtual void SerializeMembers(ISerializationContext <TSerializationContext> context, List <MemberValue> membersToSerialize)
        {
            ApiCop.UpdateRule <InitializationApiCopRule>("SerializerBase.WarmupAtStartup",
                                                         x => x.SetInitializationMode(InitializationMode.Lazy, GetType().GetSafeFullName()));

            var scopeName = SerializationContextHelper.GetSerializationReferenceManagerScopeName();

            using (ScopeManager <ISerializer> .GetScopeManager(scopeName, () => this))
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

                foreach (var member in membersToSerialize)
                {
                    bool skipByModifiers = false;
                    foreach (var serializerModifier in serializerModifiers)
                    {
                        if (serializerModifier.ShouldIgnoreMember(context, context.Model, member))
                        {
                            skipByModifiers = true;
                            break;
                        }
                    }

                    if (skipByModifiers)
                    {
                        continue;
                    }

                    var memberSerializationEventArgs = new MemberSerializationEventArgs(context, member);

                    SerializingMember.SafeInvoke(this, memberSerializationEventArgs);

                    BeforeSerializeMember(context, member);

                    foreach (var serializerModifier in serializerModifiers)
                    {
                        serializerModifier.SerializeMember(context, member);
                    }

                    SerializeMember(context, member);

                    AfterSerializeMember(context, member);

                    SerializedMember.SafeInvoke(this, memberSerializationEventArgs);
                }
            }
        }
示例#10
0
        /// <summary>
        /// Serializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <param name="membersToSerialize">The members to serialize.</param>
        protected virtual void SerializeMembers(ISerializationContext <TSerializationContextInfo> context, List <MemberValue> membersToSerialize)
        {
            if (membersToSerialize.Count == 0)
            {
                return;
            }

            using (GetCurrentSerializationScopeManager(context.Configuration))
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

                foreach (var member in membersToSerialize)
                {
                    if (StartMemberSerialization(context, member, serializerModifiers))
                    {
                        EndMemberSerialization(context, member);
                    }
                }
            }
        }
示例#11
0
        /// <summary>
        /// Returns whether the enum member value should be serialized as string.
        /// </summary>
        /// <param name="memberValue"></param>
        /// <param name="checkActualMemberType"></param>
        /// <returns></returns>
        protected virtual bool ShouldSerializeEnumAsString(MemberValue memberValue, bool checkActualMemberType)
        {
            var cacheKey = $"{memberValue.ModelTypeName}|{memberValue.Name}|{checkActualMemberType}";

            return(_shouldSerializeEnumAsStringCache.GetFromCacheOrFetch(cacheKey, () =>
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(memberValue.ModelType);

                var fieldInfo = memberValue.ModelType.GetFieldEx(memberValue.Name);
                if (fieldInfo != null)
                {
                    if (fieldInfo.IsDecoratedWithAttribute <SerializeEnumAsStringAttribute>())
                    {
                        return true;
                    }
                }

                var propertyInfo = memberValue.ModelType.GetPropertyEx(memberValue.Name);
                if (propertyInfo != null)
                {
                    if (propertyInfo.IsDecoratedWithAttribute <SerializeEnumAsStringAttribute>())
                    {
                        return true;
                    }
                }

                // Note: serializer modifiers can always win
                foreach (var serializerModifier in serializerModifiers)
                {
                    var value = serializerModifier.ShouldSerializeEnumMemberUsingToString(memberValue);
                    if (value.HasValue)
                    {
                        return value.Value;
                    }
                }

                return false;
            }));
        }
        /// <summary>
        /// Serializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <param name="membersToSerialize">The members to serialize.</param>
        protected virtual void SerializeMembers(ISerializationContext <TSerializationContext> context, List <MemberValue> membersToSerialize)
        {
            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

            foreach (var member in membersToSerialize)
            {
                bool skipByModifiers = false;
                foreach (var serializerModifier in serializerModifiers)
                {
                    if (serializerModifier.ShouldIgnoreMember(context, context.Model, member))
                    {
                        skipByModifiers = true;
                        break;
                    }
                }

                if (skipByModifiers)
                {
                    continue;
                }

                var memberSerializationEventArgs = new MemberSerializationEventArgs(context, member);

                SerializingMember.SafeInvoke(this, memberSerializationEventArgs);

                BeforeSerializeMember(context, member);

                foreach (var serializerModifier in serializerModifiers)
                {
                    serializerModifier.SerializeMember(context, member);
                }

                SerializeMember(context, member);

                AfterSerializeMember(context, member);

                SerializedMember.SafeInvoke(this, memberSerializationEventArgs);
            }
        }
示例#13
0
        /// <summary>
        /// Deserializes the specified model.
        /// </summary>
        /// <param name="model">The model.</param>
        /// <param name="context">The serialization context.</param>
        protected virtual object Deserialize(object model, ISerializationContext <TSerializationContextInfo> context)
        {
            Argument.IsNotNull("model", model);
            Argument.IsNotNull("context", context);

            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType);

            Log.Debug("Using '{0}' serializer modifiers to deserialize type '{1}'", serializerModifiers.Length, context.ModelTypeName);

            var serializingEventArgs = new SerializationEventArgs(context);

            Deserializing?.Invoke(this, serializingEventArgs);

            foreach (var serializerModifier in serializerModifiers)
            {
                serializerModifier.OnDeserializing(context, model);
            }

            BeforeDeserialization(context);

            var deserializedMemberValues = DeserializeMembers(context);

            PopulateModel(context, deserializedMemberValues);

            // Always use the deserialized model (might be a value type)
            model = context.Model;

            AfterDeserialization(context);

            foreach (var serializerModifier in serializerModifiers)
            {
                serializerModifier.OnDeserialized(context, model);
            }

            Deserialized?.Invoke(this, serializingEventArgs);

            return(model);
        }
        /// <summary>
        /// Deserializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <returns>The deserialized list of member values.</returns>
        protected virtual List <MemberValue> DeserializeMembers(ISerializationContext <TSerializationContextInfo> context)
        {
            var deserializedMemberValues = new List <MemberValue>();

            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType).Reverse();

            var membersToDeserialize = GetSerializableMembers(context, context.Model);

            foreach (var member in membersToDeserialize)
            {
                StartMemberDeserialization(context, member);

                var serializationObject = DeserializeMember(context, member);

                var finalMemberValue = EndMemberDeserialization(context, member, serializationObject, serializerModifiers);
                if (finalMemberValue != null)
                {
                    deserializedMemberValues.Add(finalMemberValue);
                }
            }

            return(deserializedMemberValues);
        }
示例#15
0
            public void RemovesSerializerModifier()
            {
                var serializationManager = new SerializationManager();

                serializationManager.AddSerializerModifier<DynamicSerializerModifierModel, DynamicSerializerModifier>();

                var modifiers = serializationManager.GetSerializerModifiers(typeof(DynamicSerializerModifierModel));

                Assert.AreEqual(1, modifiers.Length);
                Assert.AreEqual(typeof(DynamicSerializerModifier), modifiers[0].GetType());

                serializationManager.RemoveSerializerModifier<DynamicSerializerModifierModel, DynamicSerializerModifier>();

                modifiers = serializationManager.GetSerializerModifiers(typeof(DynamicSerializerModifierModel));

                Assert.AreEqual(0, modifiers.Length);
            }
        /// <summary>
        /// Deserializes the members.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <returns>The deserialized list of member values.</returns>
        protected virtual List <MemberValue> DeserializeMembers(ISerializationContext <TSerializationContext> context)
        {
            ApiCop.UpdateRule <InitializationApiCopRule>("SerializerBase.WarmupAtStartup",
                                                         x => x.SetInitializationMode(InitializationMode.Lazy, GetType().GetSafeFullName(false)));

            var deserializedMemberValues = new List <MemberValue>();

            var serializerModifiers = SerializationManager.GetSerializerModifiers(context.ModelType).Reverse();

            var membersToDeserialize = GetSerializableMembers(context, context.Model);

            foreach (var member in membersToDeserialize)
            {
                var memberSerializationEventArgs = new MemberSerializationEventArgs(context, member);

                DeserializingMember.SafeInvoke(this, memberSerializationEventArgs);

                BeforeDeserializeMember(context, member);

                var serializationObject = DeserializeMember(context, member);
                if (serializationObject.IsSuccessful)
                {
                    // Note that we need to sync the member values every time
                    var memberValue = new MemberValue(member.MemberGroup, member.ModelType, member.MemberType, member.Name,
                                                      member.NameForSerialization, serializationObject.MemberValue);

                    if (memberValue.MemberGroup == SerializationMemberGroup.Dictionary)
                    {
                        var targetDictionary = TypeFactory.CreateInstance(member.MemberType) as IDictionary;
                        if (targetDictionary == null)
                        {
                            throw Log.ErrorAndCreateException <NotSupportedException>("'{0}' seems to be a dictionary, but target model cannot be updated because it does not implement IDictionary",
                                                                                      context.ModelTypeName);
                        }

                        var enumerable = memberValue.Value as List <SerializableKeyValuePair>;
                        if (enumerable != null)
                        {
                            foreach (var item in enumerable)
                            {
                                targetDictionary.Add(item.Key, item.Value);
                            }
                        }
                        else
                        {
                            var sourceDictionary = memberValue.Value as IDictionary;
                            if (sourceDictionary != null)
                            {
                                foreach (var key in sourceDictionary.Keys)
                                {
                                    targetDictionary.Add(key, sourceDictionary[key]);
                                }
                            }
                        }

                        member.Value = targetDictionary;
                    }
                    else if (memberValue.MemberGroup == SerializationMemberGroup.Collection)
                    {
                        var sourceCollection = memberValue.Value as IEnumerable;

                        if (member.MemberType.IsArrayEx())
                        {
                            var elementType = member.MemberType.GetElementTypeEx();
                            member.Value = sourceCollection.ToArray(elementType);
                        }
                        else
                        {
                            var targetCollection = TypeFactory.CreateInstance(member.MemberType) as IList;
                            if (targetCollection == null)
                            {
                                throw Log.ErrorAndCreateException <NotSupportedException>("'{0}' seems to be a collection, but target model cannot be updated because it does not implement IList",
                                                                                          context.ModelTypeName);
                            }

                            if (sourceCollection != null)
                            {
                                foreach (var item in sourceCollection)
                                {
                                    targetCollection.Add(item);
                                }
                            }

                            member.Value = targetCollection;
                        }
                    }
                    else
                    {
                        member.Value = memberValue.Value;
                    }

                    deserializedMemberValues.Add(memberValue);

                    foreach (var serializerModifier in serializerModifiers)
                    {
                        serializerModifier.DeserializeMember(context, member);
                        memberValue.Value = member.Value;
                    }

                    AfterDeserializeMember(context, member);
                    memberValue.Value = member.Value;

                    DeserializedMember.SafeInvoke(this, memberSerializationEventArgs);
                    memberValue.Value = member.Value;
                }
            }

            if (deserializedMemberValues.Count > 0)
            {
                var firstMember = deserializedMemberValues[0];
                if (firstMember.MemberGroup == SerializationMemberGroup.SimpleRootObject)
                {
                    // Completely replace root object (this is a basic (non-reference) type)
                    context.Model = firstMember.Value;
                }
                else if (firstMember.MemberGroup == SerializationMemberGroup.Dictionary)
                {
                    var targetDictionary = context.Model as IDictionary;
                    if (targetDictionary == null)
                    {
                        throw Log.ErrorAndCreateException <NotSupportedException>("'{0}' seems to be a dictionary, but target model cannot be updated because it does not implement IDictionary",
                                                                                  context.ModelTypeName);
                    }

                    targetDictionary.Clear();

                    var sourceDictionary = firstMember.Value as IDictionary;
                    if (sourceDictionary != null)
                    {
                        foreach (var key in sourceDictionary.Keys)
                        {
                            targetDictionary.Add(key, sourceDictionary[key]);
                        }
                    }
                }
                else if (firstMember.MemberGroup == SerializationMemberGroup.Collection)
                {
                    if (context.ModelType.IsArrayEx())
                    {
                        context.Model = firstMember.Value;
                    }
                    else
                    {
                        var targetCollection = context.Model as IList;
                        if (targetCollection == null)
                        {
                            throw Log.ErrorAndCreateException <NotSupportedException>("'{0}' seems to be a collection, but target model cannot be updated because it does not implement IList",
                                                                                      context.ModelTypeName);
                        }

                        targetCollection.Clear();

                        var sourceCollection = firstMember.Value as IEnumerable;
                        if (sourceCollection != null)
                        {
                            foreach (var item in sourceCollection)
                            {
                                targetCollection.Add(item);
                            }
                        }
                    }
                }
                else
                {
                    PopulateModel(context.Model, deserializedMemberValues.ToArray());
                }
            }

            return(deserializedMemberValues);
        }
示例#17
0
        /// <summary>
        /// Returns whether the member value should be serialized using <c>ToString(IFormatProvider)</c> and deserialized using <c>Parse(string, IFormatProvider)</c>.
        /// </summary>
        /// <param name="memberValue">The member value.</param>
        /// <param name="checkActualMemberType">if set to <c>true</c>, check the actual member type.</param>
        /// <returns>
        ///   <c>true</c> if the member should be serialized using parse.
        /// </returns>
        protected virtual bool ShouldSerializeUsingParseAndToString(MemberValue memberValue, bool checkActualMemberType)
        {
            var cacheKey = $"{memberValue.ModelTypeName}|{memberValue.Name}|{checkActualMemberType}";

            return(_shouldSerializeUsingParseCache.GetFromCacheOrFetch(cacheKey, () =>
            {
                var serializerModifiers = SerializationManager.GetSerializerModifiers(memberValue.ModelType);

                var useParseAndToString = false;

                var fieldInfo = memberValue.ModelType.GetFieldEx(memberValue.Name);
                if (fieldInfo != null)
                {
                    useParseAndToString = fieldInfo.IsDecoratedWithAttribute <SerializeUsingParseAndToStringAttribute>();
                }

                if (!useParseAndToString)
                {
                    var propertyInfo = memberValue.ModelType.GetPropertyEx(memberValue.Name);
                    if (propertyInfo != null)
                    {
                        useParseAndToString = propertyInfo.IsDecoratedWithAttribute <SerializeUsingParseAndToStringAttribute>();
                    }
                }

                // Note: serializer modifiers can always win
                foreach (var serializerModifier in serializerModifiers)
                {
                    var value = serializerModifier.ShouldSerializeMemberUsingParse(memberValue);
                    if (value.HasValue)
                    {
                        if (!value.Value)
                        {
                            return false;
                        }

                        // At least 1 serializer modifier wants this to be using parse and tostring
                        useParseAndToString = true;
                    }
                }

                if (!useParseAndToString)
                {
                    return false;
                }

                var memberType = checkActualMemberType ? memberValue.ActualMemberType : memberValue.MemberType;
                if (memberType == null)
                {
                    memberType = memberValue.MemberType;
                }

                var toStringMethod = GetObjectToStringMethod(memberType);
                if (toStringMethod == null)
                {
                    return false;
                }

                var parseMethod = GetObjectParseMethod(memberType);
                if (parseMethod == null)
                {
                    return false;
                }

                return true;
            }));
        }
            public void ThrowsArgumentNullExceptionForNullType()
            {
                var serializationManager = new SerializationManager();

                ExceptionTester.CallMethodAndExpectException<ArgumentNullException>(() => serializationManager.GetSerializerModifiers(null));
            }