/// <summary> /// Resolves class, interface, or struct type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// An unsuccessful <see cref="UnsupportedTypeException" /> result if <paramref name="type" /> /// is an array or a primitive type; a successful <see cref="RecordResolution" /> result /// otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (!type.IsArray && !type.IsPrimitive) { var contract = GetAttribute <DataContractAttribute>(type); var name = CreateNameResolution(type, contract); var @namespace = CreateNamespaceResolution(type, contract); var fields = (contract == null ? GetMembers(type, MemberVisibility) .Select(m => ( m.MemberInfo, m.Type, Attribute: GetAttribute <NonSerializedAttribute>(m.MemberInfo) )) .Where(m => m.Attribute == null) .Select(m => ( m.MemberInfo, m.Type, Name: new IdentifierResolution(m.MemberInfo.Name), Order: 0 )) : GetMembers(type, MemberVisibility) .Select(m => ( m.MemberInfo, m.Type, Attribute: GetAttribute <DataMemberAttribute>(m.MemberInfo) )) .Where(m => m.Attribute != null) .Select(m => ( m.MemberInfo, m.Type, Name: CreateNameResolution(m.MemberInfo, m.Attribute), m.Attribute !.Order ))) .OrderBy(m => m.Order) .ThenBy(m => m.Name.Value) .Select(m => new FieldResolution(m.MemberInfo, m.Type, m.Name)) .ToList(); var constructors = GetConstructors(type, MemberVisibility) .Select(c => new ConstructorResolution( c.ConstructorInfo, c.Parameters.Select(p => new ParameterResolution(p, p.ParameterType, new IdentifierResolution(p.Name))).ToList() )).ToList(); result.TypeResolution = new RecordResolution(type, name, @namespace, fields, constructors); } else { result.Exceptions.Add(new UnsupportedTypeException(type)); } return(result); }
/// <summary> /// Resolves enum type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// A successful <see cref="EnumResolution" /> result if <paramref name="type" /> is an /// <see cref="Enum" /> type; an unsuccessful <see cref="UnsupportedTypeException" /> /// result otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (type.IsEnum) { var contract = GetAttribute <DataContractAttribute>(type); var name = CreateNameResolution(type, contract); var @namespace = CreateNamespaceResolution(type, contract); var isFlagEnum = GetAttribute <FlagsAttribute>(type) != null; var symbols = (contract == null ? type.GetFields(BindingFlags.Public | BindingFlags.Static) .Select(f => ( MemberInfo: f as MemberInfo, Attribute: GetAttribute <NonSerializedAttribute>(f) )) .Where(f => f.Attribute == null) .Select(f => ( f.MemberInfo, Name: new IdentifierResolution(f.MemberInfo.Name), Value: Enum.Parse(type, f.MemberInfo.Name) )) : type.GetFields(BindingFlags.Public | BindingFlags.Static) .Select(f => ( MemberInfo: f as MemberInfo, Attribute: GetAttribute <EnumMemberAttribute>(f) )) .Where(f => f.Attribute != null) .Select(f => ( f.MemberInfo, Name: CreateNameResolution(f.MemberInfo, f.Attribute), Value: Enum.Parse(type, f.MemberInfo.Name) ))) .OrderBy(f => f.Value) .ThenBy(f => f.Name.Value) .Select(f => new SymbolResolution(f.MemberInfo, f.Name, f.Value)) .ToList(); result.TypeResolution = new EnumResolution(type, type.GetEnumUnderlyingType(), name, @namespace, isFlagEnum, symbols); } else { result.Exceptions.Add(new UnsupportedTypeException(type)); } return(result); }
/// <summary> /// Resolves decimal type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// A successful <see cref="DecimalResolution" /> result if the type is <see cref="decimal" />; /// an unsuccessful <see cref="UnsupportedTypeException" /> result otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (type == typeof(decimal)) { result.TypeResolution = new DecimalResolution(type, 29, 14); } else { result.Exceptions.Add(new UnsupportedTypeException(type)); } return(result); }
/// <summary> /// Resolves date/time type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// A successful <see cref="TimestampResolution" /> result if the type is <see cref="DateTime" /> /// or <see cref="DateTimeOffset" />; an unsuccessful <see cref="UnsupportedTypeException" /> /// result otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (type == typeof(DateTime) || type == typeof(DateTimeOffset)) { result.TypeResolution = new TimestampResolution(type, 1m / TimeSpan.TicksPerSecond); } else { result.Exceptions.Add(new UnsupportedTypeException(type)); } return(result); }
/// <summary> /// Resolves byte array type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// A successful <see cref="ByteArrayResolution" /> result if the type is <see cref="T:System.Byte[]" />; /// an unsuccessful <see cref="UnsupportedTypeException" /> result otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (type == typeof(byte[])) { result.TypeResolution = new ByteArrayResolution(type); } else { result.Exceptions.Add(new UnsupportedTypeException(type)); } return(result); }
/// <summary> /// Resolves dictionary type information. /// </summary> /// <param name="type"> /// The type to resolve. /// </param> /// <returns> /// A successful <see cref="MapResolution" /> result if the type is <see cref="T:System.Collections.Generic.IEnumerable{System.Collections.Generic.KeyValuePair`2}" />; /// an unsuccessful <see cref="UnsupportedTypeException" /> result otherwise. /// </returns> public override ITypeResolutionResult ResolveType(Type type) { var result = new TypeResolutionResult(); if (type.GetEnumerableType() is Type pair && pair.IsGenericType && pair.GetGenericTypeDefinition() == typeof(KeyValuePair <,>)) { var arguments = pair.GetGenericArguments(); var key = arguments.ElementAt(0); var value = arguments.ElementAt(1); var constructors = GetConstructors(type, MemberVisibility) .Select(c => new ConstructorResolution( c.ConstructorInfo, c.Parameters.Select(p => new ParameterResolution(p, p.ParameterType, new IdentifierResolution(p.Name))).ToList() )) .ToList(); result.TypeResolution = new MapResolution(type, key, value, constructors); }