private void CollectTypes() { AddSystemType <DateTime>("dateTime"); AddSystemType <DateTime>("date"); AddSystemType <bool>("boolean"); AddSystemType <float>("float"); AddSystemType <double>("double"); AddSystemType <decimal>("decimal"); AddSystemType <long>("long"); AddSystemType <int>("int"); AddSystemType <short>("short"); AddSystemType <BigInteger>("integer"); AddSystemType <string>("string"); AddSystemType <string>("anyURI"); AddSystemType <Stream>("base64Binary"); AddSystemType <Stream>("hexBinary"); AddSystemType <Stream>("base64"); var typeDefinitions = contractAssembly.GetTypes() .Where(type => type.IsXRoadSerializable() || (type.GetTypeInfo().IsEnum&& type.GetTypeInfo().GetCustomAttribute <XmlTypeAttribute>() != null)) .Where(type => !version.HasValue || type.GetTypeInfo().ExistsInVersion(version.Value)) .Select(type => schemaDefinitionProvider.GetTypeDefinition(type)) .Where(def => !def.IsAnonymous && def.Name != null && def.State == DefinitionState.Default) .ToList(); foreach (var typeDefinition in typeDefinitions) { if (schemaTypeDefinitions.ContainsKey(typeDefinition.Name)) { throw new Exception($"Multiple type definitions for same name `{typeDefinition.Name}`."); } schemaTypeDefinitions.Add(typeDefinition.Name, typeDefinition); runtimeTypeDefinitions.Add(typeDefinition.Type, typeDefinition); var baseType = typeDefinition.Type.GetTypeInfo().BaseType; if (baseType == null || !baseType.IsXRoadSerializable()) { continue; } List <Type> typeList; if (!derivedTypes.TryGetValue(baseType, out typeList)) { derivedTypes.Add(baseType, typeList = new List <Type>()); } typeList.Add(typeDefinition.Type); } }
private ITypeMap AddTypeMap(Type runtimeType, IDictionary <Type, ITypeMap> partialTypeMaps) { if (runtimeType.IsXRoadSerializable() && Version.HasValue && !runtimeType.GetTypeInfo().ExistsInVersion(Version.Value)) { throw new SchemaDefinitionException($"The runtime type `{runtimeType.Name}` is not defined for DTO version `{Version.Value}`."); } var typeDefinition = schemaDefinitionProvider.GetTypeDefinition(runtimeType); ITypeMap typeMap; if (typeDefinition.TypeMapType != null) { typeMap = (ITypeMap)Activator.CreateInstance(typeDefinition.TypeMapType, this, typeDefinition); return(runtimeTypeMaps.GetOrAdd(runtimeType, typeMap)); } if (typeDefinition is CollectionDefinition collectionDefinition) { var elementType = typeDefinition.Type.GetElementType(); if (!ReferenceEquals(elementType.GetTypeInfo().Assembly, contractAssembly)) { return(null); } var itemTypeMap = GetTypeMap(elementType, partialTypeMaps); collectionDefinition.ItemDefinition = itemTypeMap.Definition; var typeMapType = typeof(ArrayTypeMap <>).MakeGenericType(itemTypeMap.Definition.Type); typeMap = (ITypeMap)Activator.CreateInstance(typeMapType, this, collectionDefinition, itemTypeMap); return(runtimeTypeMaps.GetOrAdd(runtimeType, typeMap)); } if (!ReferenceEquals(typeDefinition.Type.GetTypeInfo().Assembly, contractAssembly)) { return(null); } if (typeDefinition.IsCompositeType && typeDefinition.Type.GetTypeInfo().GetConstructor(Type.EmptyTypes) == null) { throw new SchemaDefinitionException($"The runtime type '{typeDefinition.Type.Name}' does not have default constructor."); } if (typeDefinition.Type.GetTypeInfo().IsEnum) { typeMap = (ITypeMap)Activator.CreateInstance(typeof(EnumTypeMap), typeDefinition); } else if (typeDefinition.Type.GetTypeInfo().IsAbstract) { typeMap = (ITypeMap)Activator.CreateInstance(typeof(AbstractTypeMap), typeDefinition); } else if (typeDefinition.HasStrictContentOrder) { typeMap = (ITypeMap)Activator.CreateInstance(typeof(SequenceTypeMap <>).MakeGenericType(typeDefinition.Type), this, typeDefinition); } else { typeMap = (ITypeMap)Activator.CreateInstance(typeof(AllTypeMap <>).MakeGenericType(typeDefinition.Type), this, typeDefinition); } if (!(typeMap is ICompositeTypeMap compositeTypeMap)) { return(runtimeTypeMaps.GetOrAdd(runtimeType, typeMap)); } partialTypeMaps = partialTypeMaps ?? new Dictionary <Type, ITypeMap>(); partialTypeMaps.Add(typeDefinition.Type, compositeTypeMap); compositeTypeMap.InitializeProperties(GetRuntimeProperties(typeDefinition, partialTypeMaps), availableFilters); partialTypeMaps.Remove(typeDefinition.Type); return(runtimeTypeMaps.GetOrAdd(runtimeType, compositeTypeMap)); }