Asp.net web api 虚张声势的默认模型示例(虚张声势)

Asp.net web api 虚张声势的默认模型示例(虚张声势),asp.net-web-api,asp.net-web-api2,swagger,swagger-ui,Asp.net Web Api,Asp.net Web Api2,Swagger,Swagger Ui,我正在运行ASP WebAPI 2并成功安装了Swashback。我试图弄清楚人们是如何定义默认模式值的 例如,在Swagger live演示网站上,他们将pet的默认值更改为“doggie”。他们还定义了状态的允许值。() 我通过以下链接实现了这一点: 简言之,这是需要做的: 如链接中所述,创建SwaggerDefaultValue和addDefaultValue类。我做了一些改变: public class SwaggerDefaultValue : Attribute { pu

我正在运行ASP WebAPI 2并成功安装了Swashback。我试图弄清楚人们是如何定义默认模式值的

例如,在Swagger live演示网站上,他们将pet的默认值更改为“doggie”。他们还定义了状态的允许值。()


我通过以下链接实现了这一点:

简言之,这是需要做的:

  • 如链接中所述,创建SwaggerDefaultValue和addDefaultValue类。我做了一些改变:

    public class SwaggerDefaultValue : Attribute
    {
        public string Name { get; set; }
        public string Value { get; set; }
    
        public SwaggerDefaultValue(string value)
        {
            this.Value = value;
        }
    
        public SwaggerDefaultValue(string name, string value) : this(value)
        {
            this.Name = name;
        }
    }
    
    public class AddDefaultValues : IOperationFilter
    {
        public void Apply(Operation operation, SchemaRegistry schemaRegistry, ApiDescription apiDescription)
        {
            IDictionary<string, object> parameterValuePairs =
            GetParameterValuePairs(apiDescription.ActionDescriptor);
    
            foreach (var param in operation.parameters)
            {
                var parameterValuePair = parameterValuePairs.FirstOrDefault(p => p.Key.IndexOf(param.name, StringComparison.InvariantCultureIgnoreCase) >= 0);
                param.@default = parameterValuePair.Value;
            }
        }
    
        private IDictionary<string, object> GetParameterValuePairs(HttpActionDescriptor actionDescriptor)
        {
            IDictionary<string, object> parameterValuePairs = new Dictionary<string, object>();
    
            foreach (SwaggerDefaultValue defaultValue in actionDescriptor.GetCustomAttributes<SwaggerDefaultValue>())
            {
                parameterValuePairs.Add(defaultValue.Name, defaultValue.Value);
            }
    
            foreach (var parameter in actionDescriptor.GetParameters())
            {
                if (!parameter.ParameterType.IsPrimitive)
                {
                    foreach (PropertyInfo property in parameter.ParameterType.GetProperties())
                    {
                        var defaultValue = GetDefaultValue(property);
    
                        if (defaultValue != null)
                        {
                             parameterValuePairs.Add(property.Name, defaultValue);
                        }
                    }
                }
            }
    
            return parameterValuePairs;
        }
    
        private static object GetDefaultValue(PropertyInfo property)
        {
            var customAttribute = property.GetCustomAttributes<SwaggerDefaultValue>().FirstOrDefault();
    
            if (customAttribute != null)
            {
                return customAttribute.Value;
            }
    
            return null;
        }
    }
    

  • 嗯,vgaspar.trivix的代码对我来说并不完全有效,没有为模式设置默认值。我还得到了一个
    NullPointerException
    。我通过编辑
    Apply
    方法并按如下方式操作schemaRegistry,使其按预期工作:

    public void Apply(Operation operation, SchemaRegistry schemaRegistry, ApiDescription apiDescription)
    {
        if (operation.parameters == null)
            return;
        IDictionary<string, object> parameterValuePairs =
        GetParameterValuePairs(apiDescription.ActionDescriptor);
    
        foreach (var param in operation.parameters)
        {
            if (param.schema != null && param.schema.@ref != null)
            {
                string schemaName = param.schema.@ref.Split('/').LastOrDefault();
                if (schemaRegistry.Definitions.ContainsKey(schemaName))
                    foreach (var props in schemaRegistry.Definitions[schemaName].properties)
                    {
                        if (parameterValuePairs.ContainsKey(props.Key))
                            props.Value.@default = parameterValuePairs[props.Key];
                    }
            }
            var parameterValuePair = parameterValuePairs.FirstOrDefault(p => p.Key.IndexOf(param.name, StringComparison.InvariantCultureIgnoreCase) >= 0);
            param.@default = parameterValuePair.Value;
        }
    }
    
    public void Apply(操作操作,SchemaRegistry SchemaRegistry,apisdescription apisdescription)
    {
    if(operation.parameters==null)
    返回;
    IDictionary参数值对=
    GetParameterValuePairs(apiscription.ActionDescriptor);
    foreach(操作中的var param.parameters)
    {
    if(param.schema!=null&¶m.schema.@ref!=null)
    {
    字符串schemaName=param.schema@ref.Split('/').LastOrDefault();
    if(schemaRegistry.Definitions.ContainsKey(schemaName))
    foreach(schemaRegistry.Definitions[schemaName].props中的var props)
    {
    if(parameterValuePairs.ContainsKey(props.Key))
    props.Value@default=parameterValuePairs[props.Key];
    }
    }
    var parameterValuePair=parameterValuePairs.FirstOrDefault(p=>p.Key.IndexOf(param.name,StringComparison.InvariantCultureIgnoreCase)>=0);
    param@default=parameterValuePair.Value;
    }
    }
    
    可以通过实现
    ISchemaFilter
    并使用以下内容注册来定义示例模型架构:

    public IHttpActionResult Put([FromBody]Pet pet)
    {
       ...
       return Ok();
    }
    
    public class Pet {
        [SwaggerDefaultValue("doggie")]
        public string Name { get; set; }
    
        [SwaggerDefaultValue("available")]
        public string Status;
    
        ...
    }
    
    httpConfig 
        .EnableSwagger(c =>
             {
                 c.SchemaFilter<AddSchemaExamples>()
             });
    

    我知道这个线程已经很老了,但我想与大家分享我的解决方案,它只为Swagger示例模式创建了一个自定义构造函数

    在我的模型中:

    /// <summary>
    /// Supply a custom constructor for Swagger where you can apply defaults to control the example schema.  
    /// The constructor must have one parameter of type System.Reflection.ParameterInfo[].
    /// Note: Setting a property to null will prevent it from showing in the Swagger example.
    /// </summary>System.Reflection.ParameterInfo[].
    /// </summary>
    public class SwaggerConstructor : Attribute { }
    

    刚才偶然发现这个,您也可以在XML文档中设置标记,在我的一个模型中,我定义了这个

        /// <summary>
        /// Note content
        /// </summary>
        /// <example>Any text for a note.</example>
        public string Note { get; set; }
    
    //
    ///注释内容
    /// 
    ///注释的任何文本。
    公共字符串注释{get;set;}
    
    在swagger文档中,当选择“立即试用”时,其结果如下所示


    希望这对别人有帮助

    有完全相同的问题,你解决了,谢谢!我已经试过了,但是如果我想删除一些模型属性,该怎么办?@philipp michalski如果Pet类是一个动作的响应,而不是一个参数呢?如果有一个操作接受Pet作为输入参数,那么返回类型为Pet的另一个操作将正常工作,因为此代码将更改Swagger文档的“定义”部分,这将影响所有引用。但是,如果您只有一个返回类型为Pet的操作,则此代码不会产生相同的效果。我的例子是不同类型的输入参数和输出参数。感谢您的帮助据我所知,这个应该是非常通用的,它接受各种参数作为默认值,您只需要添加
    [SwaggerDefaultValue(Pet())]publicpet行到您的模式。但那是很久以前的事了,我真的不记得了。我想知道为什么斯威格还没有解决这个问题。。。
    
    /// <summary>
    /// Supply a custom constructor for Swagger where you can apply defaults to control the example schema.  
    /// The constructor must have one parameter of type System.Reflection.ParameterInfo[].
    /// Note: Setting a property to null will prevent it from showing in the Swagger example.
    /// </summary>System.Reflection.ParameterInfo[].
    /// </summary>
    public class SwaggerConstructor : Attribute { }
    
    c.SchemaFilter<ApplySchemaVendorExtensions>();
    
        public class ApplySchemaVendorExtensions : ISchemaFilter
    {
        public void Apply(Schema schema, SchemaRegistry schemaRegistry, Type type)
        {
            ConstructorInfo constructor = type.GetConstructors().FirstOrDefault(c => c.GetCustomAttribute<SwaggerConstructor>() != null);
            if (constructor != null)
            {
                schema.example = constructor.Invoke(new object[] { constructor.GetParameters() });
            }
        }
    }
    
        [SwaggerConstructor]
        public MyClass(System.Reflection.ParameterInfo[] decoy) : base()
        {
            MyProperty = false;
        }
    
        /// <summary>
        /// Note content
        /// </summary>
        /// <example>Any text for a note.</example>
        public string Note { get; set; }