static private NewTargetDoesNotHavePublicDefaultConstructor ( |
||
type | The target type. | |
리턴 |
public static SerializationTarget Prepare(SerializationContext context, Type targetType) { var getters = GetTargetMembers(targetType).OrderBy(entry => entry.Contract.Id).ToArray(); if (getters.Length == 0) { throw new SerializationException(String.Format(CultureInfo.CurrentCulture, "Cannot serialize type '{0}' because it does not have any serializable fields nor properties.", targetType)); } var memberCandidates = getters.Where(entry => CheckTargetEligibility(entry.Member)).ToArray(); if (memberCandidates.Length == 0) { var constructor = FindDeserializationConstructor(targetType); return(new SerializationTarget(ComplementMembers(getters, context, targetType), constructor)); } var defaultConstructor = targetType.GetConstructor(ReflectionAbstractions.EmptyTypes); if (defaultConstructor == null && !targetType.GetIsValueType()) { throw SerializationExceptions.NewTargetDoesNotHavePublicDefaultConstructor(targetType); } // Because members' order is equal to declared order is NOT guaranteed, so explicit ordering is required. IList <SerializingMember> members; if (memberCandidates.All(item => item.Contract.Id == DataMemberContract.UnspecifiedId)) { // Alphabetical order. members = memberCandidates.OrderBy(item => item.Contract.Name).ToArray(); } else { // ID order. members = ComplementMembers(memberCandidates, context, targetType); } return(new SerializationTarget(members, defaultConstructor)); }
public static SerializationTarget Prepare(SerializationContext context, Type targetType) { var getters = GetTargetMembers(targetType).OrderBy(entry => entry.Contract.Id).ToArray(); if (getters.Length == 0) { throw new SerializationException(String.Format(CultureInfo.CurrentCulture, "Cannot serialize type '{0}' because it does not have any serializable fields nor properties.", targetType)); } bool?canDeserialize = null; var memberCandidates = getters.Where(entry => CheckTargetEligibility(entry.Member)).ToArray(); if (memberCandidates.Length == 0) { var deserializationConstructor = FindDeserializationConstructor(context, targetType, out canDeserialize); var complementedMembers = ComplementMembers(getters, context, targetType); var correspondingMemberNames = FindCorrespondingMemberNames(complementedMembers, deserializationConstructor); return (new SerializationTarget( complementedMembers, deserializationConstructor, correspondingMemberNames, canDeserialize )); } // Try to get default constructor. var constructor = targetType.GetConstructor(ReflectionAbstractions.EmptyTypes); if (constructor == null && !targetType.GetIsValueType()) { // Try to get deserialization constructor. var deserializationConstructor = FindDeserializationConstructor(context, targetType, out canDeserialize); if (deserializationConstructor == null && !context.CompatibilityOptions.AllowAsymmetricSerializer) { throw SerializationExceptions.NewTargetDoesNotHavePublicDefaultConstructor(targetType); } constructor = deserializationConstructor; } else { // Let's prefer annotated constructor here. var markedConstructors = FindExplicitDeserializationConstructors(targetType.GetConstructors()); if (markedConstructors.Count == 1) { // For backward compatibility, no exceptions are thrown here even if mulitiple deserialization constructor attributes in the type // just use default constructor for it. constructor = markedConstructors[0]; } // OK, appropriate constructor and setters are found. canDeserialize = true; } // Because members' order is equal to declared order is NOT guaranteed, so explicit ordering is required. IList <SerializingMember> members; if (memberCandidates.All(item => item.Contract.Id == DataMemberContract.UnspecifiedId)) { // Alphabetical order. members = memberCandidates.OrderBy(item => item.Contract.Name).ToArray(); } else { // ID order. members = ComplementMembers(memberCandidates, context, targetType); } return (new SerializationTarget( members, constructor, FindCorrespondingMemberNames(members, constructor), canDeserialize )); }
public static SerializationTarget Prepare(SerializationContext context, Type targetType) { VerifyCanSerializeTargetType(context, targetType); IEnumerable <string> memberIgnoreList = context.BindingOptions.GetIgnoringMembers(targetType); var getters = GetTargetMembers(targetType) .Where(getter => !memberIgnoreList.Contains(getter.MemberName, StringComparer.Ordinal)) .OrderBy(entry => entry.Contract.Id) .ToArray(); if (getters.Length == 0 && !typeof(IPackable).IsAssignableFrom(targetType) && !typeof(IUnpackable).IsAssignableFrom(targetType) #if FEATURE_TAP && (context.SerializerOptions.WithAsync && (!typeof(IAsyncPackable).IsAssignableFrom(targetType) && !typeof(IAsyncUnpackable).IsAssignableFrom(targetType) ) ) #endif // FEATURE_TAP ) { throw new SerializationException(String.Format(CultureInfo.CurrentCulture, "Cannot serialize type '{0}' because it does not have any serializable fields nor properties.", targetType)); } var memberCandidates = getters.Where(entry => CheckTargetEligibility(context, entry.Member)).ToArray(); if (memberCandidates.Length == 0 && !context.CompatibilityOptions.AllowAsymmetricSerializer) { ConstructorKind constructorKind; var deserializationConstructor = FindDeserializationConstructor(context, targetType, out constructorKind); var complementedMembers = ComplementMembers(getters, context, targetType); var correspondingMemberNames = FindCorrespondingMemberNames(complementedMembers, deserializationConstructor); return (new SerializationTarget( complementedMembers, deserializationConstructor, correspondingMemberNames, DetermineCanDeserialize(constructorKind, context, targetType, correspondingMemberNames, allowDefault: false) )); } else { bool? canDeserialize; ConstructorKind constructorKind; // Try to get default constructor. var constructor = targetType.GetConstructor(ReflectionAbstractions.EmptyTypes); if (constructor == null && !targetType.GetIsValueType()) { // Try to get deserialization constructor. var deserializationConstructor = FindDeserializationConstructor(context, targetType, out constructorKind); if (deserializationConstructor == null && !context.CompatibilityOptions.AllowAsymmetricSerializer) { throw SerializationExceptions.NewTargetDoesNotHavePublicDefaultConstructor(targetType); } constructor = deserializationConstructor; canDeserialize = null; } else if (memberCandidates.Length == 0) { #if DEBUG Contract.Assert(context.CompatibilityOptions.AllowAsymmetricSerializer); #endif // DEBUG // Absolutely cannot deserialize in this case. canDeserialize = false; constructorKind = ConstructorKind.Ambiguous; } else { constructorKind = ConstructorKind.Default; // Let's prefer annotated constructor here. var markedConstructors = FindExplicitDeserializationConstructors(targetType.GetConstructors()); if (markedConstructors.Count == 1) { // For backward compatibility, no exceptions are thrown here even if mulitiple deserialization constructor attributes in the type // just use default constructor for it. constructor = markedConstructors[0]; constructorKind = ConstructorKind.Marked; } // OK, appropriate constructor and setters are found. canDeserialize = true; } if (constructor != null && constructor.GetParameters().Any() || context.CompatibilityOptions.AllowAsymmetricSerializer) { // Recalculate members because getter-only/readonly members should be included for constructor deserialization. memberCandidates = getters; } // Because members' order is equal to declared order is NOT guaranteed, so explicit ordering is required. IList <SerializingMember> members; if (memberCandidates.All(item => item.Contract.Id == DataMemberContract.UnspecifiedId)) { // Alphabetical order. members = memberCandidates.OrderBy(item => item.Contract.Name).ToArray(); } else { // ID order. members = ComplementMembers(memberCandidates, context, targetType); } var correspondingMemberNames = FindCorrespondingMemberNames(members, constructor); return (new SerializationTarget( members, constructor, correspondingMemberNames, canDeserialize ?? DetermineCanDeserialize(constructorKind, context, targetType, correspondingMemberNames, allowDefault: true) )); } }