protected static void FixProperty <T>(Dictionary <string, OpenApiSchema> schemas, NamingStrategy namingStrategy, string propertyName, Func <OpenApiSchema, NamingStrategy, OpenApiSchema> schemaSelector, Func <OpenApiSchema, OpenApiSchema> fix) { var t = typeof(T); var rootSchema = schemas[t.Name]; var schema = schemaSelector(rootSchema, namingStrategy); var property = schema.Properties[namingStrategy.GetPropertyName(propertyName, false)]; schema.Properties[namingStrategy.GetPropertyName(propertyName, false)] = fix(property); }
/// <inheritdoc /> public override void Visit(IAcceptor acceptor, KeyValuePair <string, Type> type, NamingStrategy namingStrategy, params Attribute[] attributes) { var title = type.Value.IsGenericType ? namingStrategy.GetPropertyName(type.Value.Name.Split('`').First(), hasSpecifiedName: false) + "_" + string.Join("_", type.Value.GenericTypeArguments.Select(a => namingStrategy.GetPropertyName(a.Name, false))) : namingStrategy.GetPropertyName(type.Value.Name, hasSpecifiedName: false); this.Visit(acceptor, name: type.Key, title: title, dataType: "object", dataFormat: null, attributes: attributes); }
private static List <Error> FromModelState(ModelStateDictionary modelState, Type resourceType, bool includeExceptionStackTraceInErrors, NamingStrategy namingStrategy) { List <Error> errors = new List <Error>(); foreach (var pair in modelState.Where(x => x.Value.Errors.Any())) { var propertyName = pair.Key; PropertyInfo property = resourceType.GetProperty(propertyName); string attributeName = property.GetCustomAttribute <AttrAttribute>().PublicName ?? namingStrategy.GetPropertyName(property.Name, false); foreach (var modelError in pair.Value.Errors) { if (modelError.Exception is JsonApiException jsonApiException) { errors.Add(jsonApiException.Error); } else { errors.Add(FromModelError(modelError, attributeName, includeExceptionStackTraceInErrors)); } } } return(errors); }
/// <summary> /// Constructor, takes the model state and an overall error message. /// </summary> /// <param name="modelState">The model state.</param> /// <param name="message">An error message that applies to the entire result.</param> /// <param name="namingStrategy">The naming strategy to use. Can be null, which makes no changes.</param> public ModelStateErrorResult(ModelStateDictionary modelState, String message, NamingStrategy namingStrategy) : base(message) { var keySb = new StringBuilder(); var errorSb = new StringBuilder(); this.Errors = new Dictionary <String, String>(modelState.ErrorCount); foreach (var item in modelState) { if (item.Value.ValidationState == ModelValidationState.Invalid) { errorSb.Clear(); foreach (var error in item.Value.Errors) { errorSb.AppendLine(error.ErrorMessage); } var key = item.Key; if (namingStrategy != null && key.Contains('.')) { keySb.Clear(); var keyParts = key.Split('.'); foreach (var keyPart in keyParts) { keySb.Append(namingStrategy.GetPropertyName(keyPart, false)); keySb.Append('.'); } key = keySb.ToString(0, keySb.Length - 1); } this.Errors[key] = errorSb.ToString(); } } }
protected override IList <JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization) { IList <JsonProperty> baseProps = base.CreateProperties(type, memberSerialization); if (typeof(IDataset).IsAssignableFrom(type)) { string countName = nameof(ICollection.Count); if (NamingStrategy != null) { countName = NamingStrategy.GetPropertyName(countName, false); } foreach (var prop in baseProps) { if (prop.PropertyName == countName && prop.DeclaringType.IsGenericType && prop.DeclaringType.GetGenericTypeDefinition() == typeof(Collection <>)) { prop.Ignored = true; break; } } } return(baseProps); }
protected async Task WriteJsonAsync(JsonTextWriter writer, ISelection selection, IExpressionTree fields) { var countField = fields.Children.FirstOrDefault(c => c.Node.Name == nameof(ISelection.Count) && typeof(ISelection).IsAssignableFrom(c.Node.ToLambdaExpression().Parameters[0].Type)); var normalFields = new ExpressionTree { Node = fields.Node, Children = fields.Children.Where(c => c != countField).ToList() }; await writer.WriteStartObjectAsync(); if (countField == null || normalFields.Children.Count != 0) { var items = selection.GetItems(); await WriteKvpAsync(writer, NamingStrategy.GetPropertyName("items", false), items, normalFields, null); } if (countField != null) { await SerializePropertyAsync(writer, selection, countField); } await writer.WriteEndObjectAsync(); }
/// <inheritdoc /> protected override string ResolvePropertyName(string propertyName) { if (NamingStrategy != null) { return(NamingStrategy.GetPropertyName(propertyName, false)); } return(propertyName.ToLowerInvariant()); }
/// <inheritdoc /> public override void Visit(IAcceptor acceptor, KeyValuePair <string, Type> type, NamingStrategy namingStrategy, params Attribute[] attributes) { var title = type.Value.IsGenericType ? namingStrategy.GetPropertyName(type.Value.Name.Split('`').First(), hasSpecifiedName: false) + "_" + string.Join("_", type.Value.GenericTypeArguments.Select(a => namingStrategy.GetPropertyName(a.Name, false))) : namingStrategy.GetPropertyName(type.Value.Name, hasSpecifiedName: false); var name = this.Visit(acceptor, name: type.Key, title: title, dataType: "object", dataFormat: null, attributes: attributes); if (name.IsNullOrWhiteSpace()) { return; } if (!this.IsNavigatable(type.Value)) { return; } var instance = acceptor as OpenApiSchemaAcceptor; if (instance.IsNullOrDefault()) { return; } // Processes properties. var properties = type.Value .GetProperties(BindingFlags.Public | BindingFlags.Instance) .Where(p => !p.ExistsCustomAttribute <JsonIgnoreAttribute>()) .ToDictionary(p => p.GetJsonPropertyName(namingStrategy), p => p); this.ProcessProperties(instance, name, properties, namingStrategy); // Adds the reference. var reference = new OpenApiReference() { Type = ReferenceType.Schema, Id = type.Value.GetOpenApiReferenceId(isDictionary: false, isList: false, namingStrategy) }; instance.Schemas[name].Reference = reference; instance.Schemas[name].Example = this.GetExample(type.Value, namingStrategy); }
private string _FormatText(string text) { if (text == null) { return(null); } return(NamingStrategy == null ? text : NamingStrategy.GetPropertyName(text, false)); }
public CompactSchemaGenerator(JsonSerializer jsonSerializer, MetadataJsonSerializationOptions metadataJsonSerializationOptions) { _jsonSerializer = jsonSerializer; _metadataJsonSerializationOptions = metadataJsonSerializationOptions; NamingStrategy namingStrategy = (_jsonSerializer.ContractResolver as DefaultContractResolver)?.NamingStrategy ?? new DefaultNamingStrategy(); GetJsonPropertyName = (name) => namingStrategy.GetPropertyName(name, false); }
private static void WriteAdjustedName(JsonWriter writer, NamingStrategy namingStrategy, string name) { if (namingStrategy != null) { name = namingStrategy.GetPropertyName(name, false); } writer.WritePropertyName(name); }
private void WriteExecutionNode(JsonWriter writer, ExecutionNode node, JsonSerializer serializer) { if (node is ValueExecutionNode valueExecutionNode) { serializer.Serialize(writer, valueExecutionNode.ToValue()); } else if (node is ObjectExecutionNode objectExecutionNode) { if (objectExecutionNode.SubFields == null) { writer.WriteNull(); } else { writer.WriteStartObject(); foreach (var childNode in objectExecutionNode.SubFields) { var propName = childNode.Name; if (_namingStrategy != null) { propName = _namingStrategy.GetPropertyName(propName, false); } writer.WritePropertyName(propName); WriteExecutionNode(writer, childNode, serializer); } writer.WriteEndObject(); } } else if (node is ArrayExecutionNode arrayExecutionNode) { var items = arrayExecutionNode.Items; if (items == null) { writer.WriteNull(); } else { writer.WriteStartArray(); foreach (var childNode in items) { WriteExecutionNode(writer, childNode, serializer); } writer.WriteEndArray(); } } else if (node == null || node is NullExecutionNode) { writer.WriteNull(); } else { serializer.Serialize(writer, node.ToValue()); } }
private static string GetJsonPropertyName(MemberInfo propertyInfo, NamingStrategy namingStrategy = null) { var propertyName = propertyInfo.Name; var attribute = propertyInfo.GetCustomAttribute <JsonPropertyAttribute>(); if (attribute != null) { return(attribute.PropertyName); } return(namingStrategy == null ? propertyName : namingStrategy.GetPropertyName(propertyName, false)); }
/// <summary> /// Converts the given <see cref="Type"/> instance to the list of underlying enum name. /// </summary> /// <param name="type"><see cref="Type"/> instance.</param> /// <param name="namingStrategy"><see cref="NamingStrategy"/> instance.</param> /// <returns>Returns the list of underlying enum name.</returns> public static List <IOpenApiAny> ToOpenApiStringCollection(this Type type, NamingStrategy namingStrategy) { if (!type.IsUnflaggedEnumType()) { return(null); } var names = Enum.GetNames(type); return(names.Select(p => (IOpenApiAny) new OpenApiString(namingStrategy.GetPropertyName(p, false))) .ToList()); }
private static string GetDisplayNameForProperty(string propertyName, Type resourceType, NamingStrategy namingStrategy) { PropertyInfo property = resourceType.GetProperty(propertyName); if (property != null) { var attrAttribute = property.GetCustomAttribute <AttrAttribute>(); return(attrAttribute?.PublicName ?? namingStrategy.GetPropertyName(property.Name, false)); } return(propertyName); }
protected override string ResolvePropertyName(string propertyName) { string resolvedName = null; //This will try to relove based on above mentioned mapping bool doesCustomPropertyNameExists = _propertyMappings.TryGetValue(propertyName, out resolvedName); //if custom mapping exists in the list above, return that if (doesCustomPropertyNameExists) { return(resolvedName); } //else use the Camel Casing return(_camelCaseNamingStrategy.GetPropertyName(propertyName, false)); }
public void CreateValidationMetadata_SetValidationPropertyName_WithJsonNamingPolicy(NamingStrategy namingStrategy) { var metadataProvider = new NewtonsoftJsonValidationMetadataProvider(namingStrategy); var propertyName = nameof(SampleTestClass.NoAttributesProperty); var key = ModelMetadataIdentity.ForProperty(typeof(SampleTestClass).GetProperty(propertyName), typeof(int), typeof(SampleTestClass)); var modelAttributes = new ModelAttributes(Array.Empty <object>(), Array.Empty <object>(), Array.Empty <object>()); var context = new ValidationMetadataProviderContext(key, modelAttributes); // Act metadataProvider.CreateValidationMetadata(context); // Assert Assert.NotNull(context.ValidationMetadata.ValidationModelName); Assert.Equal(namingStrategy.GetPropertyName(propertyName, false), context.ValidationMetadata.ValidationModelName); }
public override void WriteJson(JsonWriter jsonWriter, object value, JsonSerializer jsonSerializer) { PSObject psObj = (PSObject)value; jsonWriter.WriteStartObject(); DefaultContractResolver contractResolver = (DefaultContractResolver)jsonSerializer.ContractResolver; NamingStrategy namingStrategy = (contractResolver == null ? null : contractResolver.NamingStrategy) ?? new DefaultNamingStrategy(); psObj.Properties.Where(p => p.IsGettable).ToList().ForEach(p => { jsonWriter.WritePropertyName(namingStrategy.GetPropertyName(p.Name, false)); jsonSerializer.Serialize(jsonWriter, p.Value); } ); jsonWriter.WriteEndObject(); }
protected override IList <JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization) { var list = base.CreateProperties(type, memberSerialization); if (!_namespaces.Any(x => type.Namespace.StartsWith(x))) { return(list); } foreach (var prop in list) { prop.PropertyName = NamingStrategy.GetPropertyName(prop.UnderlyingName, false); } return(list); }
/// <summary> /// Gets the publicly visible resource name from the internal type name. /// </summary> public string FormatResourceName(Type type) { try { // check the class definition first // [Resource("models"] public class Model : Identifiable { /* ... */ } if (type.GetCustomAttribute(typeof(ResourceAttribute)) is ResourceAttribute attribute) { return(attribute.ResourceName); } return(_namingStrategy.GetPropertyName(type.Name.Pluralize(), false)); } catch (InvalidOperationException exception) { throw new InvalidOperationException($"Cannot define multiple {nameof(ResourceAttribute)}s on type '{type}'.", exception); } }
private static Schema GetOrRegistrySchema(Type type, HttpMethod method, NamingStrategy namingStrategy) { lock (Caches) { if (Caches.ContainsKey(type) && Caches[type].ContainsKey(method)) { return(Caches[type][method]); } if (!Caches.ContainsKey(type)) { Caches[type] = new Dictionary <HttpMethod, Schema>(); } var o = Activator.CreateInstance(type); var stringify = JsonConvert.SerializeObject(o); var expected = JObject.Parse(stringify); var result = new Schema { Properties = new ConcurrentDictionary <string, Schema>() }; foreach (var propertyName in expected.Properties()) { var name = propertyName.Name; name = namingStrategy?.GetPropertyName(name, false); var property = type.GetProperty(propertyName.Name); if (property == null) { continue; } var propertySchema = BuildSchema(property, method, namingStrategy); if (propertySchema != null) { result.Properties.Add(name, propertySchema); } } Caches[type][method] = result; return(result); } }
public static string Generate(Type type) { var name = NameForType(type); if (type.IsGenericType) { // generic type names look like this // List`1 // we need to strip off the arity "`n" and replace it with the names of the type arguments // e.g. listOfFoo name = WithoutArity(name); var genericTypeArgNames = type.GetGenericArguments().Select(NameForType); name = name + "Of" + string.Join("And", genericTypeArgNames); } // strip any invalid characters from generated names name = Regex.Replace(name, ComponentFieldName.InvalidRegex, string.Empty); // and lastly, camelCase the name name = CamelCase.GetPropertyName(name, false); return(name); }
private void ProcessProperties(IOpenApiSchemaAcceptor instance, string schemaName, Dictionary <string, PropertyInfo> properties, NamingStrategy namingStrategy) { var schemas = new Dictionary <string, OpenApiSchema>(); var subAcceptor = new OpenApiSchemaAcceptor() { Properties = properties, RootSchemas = instance.RootSchemas, Schemas = schemas, }; subAcceptor.Accept(this.VisitorCollection, namingStrategy); // Add required properties to schema. var jsonPropertyAttributes = properties.Where(p => !p.Value.GetCustomAttribute <JsonPropertyAttribute>(inherit: false).IsNullOrDefault()) .Select(p => new KeyValuePair <string, JsonPropertyAttribute>(p.Key, p.Value.GetCustomAttribute <JsonPropertyAttribute>(inherit: false))) .Where(p => p.Value.Required == Required.Always || p.Value.Required == Required.DisallowNull); foreach (var attribute in jsonPropertyAttributes) { instance.Schemas[schemaName].Required.Add(attribute.Key); } var jsonRequiredAttributes = properties.Where(p => !p.Value.GetCustomAttribute <JsonRequiredAttribute>(inherit: false).IsNullOrDefault()) .Select(p => new KeyValuePair <string, JsonRequiredAttribute>(p.Key, p.Value.GetCustomAttribute <JsonRequiredAttribute>(inherit: false))); foreach (var attribute in jsonRequiredAttributes) { var attributeName = namingStrategy.GetPropertyName(attribute.Key, hasSpecifiedName: false); if (instance.Schemas[schemaName].Required.Contains(attributeName)) { continue; } instance.Schemas[schemaName].Required.Add(attributeName); } instance.Schemas[schemaName].Properties = subAcceptor.Schemas; // Adds schemas to the root. var schemasToBeAdded = subAcceptor.Schemas .Where(p => !instance.Schemas.Keys.Contains(p.Key)) .Where(p => p.Value.IsOpenApiSchemaObject()) .GroupBy(p => p.Value.Title) .Select(p => p.First()) .ToDictionary(p => p.Value.Title, p => p.Value); foreach (var schema in schemasToBeAdded.Where(p => p.Key != "jObject" && p.Key != "jToken")) { if (instance.RootSchemas.ContainsKey(schema.Key)) { continue; } instance.RootSchemas.Add(schema.Key, schema.Value); } // Removes title of each property. var subSchemas = instance.Schemas[schemaName].Properties; subSchemas = subSchemas.Select(p => { p.Value.Title = null; return(new KeyValuePair <string, OpenApiSchema>(p.Key, p.Value)); }) .ToDictionary(p => p.Key, p => p.Value); instance.Schemas[schemaName].Properties = subSchemas; }
public void ConfigureServices(IServiceCollection services) { // configuration services.AddSingleton(_configuration) // root .AddHostedService <ConfigurationReloader>(); // kestrel services.Configure <ServerOptions>(_configuration.GetSection("Server")) .Configure <KestrelServerOptions>(o => { var server = o.ApplicationServices.GetService <IOptionsMonitor <ServerOptions> >().CurrentValue; if (server.HttpPortDev != null) { o.ListenLocalhost(server.HttpPortDev.Value); } if (server.HttpPort != null) { o.ListenAnyIP(server.HttpPort.Value); } if (server.HttpsPort != null && server.CertificatePath != null) { o.ListenAnyIP(server.HttpsPort.Value, l => l.UseHttps(server.CertificatePath, server.CertificatePassword)); } o.Limits.MaxRequestBufferSize = 1024 * 64; // 16 KiB o.Limits.MaxRequestLineSize = 1024 * 8; // 8 KiB o.Limits.MaxRequestHeadersTotalSize = 1024 * 8; // 8 KiB o.Limits.MaxRequestBodySize = 1024 * 256; // 16 KiB }) .AddResponseCompression(o => { o.Providers.Add <GzipCompressionProvider>(); o.Providers.Add <BrotliCompressionProvider>(); }) .AddResponseCaching(o => { o.UseCaseSensitivePaths = false; // this is for static files o.SizeLimit = long.MaxValue; o.MaximumBodySize = long.MaxValue; }); // mvc services.AddMvcCore(m => { m.Filters.Add <PrimitiveResponseWrapperFilter>(); m.Filters.Add <RequestValidateQueryFilter>(); m.OutputFormatters.RemoveType <StringOutputFormatter>(); // model sanitizing binder var modelBinder = new ModelSanitizerModelBinderProvider(m.ModelBinderProviders); m.ModelBinderProviders.Clear(); m.ModelBinderProviders.Add(modelBinder); }) .AddNewtonsoftJson(o => { o.SerializerSettings.ContractResolver = new DefaultContractResolver { NamingStrategy = ModelNamingStrategy }; o.SerializerSettings.Converters.Add(new StringEnumConverter { NamingStrategy = ModelNamingStrategy, AllowIntegerValues = true }); }) .AddApiExplorer() .AddAuthorization() .AddFormatterMappings() .AddDataAnnotations() .AddCors() .AddTestControllers() .AddControllersAsServices(); services.Configure <ApiBehaviorOptions>(o => { o.SuppressMapClientErrors = true; o.InvalidModelStateResponseFactory = c => { static string fixFieldCasing(string str) => string.Join('.', str.Split('.').Select(s => ModelNamingStrategy.GetPropertyName(s, false))); var problems = c.ModelState .Where(x => !x.Value.IsContainerNode && x.Value.Errors.Count != 0) .Select(x => { var(field, entry) = x; return(new ValidationProblem { Field = ModelNamingStrategy.GetPropertyName(fixFieldCasing(field), false), Messages = entry.Errors.ToArray(e => e.ErrorMessage ?? e.Exception.ToStringWithTrace(null, _environment.IsProduction())) }); }) .ToArray(); return(ResultUtilities.UnprocessableEntity(problems)); };
/// <summary> /// Converts <see cref="Type"/> to <see cref="OpenApiSchema"/>. /// </summary> /// <param name="type"><see cref="Type"/> instance.</param> /// <param name="namingStrategy"><see cref="NamingStrategy"/> insance to create the JSON schema from .NET Types.</param> /// <param name="attribute"><see cref="OpenApiSchemaVisibilityAttribute"/> instance. Default is <c>null</c>.</param> /// <returns><see cref="OpenApiSchema"/> instance.</returns> /// <remarks> /// It runs recursively to build the entire object type. It only takes properties without <see cref="JsonIgnoreAttribute"/>. /// </remarks> public static OpenApiSchema ToOpenApiSchema(this Type type, NamingStrategy namingStrategy, OpenApiSchemaVisibilityAttribute attribute = null) { type.ThrowIfNullOrDefault(); var schema = (OpenApiSchema)null; if (type == typeof(JObject)) { schema = typeof(object).ToOpenApiSchema(namingStrategy); return(schema); } if (type == typeof(JToken)) { schema = typeof(object).ToOpenApiSchema(namingStrategy); return(schema); } var unwrappedValueType = Nullable.GetUnderlyingType(type); if (!unwrappedValueType.IsNullOrDefault()) { schema = unwrappedValueType.ToOpenApiSchema(namingStrategy); schema.Nullable = true; return(schema); } schema = new OpenApiSchema() { Type = type.ToDataType(), Format = type.ToDataFormat() }; if (!attribute.IsNullOrDefault()) { var visibility = new OpenApiString(attribute.Visibility.ToDisplayName()); schema.Extensions.Add("x-ms-visibility", visibility); } if (typeof(Enum).IsAssignableFrom(type)) { var isFlags = type.IsDefined(typeof(FlagsAttribute), false); if (!isFlags) { var converterAttribute = type.GetCustomAttribute <JsonConverterAttribute>(); if (!converterAttribute.IsNullOrDefault() && typeof(StringEnumConverter).IsAssignableFrom(converterAttribute.ConverterType)) { var names = Enum.GetNames(type); schema.Enum = names.Select(p => (IOpenApiAny) new OpenApiString(namingStrategy.GetPropertyName(p, false))).ToList(); schema.Type = "string"; schema.Format = null; } else if (type.GetEnumUnderlyingType() == typeof(short)) { var values = Enum.GetValues(type); schema.Enum = values.Cast <short>().Select(p => (IOpenApiAny) new OpenApiInteger(p)).ToList(); } else if (type.GetEnumUnderlyingType() == typeof(int)) { var values = Enum.GetValues(type); schema.Enum = values.Cast <int>().Select(p => (IOpenApiAny) new OpenApiInteger(p)).ToList(); } else if (type.GetEnumUnderlyingType() == typeof(long)) { var values = Enum.GetValues(type); schema.Enum = values.Cast <long>().Select(p => (IOpenApiAny) new OpenApiLong(p)).ToList(); } } } if (type.IsSimpleType()) { return(schema); } if (typeof(IDictionary).IsAssignableFrom(type)) { schema.AdditionalProperties = type.GetGenericArguments()[1].ToOpenApiSchema(namingStrategy); return(schema); } if (type.IsOpenApiArray()) { schema.Type = "array"; schema.Items = (type.GetElementType() ?? type.GetGenericArguments()[0]).ToOpenApiSchema(namingStrategy); return(schema); } var properties = type.GetProperties().Where(p => !p.ExistsCustomAttribute <JsonIgnoreAttribute>()); foreach (var property in properties) { var visiblity = property.GetCustomAttribute <OpenApiSchemaVisibilityAttribute>(inherit: false); var propertyName = property.GetJsonPropertyName(); schema.Properties[namingStrategy.GetPropertyName(property.Name, false)] = property.PropertyType.ToOpenApiSchema(namingStrategy, visiblity); } return(schema); }
/// <inheritdoc /> public override void Visit(IAcceptor acceptor, KeyValuePair <string, Type> type, NamingStrategy namingStrategy, params Attribute[] attributes) { var title = namingStrategy.GetPropertyName(type.Value.Name, hasSpecifiedName: false); this.Visit(acceptor, name: type.Key, title: title, dataType: "object", dataFormat: null, attributes: attributes); }
/// <summary> /// Gets the publicly visible resource name for the internal type name using the configured naming convention. /// </summary> public string FormatResourceName(Type resourceType) { return(resourceType.GetCustomAttribute(typeof(ResourceAttribute)) is ResourceAttribute attribute ? attribute.PublicName : _namingStrategy.GetPropertyName(resourceType.Name.Pluralize(), false)); }
public override string GetPropertyName(string name, bool hasSpecifiedName) { return(_namingStrategy.GetPropertyName(name, hasSpecifiedName)); }
private static Schema GetOrRegistrySchema(Type type, HttpMethod method, NamingStrategy namingStrategy) { lock (Caches) { if (Caches.ContainsKey(type) && Caches[type].ContainsKey(method)) { return(Caches[type][method]); } if (!Caches.ContainsKey(type)) { Caches[type] = new Dictionary <HttpMethod, Schema>(); } try { if (IsPrimitiveType(type)) { return(BuildSchema(type, method, namingStrategy)); } if (type.IsInterface) { if (type.IsGenericType) { if (type.GetGenericTypeDefinition() == typeof(IPageable <>)) { type = typeof(Pageable <>).MakeGenericType(type.GetGenericArguments()[0]); } if (type.GetGenericTypeDefinition() == typeof(IPage <>)) { type = typeof(Page <>).MakeGenericType(type.GetGenericArguments()[0]); } if (type.GetGenericTypeDefinition() == typeof(IList <>)) { var schema = GetOrRegistrySchema(type.GetGenericArguments()[0], method, namingStrategy); return(new Schema() { Type = "array", Items = schema }); } } } var o = Activator.CreateInstance(type); var stringify = JsonConvert.SerializeObject(o); var expected = JObject.Parse(stringify); var result = new Schema { Properties = new ConcurrentDictionary <string, Schema>() }; foreach (var propertyName in expected.Properties()) { var name = namingStrategy.GetPropertyName(propertyName.Name, false); var property = type.GetProperty(propertyName.Name); if (property == null) { continue; } var propertySchema = BuildSchema(property, method, namingStrategy); if (propertySchema != null) { result.Properties.Add(name, propertySchema); } } Caches[type][method] = result; } catch { // impossible de convertir en schema Caches[type][method] = new Schema() { Type = "object" }; } return(Caches[type][method]); } }
protected virtual string GetKey(object entity, IExpressionTree fields, PropertyExpression property) => NamingStrategy.GetPropertyName(property.Name, false);