.net core webapi 定义多版本与 Swagger 的文档输出

前提:

  需要nuget  以下两个程序集

        Swashbuckle.AspNetCore 我暂时用的是  4.01;

        Microsoft.AspNetCore.Mvc.Versioning.ApiExplorer    2.2.0

描述:解决 .net core  webapi 同一个项目中,多个版本的控制及文档输出;

 Controllers 层次如下:

 

实际效果:(引用他人的git图片)

  

 

解决办法:

  步骤1  对startup.cs 进行修改代码如下:

    1.1 增加私有变量:  

/// <summary>
/// Api版本提者信息
/// </summary>
private IApiVersionDescriptionProvider provider;

    1.2 在配置服务 ConfigureServices 中增加如下代码:

复制代码

            services.AddApiVersioning(option =>
            {
                option.AssumeDefaultVersionWhenUnspecified = true;
                option.ReportApiVersions = false;
            })
            .AddMvcCore().AddVersionedApiExplorer(option =>
            {
                option.GroupNameFormat = "'v'VVV";
                option.AssumeDefaultVersionWhenUnspecified = true;
            });

            this.provider = services.BuildServiceProvider().GetRequiredService<IApiVersionDescriptionProvider>();
            services.AddSwaggerGen(options =>
            {
                foreach (var description in provider.ApiVersionDescriptions)
                {
                    options.SwaggerDoc(description.GroupName,
                         new Info()
                         {
                             Title = $"接口 v{description.ApiVersion}",
                             Version = description.ApiVersion.ToString(),
                             Description = "切换版本请点右上角版本切换"
                         }
                    );
                }
              options.IncludeXmlComments(this.GetType().Assembly.Location.Replace(".dll", ".xml"), true);
            });

复制代码

    1.3 在配置http管道 Configure 中增加如下代码:

复制代码

            app.UseSwagger();
            app.UseSwaggerUI(c =>
            {
                foreach (var description in provider.ApiVersionDescriptions)
                {
                    c.SwaggerEndpoint($"/swagger/{description.GroupName}/swagger.json", description.GroupName.ToUpperInvariant());
                }
            });

复制代码

 

   步骤2 对Controllers 配置相应版本信息

  不同的版本只需改变    [ApiVersion("x.x.x")]

复制代码

    /// <summary>
    /// 1.0 版本
    /// </summary>
    [ApiController]
    [ApiVersion("1.0")]
    [Route("api/v{version}/[controller]/[action]")]
    public class EasenController : ControllerBase
    {
         ..................
    }

复制代码

 

  步骤3 为了更好的在Swagger 文档调试的时候自动填入相应的版本号进行优化

    3.1 增加 SwaggerOperationFilter.cs 代码如下:

复制代码

    /// <summary>
    /// Swagger 过滤器
    /// </summary>
    public class SwaggerOperationFilter : IOperationFilter
    {
        /// <summary>
        /// 应用过滤器
        /// </summary>
        /// <param name="operation"></param>
        /// <param name="context"></param>
        public void Apply(Operation operation, OperationFilterContext context)
        {
            #region Swagger版本描述处理
            foreach (var parameter in operation.Parameters.OfType<NonBodyParameter>())
            {
                var description = context.ApiDescription.ParameterDescriptions.First(p => p.Name == parameter.Name);
                if (parameter.Description == null)
                {
                    parameter.Description = "填写版本号如:1.0";
                    parameter.Default = context.ApiDescription.GroupName.Replace("v", "");
                }
            }
            #endregion
      }
}

复制代码

      3.2 在 startup.cs   ConfigureServices  中对 AddSwaggerGen 配置项进行修改代码如下:

        services.AddSwaggerGen(options =>
        {
                ...............
                options.OperationFilter<SwaggerOperationFilter>(); 
             });

转自:https://www.cnblogs.com/intotf/p/10075331.html

 

 

====================================================================

第一步 导入nuget包

nuget导入Swashbuckle.AspNetCore (对应有Swashbuckle.AspNetCore.Swagger、Swashbuckle.AspNetCore.SwaggerGen、Swashbuckle.AspNetCore.SwaggerUI)

版本控制还需要引入

Microsoft.AspNetCore.Mvc.Versioning.ApiExplorer

Microsoft.AspNetCore.Mvc.Versioning

第二步 添加服务及配置

下面代码中都结合了IdentityServer4中的相关设置,可以忽略

非版本控制

ConfigServices中添加如下代码

复制代码

