コード例 #1
0
        public DataContract GetDataContractForType(Type type)
        {
            var underlyingType = type.IsNullable(out Type innerType) ? innerType : type;

            if (PrimitiveTypesAndFormats.ContainsKey(underlyingType))
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats[underlyingType];

                return(new DataContract(
                           dataType: primitiveTypeAndFormat.Item1,
                           format: primitiveTypeAndFormat.Item2,
                           underlyingType: underlyingType));
            }

            if (underlyingType.IsEnum)
            {
                var enumValues = GetSerializedEnumValuesFor(underlyingType);

                var primitiveTypeAndFormat = (enumValues.Any(value => value is string))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[underlyingType.GetEnumUnderlyingType()];

                return(new DataContract(
                           dataType: primitiveTypeAndFormat.Item1,
                           format: primitiveTypeAndFormat.Item2,
                           underlyingType: underlyingType,
                           enumValues: enumValues));
            }

            if (underlyingType.IsDictionary(out Type keyType, out Type valueType))
            {
                if (keyType.IsEnum)
                {
                    throw new NotSupportedException(
                              $"Schema cannot be generated for type {underlyingType} as it's not supported by the System.Text.Json serializer");
                }

                return(new DataContract(
                           dataType: DataType.Object,
                           underlyingType: underlyingType,
                           additionalPropertiesType: valueType));
            }

            if (underlyingType.IsEnumerable(out Type itemType))
            {
                return(new DataContract(
                           dataType: DataType.Array,
                           underlyingType: underlyingType,
                           arrayItemType: itemType));
            }

            return(new DataContract(
                       dataType: DataType.Object,
                       underlyingType: underlyingType,
                       properties: GetDataPropertiesFor(underlyingType, out Type extensionDataValueType),
                       additionalPropertiesType: extensionDataValueType));
        }
