private OpenApiSchema GenerateInlineSchema(DataContract dataContract, SchemaRepository schemaRepository) { if (dataContract.DataType == DataType.Unknown) { return(new OpenApiSchema()); } if (dataContract.DataType == DataType.Object) { return(GenerateObjectSchema(dataContract, schemaRepository)); } if (dataContract.DataType == DataType.Array) { return(GenerateArraySchema(dataContract, schemaRepository)); } else { return(GeneratePrimitiveSchema(dataContract)); } }
private OpenApiSchema GenerateSchemaForType(Type type, SchemaRepository schemaRepository) { if (TryGetCustomMapping(type, out var mapping)) { return(mapping()); } if (type.IsAssignableToOneOf(typeof(IFormFile), typeof(FileResult))) { return(new OpenApiSchema { Type = "string", Format = "binary" }); } if (_generatorOptions.GeneratePolymorphicSchemas) { var knownSubTypes = _generatorOptions.SubTypesResolver(type); if (knownSubTypes.Any()) { return(GeneratePolymorphicSchema(knownSubTypes, schemaRepository)); } } var dataContract = _dataContractResolver.GetDataContractForType(type); var shouldBeReferenced = // regular object (dataContract.DataType == DataType.Object && dataContract.Properties != null && !dataContract.UnderlyingType.IsDictionary()) || // dictionary-based AND self-referencing (dataContract.DataType == DataType.Object && dataContract.AdditionalPropertiesType == dataContract.UnderlyingType) || // array-based AND self-referencing (dataContract.DataType == DataType.Array && dataContract.ArrayItemType == dataContract.UnderlyingType) || // enum-based AND opted-out of inline (dataContract.EnumValues != null && !_generatorOptions.UseInlineDefinitionsForEnums); return((shouldBeReferenced) ? GenerateReferencedSchema(dataContract, schemaRepository) : GenerateInlineSchema(dataContract, schemaRepository)); }
protected override OpenApiSchema GenerateDefinitionSchema(ApiModel apiModel, SchemaRepository schemaRepository) { var apiObject = (ApiObject)apiModel; var additionalProperties = (apiObject.AdditionalPropertiesType != null) ? Generator.GenerateSchema(apiObject.AdditionalPropertiesType, schemaRepository) : null; var schema = new OpenApiSchema { Type = "object", Properties = new Dictionary <string, OpenApiSchema>(), Required = new SortedSet <string>(), AdditionalPropertiesAllowed = (additionalProperties != null), AdditionalProperties = additionalProperties }; foreach (var apiProperty in apiObject.ApiProperties) { // For data annotations, support inline attributes (i.e. applied to member directly) OR attributes applied through a MetadataType var propertyAttributes = (apiProperty.MemberInfo is PropertyInfo propertyInfo) ? propertyInfo.GetInlineOrMetadataTypeAttributes() : Enumerable.Empty <object>(); if (Options.IgnoreObsoleteProperties && propertyAttributes.OfType <ObsoleteAttribute>().Any()) { continue; } schema.Properties.Add(apiProperty.ApiName, GeneratePropertySchema(apiProperty, propertyAttributes, schemaRepository)); if (apiProperty.ApiRequired || propertyAttributes.OfType <RequiredAttribute>().Any()) { schema.Required.Add(apiProperty.ApiName); } } return(schema); }
private OpenApiRequestBody GenerateRequestBody( ApiDescription apiDescription, SchemaRepository schemaRepository) { var bodyParameter = apiDescription.ParameterDescriptions .FirstOrDefault(paramDesc => paramDesc.IsFromBody()); if (bodyParameter != null) { return(GenerateRequestBodyFromBodyParameter(apiDescription, schemaRepository, bodyParameter)); } var formParameters = apiDescription.ParameterDescriptions .Where(paramDesc => paramDesc.IsFromForm()); if (formParameters.Any()) { return(GenerateRequestBodyFromFormParameters(apiDescription, schemaRepository, formParameters)); } return(null); }
private OpenApiMediaType GenerateRequestMediaType( string contentType, ApiDescription apiDescription, SchemaRepository schemaRepository) { // If there's form parameters, generate the form-flavoured media type var apiParametersFromForm = apiDescription.ParameterDescriptions .Where(paramDesc => paramDesc.IsFromForm()); if (apiParametersFromForm.Any()) { var schema = GenerateSchemaFromApiParameters(apiDescription, apiParametersFromForm, schemaRepository); // Provide schema and corresponding encoding map to specify "form" serialization style for all properties // This indicates that array properties must be submitted as multiple parameters with the same name. // NOTE: the swagger-ui doesn't currently support arrays of files - https://github.com/swagger-api/swagger-ui/issues/4600 // NOTE: the swagger-ui doesn't currently honor encoding metadata - https://github.com/swagger-api/swagger-ui/issues/4836 return(new OpenApiMediaType { Schema = schema, Encoding = schema.Properties.ToDictionary( entry => entry.Key, entry => new OpenApiEncoding { Style = ParameterStyle.Form } ) }); } // Otherwise, generate a regular media type var apiParameterFromBody = apiDescription.ParameterDescriptions .First(paramDesc => paramDesc.IsFromBody()); return(new OpenApiMediaType { Schema = _schemaGenerator.GenerateSchema(apiParameterFromBody.Type, schemaRepository) }); }
private OpenApiSchema GenerateDictionarySchema(DataContract dataContract, SchemaRepository schemaRepository) { if (dataContract.DictionaryKeys != null) { return(new OpenApiSchema { Type = "object", Properties = dataContract.DictionaryKeys.ToDictionary( name => name, name => GenerateSchema(dataContract.DictionaryValueType, schemaRepository)) }); } else { return(new OpenApiSchema { Type = "object", AdditionalPropertiesAllowed = true, AdditionalProperties = GenerateSchema(dataContract.DictionaryValueType, schemaRepository) }); } }
private OpenApiOperation GenerateOperation(ApiDescription apiDescription, SchemaRepository schemaRepository) { var operation = new OpenApiOperation { Tags = GenerateOperationTags(apiDescription), OperationId = _options.OperationIdSelector(apiDescription), Parameters = GenerateParameters(apiDescription, schemaRepository), RequestBody = GenerateRequestBody(apiDescription, schemaRepository), Responses = GenerateResponses(apiDescription, schemaRepository), Deprecated = apiDescription.CustomAttributes().OfType <ObsoleteAttribute>().Any() }; apiDescription.TryGetMethodInfo(out MethodInfo methodInfo); var filterContext = new OperationFilterContext(apiDescription, _schemaGenerator, schemaRepository, methodInfo); foreach (var filter in _options.OperationFilters) { filter.Apply(operation, filterContext); } return(operation); }
private OpenApiRequestBody GenerateRequestBodyFromBodyParameter( ApiDescription apiDescription, SchemaRepository schemaRepository, ApiParameterDescription bodyParameter) { var contentTypes = InferRequestContentTypes(apiDescription); var isRequired = bodyParameter.CustomAttributes().Any(attr => RequiredAttributeTypes.Contains(attr.GetType())); return(new OpenApiRequestBody { Content = contentTypes .ToDictionary( contentType => contentType, contentType => new OpenApiMediaType { Schema = _schemaGenerator.GenerateSchema(bodyParameter.ModelMetadata.ModelType, schemaRepository) } ), Required = isRequired }); }
public OpenApiDocument GetSwagger(string documentName, string host = null, string basePath = null) { if (!_options.SwaggerDocs.TryGetValue(documentName, out OpenApiInfo info)) { throw new UnknownSwaggerDocument(documentName, _options.SwaggerDocs.Select(d => d.Key)); } var applicableApiDescriptions = _apiDescriptionsProvider.ApiDescriptionGroups.Items .SelectMany(group => group.Items) .Where(apiDesc => !(_options.IgnoreObsoleteActions && apiDesc.CustomAttributes().OfType <ObsoleteAttribute>().Any())) .Where(apiDesc => _options.DocInclusionPredicate(documentName, apiDesc)); var schemaRepository = new SchemaRepository(documentName); var swaggerDoc = new OpenApiDocument { Info = info, Servers = GenerateServers(host, basePath), Paths = GeneratePaths(applicableApiDescriptions, schemaRepository), Components = new OpenApiComponents { Schemas = schemaRepository.Schemas, SecuritySchemes = new Dictionary <string, OpenApiSecurityScheme>(_options.SecuritySchemes) }, SecurityRequirements = new List <OpenApiSecurityRequirement>(_options.SecurityRequirements) }; var filterContext = new DocumentFilterContext(applicableApiDescriptions, _schemaGenerator, schemaRepository); foreach (var filter in _options.DocumentFilters) { filter.Apply(swaggerDoc, filterContext); } swaggerDoc.Components.Schemas = new SortedDictionary <string, OpenApiSchema>(swaggerDoc.Components.Schemas, _options.SchemaComparer); return(swaggerDoc); }
public override OpenApiSchema CreateDefinitionSchema(Type type, SchemaRepository schemaRepository) { var isNullable = type.IsNullable(out Type innerType); var enumType = isNullable ? innerType : type; //Test to determine if the serializer will treat as string or not var describeAsString = JsonSerializer.Serialize(enumType.GetEnumValues().GetValue(0), _serializerOptions).StartsWith("\""); var schema = describeAsString ? EnumTypeMap[typeof(string)]() : EnumTypeMap[enumType.GetEnumUnderlyingType()](); if (describeAsString) { schema.Enum = enumType.GetEnumValues() .Cast <object>() .Select(value => { var stringValue = JsonSerializer.Serialize(value, _serializerOptions).Replace("\"", string.Empty); return(OpenApiAnyFactory.CreateFor(schema, stringValue)); }) .ToList(); } else { schema.Enum = enumType.GetEnumValues() .Cast <object>() .Select(value => OpenApiAnyFactory.CreateFor(schema, value)) .ToList(); } schema.Nullable = isNullable; return(schema); }
private OpenApiRequestBody GenerateRequestBody( ApiDescription apiDescription, IEnumerable <object> methodAttributes, SchemaRepository schemaRepository) { var requestContentTypes = InferRequestContentTypes(apiDescription, methodAttributes); if (!requestContentTypes.Any()) { return(null); } var bodyParameter = apiDescription.ParameterDescriptions .FirstOrDefault(paramDesc => paramDesc.IsFromBody()); bool isRequired = false; if (bodyParameter != null) { bodyParameter.GetAdditionalMetadata( apiDescription, out ParameterInfo parameterInfo, out PropertyInfo propertyInfo, out IEnumerable <object> parameterOrPropertyAttributes); isRequired = parameterOrPropertyAttributes.Any(attr => RequiredAttributeTypes.Contains(attr.GetType())); } return(new OpenApiRequestBody { Required = isRequired, Content = requestContentTypes .ToDictionary( contentType => contentType, contentType => GenerateRequestMediaType(contentType, apiDescription, schemaRepository) ) }); }
private OpenApiOperation GenerateOperation(ApiDescription apiDescription, SchemaRepository schemaRepository) { #if NET6_0_OR_GREATER var metadata = apiDescription.ActionDescriptor?.EndpointMetadata; var existingOperation = metadata?.OfType <OpenApiOperation>().SingleOrDefault(); if (existingOperation != null) { return(existingOperation); } #endif try { var operation = new OpenApiOperation { Tags = GenerateOperationTags(apiDescription), OperationId = _options.OperationIdSelector(apiDescription), Parameters = GenerateParameters(apiDescription, schemaRepository), RequestBody = GenerateRequestBody(apiDescription, schemaRepository), Responses = GenerateResponses(apiDescription, schemaRepository), Deprecated = apiDescription.CustomAttributes().OfType <ObsoleteAttribute>().Any() }; apiDescription.TryGetMethodInfo(out MethodInfo methodInfo); var filterContext = new OperationFilterContext(apiDescription, _schemaGenerator, schemaRepository, methodInfo); foreach (var filter in _options.OperationFilters) { filter.Apply(operation, filterContext); } return(operation); } catch (Exception ex) { throw new SwaggerGeneratorException( message: $"Failed to generate Operation for action - {apiDescription.ActionDescriptor.DisplayName}. See inner exception", innerException: ex); } }
private OpenApiSchema GenerateSchemaFromFormParameters( IEnumerable <ApiParameterDescription> formParameters, SchemaRepository schemaRepository) { var properties = new Dictionary <string, OpenApiSchema>(); var requiredPropertyNames = new List <string>(); foreach (var formParameter in formParameters) { var name = _options.DescribeAllParametersInCamelCase ? formParameter.Name.ToCamelCase() : formParameter.Name; var schema = (formParameter.ModelMetadata != null) ? _schemaGenerator.GenerateSchema( formParameter.ModelMetadata.ModelType, schemaRepository, formParameter.PropertyInfo(), formParameter.ParameterInfo()) : new OpenApiSchema { Type = "string" }; properties.Add(name, schema); if (formParameter.IsFromPath() || formParameter.CustomAttributes().Any(attr => RequiredAttributeTypes.Contains(attr.GetType()))) { requiredPropertyNames.Add(name); } } return(new OpenApiSchema { Type = "object", Properties = properties, Required = new SortedSet <string>(requiredPropertyNames) }); }
private OpenApiOperation GenerateOperation(ApiDescription apiDescription, SchemaRepository schemaRepository) { apiDescription.GetAdditionalMetadata(out MethodInfo methodInfo, out IEnumerable <object> methodAttributes); var operation = new OpenApiOperation { Tags = GenerateTags(apiDescription), OperationId = _options.OperationIdSelector(apiDescription), Parameters = GenerateParameters(apiDescription, schemaRepository), RequestBody = GenerateRequestBody(apiDescription, methodAttributes, schemaRepository), Responses = GenerateResponses(apiDescription, methodAttributes, schemaRepository), Deprecated = methodAttributes.OfType <ObsoleteAttribute>().Any() }; var filterContext = new OperationFilterContext(apiDescription, _schemaGenerator, schemaRepository, methodInfo); foreach (var filter in _options.OperationFilters) { filter.Apply(operation, filterContext); } return(operation); }
private OpenApiSchema GenerateDictionarySchema(DataContract dataContract, SchemaRepository schemaRepository) { if (dataContract.DictionaryKeyType.IsEnum) { // This is a special case where we can include named properties based on the enum values return(new OpenApiSchema { Type = "object", Properties = dataContract.DictionaryKeyType.GetEnumNames() .ToDictionary( name => name, name => GenerateSchema(dataContract.DictionaryValueType, schemaRepository) ) }); } return(new OpenApiSchema { Type = "object", AdditionalPropertiesAllowed = true, AdditionalProperties = GenerateSchema(dataContract.DictionaryValueType, schemaRepository) }); }
private OpenApiSchema GenerateSchemaFromApiParameters( ApiDescription apiDescription, IEnumerable <ApiParameterDescription> apiParameters, SchemaRepository schemaRepository) { // First, map to a data structure that captures the pertinent metadata var parametersMetadata = apiParameters .Select(paramDesc => { paramDesc.GetAdditionalMetadata( apiDescription, out ParameterInfo parameterInfo, out PropertyInfo propertyInfo, out IEnumerable <object> parameterOrPropertyAttributes); var name = _options.DescribeAllParametersInCamelCase ? paramDesc.Name.ToCamelCase() : paramDesc.Name; var isRequired = parameterOrPropertyAttributes.Any(attr => RequiredAttributeTypes.Contains(attr.GetType())); var schema = _schemaGenerator.GenerateSchema(paramDesc.Type, schemaRepository); return(new { Name = name, IsRequired = isRequired, Schema = schema }); }); return(new OpenApiSchema { Type = "object", Properties = parametersMetadata.ToDictionary( metadata => metadata.Name, metadata => metadata.Schema ), Required = new SortedSet <string>(parametersMetadata.Where(m => m.IsRequired).Select(m => m.Name)), }); }
private OpenApiSchema GeneratePolymorphicSchema(DataContract dataContract, SchemaRepository schemaRepository, IEnumerable <Type> subTypes) { var schema = new OpenApiSchema { OneOf = new List <OpenApiSchema>(), Discriminator = TryGetDiscriminatorName(dataContract, out string discriminatorName) ? new OpenApiDiscriminator { PropertyName = discriminatorName } : null }; var subTypesDataContracts = subTypes .Select(subType => _serializerDataContractResolver.GetDataContractForType(subType)); var allowedDataContracts = dataContract.UnderlyingType.IsAbstract ? subTypesDataContracts : new[] { dataContract }.Union(subTypesDataContracts); foreach (var allowedDataContract in allowedDataContracts) { var allowedSchema = GenerateReferencedSchema( allowedDataContract.UnderlyingType, schemaRepository, () => GenerateObjectSchema(allowedDataContract, schemaRepository)); schema.OneOf.Add(allowedSchema); if (schema.Discriminator != null && TryGetDiscriminatorValue(allowedDataContract, out string discriminatorValue)) { schema.Discriminator.Mapping.Add(discriminatorValue, allowedSchema.Reference.ReferenceV3); } } return(schema); }
public override OpenApiSchema CreateDefinitionSchema(Type type, SchemaRepository schemaRepository) { if (!type.IsDictionary(out Type keyType, out Type valueType)) { throw new InvalidOperationException($"Type {type} is not a dictionary"); } OpenApiSchema schema; if (keyType.IsEnum) { // This is a special case where we can include named properties based on the enum values schema = new OpenApiSchema { Type = "object", Properties = keyType.GetEnumNames() .ToDictionary( name => name, name => _schemaGenerator.GenerateSchema(valueType, schemaRepository) ) }; } else { schema = new OpenApiSchema { Type = "object", AdditionalPropertiesAllowed = true, AdditionalProperties = _schemaGenerator.GenerateSchema(valueType, schemaRepository) }; } schema.Nullable = !_serializerOptions.IgnoreNullValues; return(schema); }
private OpenApiSchema GenerateInlineSchema(DataContract dataContract, SchemaRepository schemaRepository) { if (dataContract.IsPrimitive) { return(GeneratePrimitiveSchema(dataContract)); } if (dataContract.IsDictionary) { return(GenerateDictionarySchema(dataContract, schemaRepository)); } if (dataContract.IsArray) { return(GenerateArraySchema(dataContract, schemaRepository)); } if (dataContract.IsObject) { return(GenerateObjectSchema(dataContract, schemaRepository)); } return(new OpenApiSchema()); }
private OpenApiSchema CreateDictionarySchema(DataContract dataContract, SchemaRepository schemaRepository) { if (dataContract.DictionaryKeys != null) { // This is a special case where the set of key values is known (e.g. if the key type is an enum) return(new OpenApiSchema { Type = "object", Properties = dataContract.DictionaryKeys.ToDictionary( name => name, name => GenerateSchema(dataContract.DictionaryValueType, schemaRepository)), AdditionalPropertiesAllowed = false, }); } else { return(new OpenApiSchema { Type = "object", AdditionalPropertiesAllowed = true, AdditionalProperties = GenerateSchema(dataContract.DictionaryValueType, schemaRepository) }); } }
public OpenApiDocument GetSwagger(string documentName, string host = null, string basePath = null) { if (!_options.SwaggerDocs.TryGetValue(documentName, out OpenApiInfo info)) { throw new UnknownSwaggerDocument(documentName, _options.SwaggerDocs.Select(d => d.Key)); } var applicableApiDescriptions = _apiDescriptionsProvider.ApiDescriptionGroups.Items .SelectMany(group => group.Items) .Where(apiDesc => _options.DocInclusionPredicate(documentName, apiDesc)) .Where(apiDesc => !_options.IgnoreObsoleteActions || !apiDesc.IsObsolete()); var schemaRepository = new SchemaRepository(); var swaggerDoc = new OpenApiDocument { Info = info, Servers = GenerateServers(host, basePath), Paths = GeneratePaths(applicableApiDescriptions, schemaRepository), Components = new OpenApiComponents { Schemas = schemaRepository.Schemas, SecuritySchemes = _options.SecuritySchemes }, SecurityRequirements = _options.SecurityRequirements }; var filterContext = new DocumentFilterContext(applicableApiDescriptions, _schemaGenerator, schemaRepository); foreach (var filter in _options.DocumentFilters) { filter.Apply(swaggerDoc, filterContext); } return(swaggerDoc); }
private bool TryGetDiscriminatorFor( DataContract dataContract, SchemaRepository schemaRepository, IEnumerable <DataContract> knownTypesDataContracts, out OpenApiDiscriminator discriminator) { discriminator = null; var discriminatorName = _generatorOptions.DiscriminatorNameSelector(dataContract.UnderlyingType) ?? dataContract.ObjectTypeNameProperty; if (discriminatorName == null) { return(false); } discriminator = new OpenApiDiscriminator { PropertyName = discriminatorName }; foreach (var knownTypeDataContract in knownTypesDataContracts) { var discriminatorValue = _generatorOptions.DiscriminatorValueSelector(knownTypeDataContract.UnderlyingType) ?? knownTypeDataContract.ObjectTypeNameValue; if (discriminatorValue == null) { continue; } discriminator.Mapping.Add(discriminatorValue, GenerateConcreteSchema(knownTypeDataContract, schemaRepository).Reference.ReferenceV3); } return(true); }
public OpenApiSchema GenerateSchema( Type type, SchemaRepository schemaRepository, MemberInfo memberInfo = null, ParameterInfo parameterInfo = null) { var schema = GenerateSchemaForType(type, schemaRepository); if (memberInfo != null) { ApplyMemberMetadata(schema, type, memberInfo); } else if (parameterInfo != null) { ApplyParameterMetadata(schema, type, parameterInfo); } if (schema.Reference == null) { ApplyFilters(schema, type, schemaRepository, memberInfo, parameterInfo); } return(schema); }
private OpenApiSchema GenerateReferencedSchema(SerializerMetadata serializerMetadata, SchemaRepository schemaRepository) { return(schemaRepository.GetOrAdd( serializerMetadata.Type, _generatorOptions.SchemaIdSelector(serializerMetadata.Type), () => { var schema = GenerateInlineSchema(serializerMetadata, schemaRepository); ApplyFilters(schema, serializerMetadata.Type, schemaRepository); return schema; })); }
private OpenApiSchema GeneratePolymorphicSchema(IEnumerable <Type> knownSubTypes, SchemaRepository schemaRepository) { return(new OpenApiSchema { OneOf = knownSubTypes .Select(subType => GenerateSchema(subType, schemaRepository)) .ToList() }); }
private OpenApiSchema GenerateObjectSchema(SerializerMetadata serializerMetadata, SchemaRepository schemaRepository) { if (serializerMetadata.Properties == null) { return(new OpenApiSchema { Type = "object" }); } var schema = new OpenApiSchema { Type = "object", Properties = new Dictionary <string, OpenApiSchema>(), Required = new SortedSet <string>() }; // If it's a baseType with known subTypes, add the discriminator property if (_generatorOptions.GeneratePolymorphicSchemas && _generatorOptions.SubTypesResolver(serializerMetadata.Type).Any()) { var discriminatorName = _generatorOptions.DiscriminatorSelector(serializerMetadata.Type); if (!schema.Properties.ContainsKey(discriminatorName)) { schema.Properties.Add(discriminatorName, new OpenApiSchema { Type = "string" }); } schema.Required.Add(discriminatorName); schema.Discriminator = new OpenApiDiscriminator { PropertyName = discriminatorName }; } foreach (var serializerPropertyMetadata in serializerMetadata.Properties) { var customAttributes = serializerPropertyMetadata.MemberInfo?.GetInlineOrMetadataTypeAttributes() ?? Enumerable.Empty <object>(); if (_generatorOptions.IgnoreObsoleteProperties && customAttributes.OfType <ObsoleteAttribute>().Any()) { continue; } var propertySchema = GenerateSchema(serializerPropertyMetadata.MemberType, schemaRepository, memberInfo: serializerPropertyMetadata.MemberInfo); schema.Properties.Add(serializerPropertyMetadata.Name, propertySchema); if (serializerPropertyMetadata.IsRequired || customAttributes.OfType <RequiredAttribute>().Any()) { schema.Required.Add(serializerPropertyMetadata.Name); } if (propertySchema.Reference == null) { propertySchema.Nullable = propertySchema.Nullable && serializerPropertyMetadata.AllowNull; } } if (serializerMetadata.ExtensionDataValueType != null) { schema.AdditionalProperties = GenerateSchema(serializerMetadata.ExtensionDataValueType, schemaRepository); } // If it's a known subType, reference the baseType for inheritied properties if (_generatorOptions.GeneratePolymorphicSchemas && (serializerMetadata.Type.BaseType != null) && _generatorOptions.SubTypesResolver(serializerMetadata.Type.BaseType).Contains(serializerMetadata.Type)) { var baseSerializerContract = _serializerMetadataResolver.GetSerializerMetadataForType(serializerMetadata.Type.BaseType); var baseSchemaReference = GenerateReferencedSchema(baseSerializerContract, schemaRepository); var baseSchema = schemaRepository.Schemas[baseSchemaReference.Reference.Id]; foreach (var basePropertyName in baseSchema.Properties.Keys) { schema.Properties.Remove(basePropertyName); } return(new OpenApiSchema { AllOf = new List <OpenApiSchema> { baseSchemaReference, schema } }); } return(schema); }
private OpenApiSchema GenerateArraySchema(SerializerMetadata serializerMetadata, SchemaRepository schemaRepository) { return(new OpenApiSchema { Type = "array", Items = GenerateSchema(serializerMetadata.ArrayItemType, schemaRepository), UniqueItems = serializerMetadata.Type.IsSet() ? (bool?)true : null }); }
private OpenApiSchema GenerateInlineSchema(SerializerMetadata serializerMetadata, SchemaRepository schemaRepository) { if (serializerMetadata.IsPrimitive) { return(GeneratePrimitiveSchema(serializerMetadata)); } if (serializerMetadata.IsDictionary) { return(GenerateDictionarySchema(serializerMetadata, schemaRepository)); } if (serializerMetadata.IsArray) { return(GenerateArraySchema(serializerMetadata, schemaRepository)); } if (serializerMetadata.IsObject) { return(GenerateObjectSchema(serializerMetadata, schemaRepository)); } return(new OpenApiSchema()); }
private OpenApiSchema GeneratePropertySchema( JsonProperty jsonProperty, MemberInfo memberInfo, object[] attributes, SchemaRepository schemaRepository) { var schema = RootGenerator.GenerateSchema(jsonProperty.PropertyType, schemaRepository); schema.WriteOnly = jsonProperty.Writable && !jsonProperty.Readable; schema.ReadOnly = jsonProperty.Readable && !jsonProperty.Writable; foreach (var attribute in attributes) { if (attribute is DefaultValueAttribute defaultValue) { schema.Default = OpenApiAnyFactory.TryCreateFor(schema, defaultValue.Value, out IOpenApiAny openApiAny) ? openApiAny : schema.Default; } else if (attribute is RegularExpressionAttribute regex) { schema.Pattern = regex.Pattern; } else if (attribute is RangeAttribute range) { schema.Maximum = decimal.TryParse(range.Maximum.ToString(), out decimal maximum) ? maximum : schema.Maximum; schema.Minimum = decimal.TryParse(range.Minimum.ToString(), out decimal minimum) ? minimum : schema.Minimum; } else if (attribute is MinLengthAttribute minLength) { schema.MinLength = minLength.Length; } else if (attribute is MaxLengthAttribute maxLength) { schema.MaxLength = maxLength.Length; } else if (attribute is StringLengthAttribute stringLength) { schema.MinLength = stringLength.MinimumLength; schema.MaxLength = stringLength.MaximumLength; } else if (attribute is EmailAddressAttribute) { schema.Format = "email"; } else if (attribute is CreditCardAttribute) { schema.Format = "credit-card"; } else if (attribute is PhoneAttribute) { schema.Format = "tel"; } else if (attribute is DataTypeAttribute dataTypeAttribute && schema.Type == "string") { schema.Format = DataTypeFormatMap.TryGetValue(dataTypeAttribute.DataType, out string format) ? format : schema.Format; } } return(schema); }
public abstract OpenApiSchema CreateDefinitionSchema(Type type, SchemaRepository schemaRepository);