services.AddSwaggerGen(options =>
            {           
                options.SwaggerDoc("v1", new Swashbuckle.AspNetCore.Swagger.Info
                {
                    Version = "v1.0",
                   Title = "体检微服务接口"
                });
              

                var basePath = PlatformServices.Default.Application.ApplicationBasePath;
                var xmlPath = Path.Combine(basePath, "ExaminationServicesApi.xml");
                options.IncludeXmlComments(xmlPath);

                var xmlmodelPath = 
                Path.Combine(basePath, "ExaminationServicesDomain.xml");
                options.IncludeXmlComments(xmlmodelPath);

                #region Swagger添加授权验证服务

                //options.AddSecurityDefinition("Bearer", new ApiKeyScheme
                //{
                //    Description = "JWT Bearer 授权 \"Authorization: Bearer+空格+token\"",
                //    Name = "Authorization",
                //    In = "header",
                //    Type = "apiKey"
                //});

                options.AddSecurityDefinition("oauth2", new OAuth2Scheme
                {
                    Type = "oauth2",
                    Flow = "implicit",
                    AuthorizationUrl = _authorityconfig.Authority + "/connect/authorize",
                    Scopes = new Dictionary<string, string>
                        {
                          //{ "openid", "身份信息" } ,
                          //{ "profile", "个人基本信息" } ,
                          { "userservicesapi", "用户服务" },
                          { "examinationservicesapi", "体检服务" }
                        }
                });
                options.OperationFilter<CustomOperationFilter>();
                #endregion

            });

复制代码

复制代码

 app.UseSwagger();
            app.UseSwaggerUI(c =>
            {
                c.SwaggerEndpoint("/swagger/v1/swagger.json", "WebApi");
                c.OAuthClientId("testuserservicesapiexaminationservicesapi");
                c.OAuthAppName("体检服务");
            });

复制代码

这里要注意到我添加了2个xml 一个是apicontroller的获取注释描述,如果需要model相关的描述可以将model所在的应用程序集xml处理下,以便于在接口文档上可以看到model的先关说明

版本控制

ConfigServices中添加如下代码 只不过是动态的处理了版本信息

复制代码

 services.AddApiVersioning(option =>
            {
                option.AssumeDefaultVersionWhenUnspecified = true;
                option.ReportApiVersions = false;
            })
            .AddMvcCore().AddVersionedApiExplorer(option => {
                option.GroupNameFormat = "'v'VVV";
                option.AssumeDefaultVersionWhenUnspecified = true;
            }); 
            services.AddSwaggerGen(options =>
            {
                var provider = services.BuildServiceProvider().GetRequiredService<IApiVersionDescriptionProvider>();
                foreach (var description in provider.ApiVersionDescriptions)
                {
                    options.SwaggerDoc(description.GroupName,
                         new Info()
                        {
                            Title = $"体检微服务接口 v{description.ApiVersion}",
                            Version = description.ApiVersion.ToString(),
                            Description = "切换版本请点右上角版本切换",
                            Contact = new Contact() { Name = "黎又铭", Email = "2939828886@qq.com" }
                        }
                    );
                }


                //options.SwaggerDoc("v1", new Swashbuckle.AspNetCore.Swagger.Info
                //{
                //    Version = "v1.0",
                //    Title = "体检微服务接口"
                //});
              

                var basePath = PlatformServices.Default.Application.ApplicationBasePath;
                var xmlPath = Path.Combine(basePath, "ExaminationServicesApi.xml");
                options.IncludeXmlComments(xmlPath);


               
                var xmlmodelPath = 
                Path.Combine(basePath, "ExaminationServicesDomain.xml");
                options.IncludeXmlComments(xmlmodelPath);

                #region Swagger添加授权验证服务

                //options.AddSecurityDefinition("Bearer", new ApiKeyScheme
                //{
                //    Description = "JWT Bearer 授权 \"Authorization: Bearer+空格+token\"",
                //    Name = "Authorization",
                //    In = "header",
                //    Type = "apiKey"
                //});

                options.AddSecurityDefinition("oauth2", new OAuth2Scheme
                {
                    Type = "oauth2",
                    Flow = "implicit",
                    AuthorizationUrl = _authorityconfig.Authority + "/connect/authorize",
                    Scopes = new Dictionary<string, string>
                        {
                          //{ "openid", "身份信息" } ,
                          //{ "profile", "个人基本信息" } ,
                          { "userservicesapi", "用户服务" },
                          { "examinationservicesapi", "体检服务" }

                        }
                });
                options.OperationFilter<CustomOperationFilter>();
                #endregion

            });

复制代码

复制代码

 app.UseSwagger();
            app.UseSwaggerUI(c =>
            {
               
                foreach (var description in provider.ApiVersionDescriptions)
                {
                    c.SwaggerEndpoint($"/swagger/{description.GroupName}/swagger.json", description.GroupName.ToUpperInvariant());
                }
                //c.SwaggerEndpoint("/swagger/v1/swagger.json", "WebApi");
                c.OAuthClientId("testuserservicesapiexaminationservicesapi");
                c.OAuthAppName("体检服务");
            });

复制代码

对比两种情况可以看出实际上就多出来一个办理版本信息而已,ApiVersionDescriptions 其实就是通过这个特性动态遍历了版本信息,所以多版本控制只需要在ApiController中添加好相关的属性标签即可

第三步 使用

复制代码

[ApiVersion("1.0")]
[Route("api/v{api-version:apiVersion}/[controller]")]
 public class DemoController : ControllerBase
{

}

复制代码

 

在前面代码中我们用到了 CustomOperationFilter这个处理,在这个操作过滤器中我在之前的代码中添加授权及文件上传,这里我们使用版本控制还需要在里面添加好版本参数描述处理