コード例 #2
0
        public DataContract GetDataContractForType(Type type)
        {
            if (type.IsOneOf(typeof(object), typeof(JsonDocument), typeof(JsonElement)))
            {
                return(DataContract.ForDynamic(underlyingType: type));
            }

            if (PrimitiveTypesAndFormats.ContainsKey(type))
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats[type];

                return(DataContract.ForPrimitive(
                           underlyingType: type,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (type.IsEnum)
            {
                var enumValues = type.GetEnumValues();

                //Test to determine if the serializer will treat as string
                var serializeAsString = (enumValues.Length > 0) && Serialize(enumValues.GetValue(0)).StartsWith("\"");

                var primitiveTypeAndFormat = serializeAsString
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[type.GetEnumUnderlyingType()];

                return(DataContract.ForPrimitive(
                           underlyingType: type,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (IsSupportedDictionary(type, out Type keyType, out Type valueType))
            {
                return(DataContract.ForDictionary(
                           underlyingType: type,
                           keyType: keyType,
                           valueType: valueType));
            }

            if (IsSupportedCollection(type, out Type itemType))
            {
                return(DataContract.ForArray(
                           underlyingType: type,
                           itemType: itemType));
            }

            return(DataContract.ForObject(
                       underlyingType: type,
                       properties: GetDataPropertiesFor(type, out Type extensionDataType),
                       extensionDataType: extensionDataType));
        }
        public DataContract GetDataContractForType(Type type)
        {
            if (type.IsOneOf(typeof(JsonDocument), typeof(JsonElement)))
            {
                return(DataContract.ForDynamic(underlyingType: type));
            }

            if (PrimitiveTypesAndFormats.ContainsKey(type))
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats[type];

                return(DataContract.ForPrimitive(
                           underlyingType: type,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (type.IsEnum)
            {
                var enumValues = GetSerializedEnumValuesFor(type);

                var primitiveTypeAndFormat = (enumValues.Any(value => value is string))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[type.GetEnumUnderlyingType()];

                return(DataContract.ForPrimitive(
                           underlyingType: type,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2,
                           enumValues: enumValues));
            }

            if (IsSupportedDictionary(type, out Type keyType, out Type valueType))
            {
                return(DataContract.ForDictionary(
                           underlyingType: type,
                           valueType: valueType));
            }

            if (IsSupportedCollection(type, out Type itemType))
            {
                return(DataContract.ForArray(
                           underlyingType: type,
                           itemType: itemType));
            }

            return(DataContract.ForObject(
                       underlyingType: type,
                       properties: GetDataPropertiesFor(type, out Type extensionDataType),
                       extensionDataType: extensionDataType));
        }
        public SerializerContract GetSerializerContractForType(Type type)
        {
            var underlyingType = type.IsNullable(out Type innerType) ? innerType : type;

            if (PrimitiveTypesAndFormats.ContainsKey(underlyingType))
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats[underlyingType];
                return(SerializerContract.ForPrimitive(underlyingType, primitiveTypeAndFormat.Item1, primitiveTypeAndFormat.Item2));
            }

            if (underlyingType.IsEnum)
            {
                var enumValues = GetSerializeEnumValuesFor(underlyingType);

                var primitiveTypeAndFormat = (enumValues.Any(value => value.GetType() == typeof(string)))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[underlyingType.GetEnumUnderlyingType()];

                return(SerializerContract.ForPrimitive(underlyingType, primitiveTypeAndFormat.Item1, primitiveTypeAndFormat.Item2, enumValues));
            }

            if (underlyingType.IsDictionary(out Type keyType, out Type valueType))
            {
                return(SerializerContract.ForDictionary(underlyingType, keyType, valueType));
            }

            if (underlyingType.IsEnumerable(out Type itemType))
            {
                return(SerializerContract.ForArray(underlyingType, itemType));
            }

            return(SerializerContract.ForObject(
                       underlyingType,
                       GetSerializerPropertiesFor(underlyingType, out Type extensionDataValueType),
                       extensionDataValueType));
        }
コード例 #5
0
        public DataContract GetDataContractForType(Type type)
        {
            if (type.IsOneOf(typeof(object), typeof(JToken), typeof(JObject), typeof(JArray)))
            {
                return(DataContract.ForDynamic(underlyingType: type));
            }

            var jsonContract = _contractResolver.ResolveContract(type);

            if (jsonContract is JsonPrimitiveContract && !jsonContract.UnderlyingType.IsEnum)
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats.ContainsKey(jsonContract.UnderlyingType)
                    ? PrimitiveTypesAndFormats[jsonContract.UnderlyingType]
                    : Tuple.Create(DataType.String, (string)null);

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (jsonContract is JsonPrimitiveContract && jsonContract.UnderlyingType.IsEnum)
            {
                var enumValues = GetSerializedEnumValuesFor(jsonContract);

                var primitiveTypeAndFormat = (enumValues.Values.Any(value => value is string))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[jsonContract.UnderlyingType.GetEnumUnderlyingType()];

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (jsonContract is JsonArrayContract jsonArrayContract)
            {
                return(DataContract.ForArray(
                           underlyingType: jsonArrayContract.UnderlyingType,
                           itemType: jsonArrayContract.CollectionItemType ?? typeof(object)));
            }

            if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
            {
                var keyType   = jsonDictionaryContract.DictionaryKeyType ?? typeof(object);
                var valueType = jsonDictionaryContract.DictionaryValueType ?? typeof(object);

                IEnumerable <string> keys = null;

                if (keyType.IsEnum)
                {
                    // This is a special case where we know the possible key values
                    var enumValues = GetSerializedEnumValuesFor(_contractResolver.ResolveContract(keyType));

                    keys = enumValues.Values.Any(value => value is string)
                        ? enumValues.Cast <string>()
                        : keyType.GetEnumNames();
                }

                return(DataContract.ForDictionary(
                           underlyingType: jsonDictionaryContract.UnderlyingType,
                           keyType: keyType,
                           valueType: valueType));
            }

            if (jsonContract is JsonObjectContract jsonObjectContract)
            {
                string typeNameProperty = null;
                string typeNameValue    = null;

                if (_serializerSettings.TypeNameHandling == TypeNameHandling.Objects ||
                    _serializerSettings.TypeNameHandling == TypeNameHandling.All ||
                    _serializerSettings.TypeNameHandling == TypeNameHandling.Auto)
                {
                    typeNameProperty = "$type";

                    typeNameValue = (_serializerSettings.TypeNameAssemblyFormatHandling == TypeNameAssemblyFormatHandling.Full)
                        ? jsonObjectContract.UnderlyingType.AssemblyQualifiedName
                        : $"{jsonObjectContract.UnderlyingType.FullName}, {jsonObjectContract.UnderlyingType.Assembly.GetName().Name}";
                }

                return(DataContract.ForObject(
                           underlyingType: jsonObjectContract.UnderlyingType,
                           properties: GetDataPropertiesFor(jsonObjectContract, out Type extensionDataType),
                           extensionDataType: extensionDataType,
                           typeNameProperty: typeNameProperty,
                           typeNameValue: typeNameValue));
            }

            return(DataContract.ForDynamic(underlyingType: type));
        }
コード例 #6
0
        public DataContract GetDataContractForType(Type type)
        {
            var jsonContract = _contractResolver.ResolveContract(type.IsNullable(out Type innerType) ? innerType : type);

            if (jsonContract is JsonPrimitiveContract && !jsonContract.UnderlyingType.IsEnum)
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats.ContainsKey(jsonContract.UnderlyingType)
                    ? PrimitiveTypesAndFormats[jsonContract.UnderlyingType]
                    : Tuple.Create(DataType.String, (string)null);

                return(new DataContract(
                           dataType: primitiveTypeAndFormat.Item1,
                           format: primitiveTypeAndFormat.Item2,
                           underlyingType: jsonContract.UnderlyingType));
            }

            if (jsonContract is JsonPrimitiveContract && jsonContract.UnderlyingType.IsEnum)
            {
                var enumValues = GetSerializedEnumValuesFor(jsonContract);

                var primitiveTypeAndFormat = (enumValues.Any(value => value.GetType() == typeof(string)))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[jsonContract.UnderlyingType.GetEnumUnderlyingType()];

                return(new DataContract(
                           dataType: primitiveTypeAndFormat.Item1,
                           format: primitiveTypeAndFormat.Item2,
                           underlyingType: jsonContract.UnderlyingType,
                           enumValues: enumValues));
            }

            if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
            {
                var keyType   = jsonDictionaryContract.DictionaryKeyType ?? typeof(object);
                var valueType = jsonDictionaryContract.DictionaryValueType ?? typeof(object);

                if (keyType.IsEnum)
                {
                    // This is a special case where we can include named properties based on the enum values
                    var enumValues = GetDataContractForType(keyType).EnumValues;

                    var propertyNames = enumValues.Any(value => value is string)
                        ? enumValues.Cast <string>()
                        : keyType.GetEnumNames();

                    return(new DataContract(
                               dataType: DataType.Object,
                               underlyingType: jsonDictionaryContract.UnderlyingType,
                               properties: propertyNames.Select(name => new DataProperty(name, valueType))));
                }

                return(new DataContract(
                           dataType: DataType.Object,
                           underlyingType: jsonDictionaryContract.UnderlyingType,
                           additionalPropertiesType: valueType));
            }

            if (jsonContract is JsonArrayContract jsonArrayContract)
            {
                return(new DataContract(
                           dataType: DataType.Array,
                           underlyingType: jsonArrayContract.UnderlyingType,
                           arrayItemType: jsonArrayContract.CollectionItemType ?? typeof(object)));
            }

            if (jsonContract is JsonObjectContract jsonObjectContract)
            {
                return(new DataContract(
                           dataType: DataType.Object,
                           underlyingType: jsonObjectContract.UnderlyingType,
                           properties: GetDataPropertiesFor(jsonObjectContract),
                           additionalPropertiesType: jsonObjectContract.ExtensionDataValueType));
            }

            if (jsonContract.UnderlyingType == typeof(JArray))
            {
                return(new DataContract(
                           dataType: DataType.Array,
                           underlyingType: jsonContract.UnderlyingType,
                           arrayItemType: typeof(JToken)));
            }

            if (jsonContract.UnderlyingType == typeof(JObject))
            {
                return(new DataContract(
                           dataType: DataType.Object,
                           underlyingType: jsonContract.UnderlyingType));
            }

            return(new DataContract(
                       dataType: DataType.Unknown,
                       underlyingType: jsonContract.UnderlyingType));
        }
        public DataContract GetDataContractForType(Type type)
        {
            if (type.IsAssignableTo(typeof(JToken)))
            {
                return(DataContract.ForDynamic(underlyingType: type));
            }

            var jsonContract = _contractResolver.ResolveContract(type);

            if (jsonContract is JsonPrimitiveContract && !jsonContract.UnderlyingType.IsEnum)
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats.ContainsKey(jsonContract.UnderlyingType)
                    ? PrimitiveTypesAndFormats[jsonContract.UnderlyingType]
                    : Tuple.Create(DataType.String, (string)null);

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2));
            }

            if (jsonContract is JsonPrimitiveContract && jsonContract.UnderlyingType.IsEnum)
            {
                var enumValues = GetSerializedEnumValuesFor(jsonContract);

                var primitiveTypeAndFormat = (enumValues.Any(value => value.GetType() == typeof(string)))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[jsonContract.UnderlyingType.GetEnumUnderlyingType()];

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2,
                           enumValues: enumValues));
            }

            if (jsonContract is JsonArrayContract jsonArrayContract)
            {
                return(DataContract.ForArray(
                           underlyingType: jsonArrayContract.UnderlyingType,
                           itemType: jsonArrayContract.CollectionItemType ?? typeof(object)));
            }

            if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
            {
                var keyType   = jsonDictionaryContract.DictionaryKeyType ?? typeof(object);
                var valueType = jsonDictionaryContract.DictionaryValueType ?? typeof(object);

                IEnumerable <string> keys = null;

                if (keyType.IsEnum)
                {
                    // This is a special case where we know the possible key values
                    var enumValues = GetSerializedEnumValuesFor(_contractResolver.ResolveContract(keyType));

                    keys = enumValues.Any(value => value is string)
                        ? enumValues.Cast <string>()
                        : keyType.GetEnumNames();
                }

                return(DataContract.ForDictionary(
                           underlyingType: jsonDictionaryContract.UnderlyingType,
                           valueType: valueType,
                           keys: keys));
            }

            if (jsonContract is JsonObjectContract jsonObjectContract)
            {
                return(DataContract.ForObject(
                           underlyingType: jsonObjectContract.UnderlyingType,
                           properties: GetDataPropertiesFor(jsonObjectContract),
                           extensionDataType: jsonObjectContract.ExtensionDataValueType));
            }

            return(DataContract.ForDynamic(underlyingType: type));
        }
コード例 #8
0
        public DataContract GetDataContractForType(Type type)
        {
            if (type.IsOneOf(typeof(object), typeof(JToken), typeof(JObject), typeof(JArray)))
            {
                return(DataContract.ForDynamic(
                           underlyingType: type,
                           jsonConverter: JsonConverterFunc));
            }

            var jsonContract = _contractResolver.ResolveContract(type);

            if (jsonContract is JsonPrimitiveContract && !jsonContract.UnderlyingType.IsEnum)
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats.ContainsKey(jsonContract.UnderlyingType)
                    ? PrimitiveTypesAndFormats[jsonContract.UnderlyingType]
                    : Tuple.Create(DataType.String, (string)null);

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2,
                           jsonConverter: JsonConverterFunc));
            }

            if (jsonContract is JsonPrimitiveContract && jsonContract.UnderlyingType.IsEnum)
            {
                var enumValues = jsonContract.UnderlyingType.GetEnumValues();

                //Test to determine if the serializer will treat as string
                var serializeAsString = (enumValues.Length > 0) &&
                                        JsonConverterFunc(enumValues.GetValue(0)).StartsWith("\"");

                var primitiveTypeAndFormat = serializeAsString
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[jsonContract.UnderlyingType.GetEnumUnderlyingType()];

                return(DataContract.ForPrimitive(
                           underlyingType: jsonContract.UnderlyingType,
                           dataType: primitiveTypeAndFormat.Item1,
                           dataFormat: primitiveTypeAndFormat.Item2,
                           jsonConverter: JsonConverterFunc));
            }

            if (jsonContract is JsonArrayContract jsonArrayContract)
            {
                return(DataContract.ForArray(
                           underlyingType: jsonArrayContract.UnderlyingType,
                           itemType: jsonArrayContract.CollectionItemType ?? typeof(object),
                           jsonConverter: JsonConverterFunc));
            }

            if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
            {
                var keyType   = jsonDictionaryContract.DictionaryKeyType ?? typeof(object);
                var valueType = jsonDictionaryContract.DictionaryValueType ?? typeof(object);

                IEnumerable <string> keys = null;

                if (keyType.IsEnum)
                {
                    // This is a special case where we know the possible key values
                    var enumValuesAsJson = keyType.GetEnumValues()
                                           .Cast <object>()
                                           .Select(value => JsonConverterFunc(value));

                    keys = enumValuesAsJson.Any(json => json.StartsWith("\""))
                        ? enumValuesAsJson.Select(json => json.Replace("\"", string.Empty))
                        : keyType.GetEnumNames();
                }

                return(DataContract.ForDictionary(
                           underlyingType: jsonDictionaryContract.UnderlyingType,
                           valueType: valueType,
                           keys: keys,
                           jsonConverter: JsonConverterFunc));
            }

            if (jsonContract is JsonObjectContract jsonObjectContract)
            {
                string typeNameProperty = null;
                string typeNameValue    = null;

                if (_serializerSettings.TypeNameHandling == TypeNameHandling.Objects ||
                    _serializerSettings.TypeNameHandling == TypeNameHandling.All ||
                    _serializerSettings.TypeNameHandling == TypeNameHandling.Auto)
                {
                    typeNameProperty = "$type";

                    typeNameValue = (_serializerSettings.TypeNameAssemblyFormatHandling == TypeNameAssemblyFormatHandling.Full)
                        ? jsonObjectContract.UnderlyingType.AssemblyQualifiedName
                        : $"{jsonObjectContract.UnderlyingType.FullName}, {jsonObjectContract.UnderlyingType.Assembly.GetName().Name}";
                }

                return(DataContract.ForObject(
                           underlyingType: jsonObjectContract.UnderlyingType,
                           properties: GetDataPropertiesFor(jsonObjectContract, out Type extensionDataType),
                           extensionDataType: extensionDataType,
                           typeNameProperty: typeNameProperty,
                           typeNameValue: typeNameValue,
                           jsonConverter: JsonConverterFunc));
            }

            return(DataContract.ForDynamic(
                       underlyingType: type,
                       jsonConverter: JsonConverterFunc));
        }
コード例 #9
0
        public SerializerMetadata GetSerializerMetadataForType(Type type)
        {
            var jsonContract = _contractResolver.ResolveContract(type.IsNullable(out Type innerType) ? innerType : type);

            if (jsonContract is JsonPrimitiveContract && !jsonContract.UnderlyingType.IsEnum)
            {
                var primitiveTypeAndFormat = PrimitiveTypesAndFormats.ContainsKey(jsonContract.UnderlyingType)
                    ? PrimitiveTypesAndFormats[jsonContract.UnderlyingType]
                    : Tuple.Create("string", (string)null);

                return(SerializerMetadata.ForPrimitive(jsonContract.UnderlyingType, primitiveTypeAndFormat.Item1, primitiveTypeAndFormat.Item2));
            }

            if (jsonContract is JsonPrimitiveContract && jsonContract.UnderlyingType.IsEnum)
            {
                var enumValues = GetSerializerEnumValuesFor(jsonContract);

                var primitiveTypeAndFormat = (enumValues.Any(value => value.GetType() == typeof(string)))
                    ? PrimitiveTypesAndFormats[typeof(string)]
                    : PrimitiveTypesAndFormats[jsonContract.UnderlyingType.GetEnumUnderlyingType()];

                return(SerializerMetadata.ForPrimitive(jsonContract.UnderlyingType, primitiveTypeAndFormat.Item1, primitiveTypeAndFormat.Item2, enumValues));
            }

            if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
            {
                var keyType   = jsonDictionaryContract.DictionaryKeyType ?? typeof(object);
                var valueType = jsonDictionaryContract.DictionaryValueType ?? typeof(object);

                return(SerializerMetadata.ForDictionary(jsonDictionaryContract.UnderlyingType, keyType, valueType));
            }

            if (jsonContract is JsonArrayContract jsonArrayContract)
            {
                var itemType = jsonArrayContract.CollectionItemType ?? typeof(object);
                return(SerializerMetadata.ForArray(jsonArrayContract.UnderlyingType, itemType));
            }

            if (jsonContract is JsonObjectContract jsonObjectContract)
            {
                return(SerializerMetadata.ForObject(
                           jsonContract.UnderlyingType,
                           GetSerializerPropertiesFor(jsonObjectContract),
                           jsonObjectContract.ExtensionDataValueType));
            }

            if (jsonContract is JsonLinqContract jsonLinqContract)
            {
                if (jsonLinqContract.UnderlyingType == typeof(JArray))
                {
                    return(SerializerMetadata.ForArray(typeof(JArray), typeof(JToken)));
                }

                if (jsonLinqContract.UnderlyingType == typeof(JObject))
                {
                    return(SerializerMetadata.ForObject(typeof(JObject)));
                }
            }

            return(SerializerMetadata.ForDynamic(jsonContract.UnderlyingType));
        }