复制代码

 public class CustomOperationFilter : IOperationFilter
    {
        public void Apply(Operation operation, OperationFilterContext context)
        {

            #region Swagger版本描述处理
            foreach (var parameter in operation.Parameters.OfType<NonBodyParameter>())
            {
                var description = context.ApiDescription.ParameterDescriptions.First(p => p.Name == parameter.Name);

                if (parameter.Description == null)
                {
                    parameter.Description = description.ModelMetadata.Description;
                }
            }

            #endregion

            #region Swagger授权过期器处理
            if (operation.Security == null)
                operation.Security = new List<IDictionary<string, IEnumerable<string>>>();
            var oAuthRequirements = new Dictionary<string, IEnumerable<string>>
                                        {

                                              {"oauth2", new List<string> { "openid", "profile", "examinationservicesapi" }}
                                        };
            operation.Security.Add(oAuthRequirements);
            #endregion

            #region Swagger 文件上传处理

            var files = context.ApiDescription.ActionDescriptor.Parameters.Where(n => n.ParameterType == typeof(IFormFile)).ToList();
            if (files.Count > 0)
            {
                for (int i = 0; i < files.Count; i++)
                {
                    if (i == 0)
                    {
                        operation.Parameters.Clear();
                    }
                    operation.Parameters.Add(new NonBodyParameter
                    {
                        Name = files[i].Name,
                        In = "formData",
                        Description = "Upload File",
                        Required = true,
                        Type = "file"
                    });

                }
                operation.Consumes.Add("multipart/form-data");
            }

            #endregion
        }
    }

复制代码

运行程序看效果

 

 版本控制就搞定了,这里需要说明的是看下面的图

额外说明

版本是不是必须的、以及描述就是在CustomOperationFilter中处理下默认的说明,你可以这样写

复制代码

 if (parameter.Description == null)
                {
                    parameter.Description ="填写版本号如:1.0";
                }

parameter.Required=false; //设置非必填或非必填

复制代码

下面看下效果,已经有注释了和设置了的非必填项目

这里额外在说一点的就是

 [ApiVersion("1.0", Deprecated = false)]

Deprecated  这个属性设置 True :标识是否弃用API ,在设置为true的情况下来看下效果

1.0版本已经是弃用了,这里又要额外说下与这个关联的属性了就是在服务配置选项中的 ReportApiVersions 设置 用下面的配置 

复制代码

 services.AddApiVersioning(option =>
            {
                option.ReportApiVersions = false;
            })
            .AddMvcCore().AddVersionedApiExplorer(option => {
                option.GroupNameFormat = "'v'VVV";
                option.AssumeDefaultVersionWhenUnspecified = true;
                option.DefaultApiVersion = new ApiVersion(1, 0);
            }); 

复制代码

false:不再请求响应中添加 版本报告信息,下图中已经不会显示我一用的版本信息了

https://www.cnblogs.com/liyouming/p/9889962.html

上面默认版本 DefaultApiVersion 我设置了1.0 在代码中出现2个版本路由地址一样,在没有填写版本号的情况下使用默认版本

AssumeDefaultVersionWhenUnspecified:true 是否在没有填写版本号的情况下使用默认版本

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
很高兴回答您的问题!您想了解的是关于使用.NET Core WebAPI开发网上书店的相关内容吗? 使用.NET Core WebAPI可以很方便地构建一个基于HTTP协议的API,用于处理网上书店的业务逻辑。下面是一些可能有用的步骤和建议: 1. 创建项目:首先,您可以使用Visual Studio或者命令行工具来创建一个新的.NET Core WebAPI项目。 2. 定义模型:根据您的需求,确定需要的数据模型,例如书籍、订单、用户等。使用C#定义这些模型,并在数据库中创建相应的表格。 3. 配置数据库:使用Entity Framework Core或者其他ORM工具来连接数据库,并配置数据库连接字符串。您可以选择使用关系型数据库,如SQL Server、MySQL,或者非关系型数据库,如MongoDB。 4. 实现控制器:创建控制器类来处理API请求,并实现相应的动作方法。例如,添加书籍、获取书籍列表、下订单等。在方法中,您可以使用依赖注入来获取服务实例,如书籍管理、订单处理等。 5. 安全认证和授权:根据需求,您可以添加身份验证和授权机制来保护API资源。例如,使用JWT(Json Web Token)来对用户进行认证,使用角色或策略来限制访问权限。 6. 编写API文档:为了方便其他开发者使用您的API,您可以使用Swagger等工具来生成和展示API文档文档中包含API的接口定义、请求/响应示例等信息。 7. 部署和测试:最后,您可以将API部署到云服务器或者其他托管平台上,并进行测试。您可以使用Postman或其他API测试工具来发送请求,并验证API的功能和性能。 当然,以上只是一个简单的指南,具体的实现细节还需要根据您的需求和项目的特点来进行调整和扩展。希望对您有所帮助!如果您有更多的问题,请随时提问。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值