小小程序员,大大发财梦

撒贝宁说:你读一篇文章疑问越多,就代表你需要成长的空间越大。

【个人学习】: Swagger的配置及使用

一、什么是Swagger?为什么要使用Swagger?

  Swagger 是一个规范和完整的框架,现在越来越多的项目采用前后端分离,API成了后端与前端沟通的纽带,API的文档也变得越来越重要。使得这个集文档在线自动生成+美观+测试于一身的框架Swagger越来越受欢迎。

  我们之前通过Word、Excel手动编写的接口文档或者说是第三方的api文档管理工具(小幺鸡等),大家有没有遇到以下情况:

  • 前端经常抱怨后端给的接口文档与实际情况不一致;
  • 后端觉得编写及维护接口文档会耗费不少精力,经常来不及或忘记更新;

  Swagger完美(这就跟开发日常的开发习惯息息相关了,要及时更新代码注释)解决了以上的问题,Swagger在API开发新版本或者迭代版本的时候,只需要更新Swagger描述文件,就可以自动生成接口文档和客户端服务端代码,做到调用端代码、服务端代码以及接口文档的一致性;

二、引用和配置Swagger

  • 通过工具-->NutGet包管理器-->程序包管理器控制台添加Swagger插件 shell命令如下:install-package Swashbuckle.AspNetCore -version 4.0.1 -Study.NetCore
  • 打开项目的NetCore项目的Startup.cs类(程序入口)配置Swagger,如下:  
            #region Swagger配置
            services.AddSwaggerGen(swg =>
            {
                swg.SwaggerDoc("v1", new Swashbuckle.AspNetCore.Swagger.Info
                {
                    Version = "v1",
                    Title = "Study.NetCore API",
                    Description = "API-说明文档",
                    TermsOfService = "None",
                    Contact = new Swashbuckle.AspNetCore.Swagger.Contact { Name = "Study.NetCore", Email = "", Url = "" }
                });
            });
            #endregion
  • 在Configure类中启动Swagger中间件,如下:

  

            #region 启动Swagger
            app.UseSwagger();
            app.UseSwaggerUI(swg =>
            {
                swg.SwaggerEndpoint("/swagger/v1/swagger.json", "APIExplainDoc");
            }); 
            #endregion
  • 启动项目,我们可以看到页面直接进入了如下的页面:

  

  • 我们输入/Swagger可以正常进入SwaggerUI页面,接下来我们把默认路由指向SwaggerUI页面。打开launchSettings.json修改如下:      
  • 这样我们运行Swagger项目,默认打开的就是SwaggerUI页面;
  • 如果要发布到正式环境,就会发现,上边的那种默认启动首页无效了,还是需要我们每次手动在域名后边输入 /swagger,这时我们在Configure中配置swg.RoutePrefix =“” 如下:
                #region 启动Swagger
                app.UseSwagger();
                app.UseSwaggerUI(swg =>
                {
                    swg.SwaggerEndpoint("/swagger/v1/swagger.json", "APIExplainDoc");
                    swg.RoutePrefix = "";
                }); 
                #endregion

三、为SwaggerUI接口添加注释

  • 右键项目名称-->属性-->生成-->勾选XML文档文件,勾选XML文档文件之后,通过修改ConfigureServices让项目启动时读取这个Xml文件,如下:
            #region Swagger配置
            services.AddSwaggerGen(swg =>
            {
                swg.SwaggerDoc("v1", new Swashbuckle.AspNetCore.Swagger.Info
                {
                    Version = "v1",
                    Title = "Study.NetCore API",
                    Description = "API-说明文档",
                    TermsOfService = "None",
                    Contact = new Swashbuckle.AspNetCore.Swagger.Contact { Name = "Study.NetCore", Email = "", Url = "" }
                });

                var bashPath = PlatformServices.Default.Application.ApplicationBasePath;
                var xmlPath = Path.Combine(bashPath, "Study.NetCore.xml");
                swg.IncludeXmlComments(xmlPath, true);//这个是controller的注释
            });
            #endregion
  • 这样运行项目后,注释都有了,非常完美。如下:

    

添加实体类的说明:基本和api的配置一致,首先勾选XML文档文件,然后在ConfigureServices中修改swagger配置,如下:

            #region Swagger配置
            services.AddSwaggerGen(swg =>
            {
                swg.SwaggerDoc("v1", new Swashbuckle.AspNetCore.Swagger.Info
                {
                    Version = "v1",
                    Title = "Study.NetCore API",
                    Description = "API-说明文档",
                    TermsOfService = "None",
                    Contact = new Swashbuckle.AspNetCore.Swagger.Contact { Name = "Study.NetCore", Email = "", Url = "" }
                });

                var bashPath = PlatformServices.Default.Application.ApplicationBasePath;
                var xmlPath = Path.Combine(bashPath, "Study.NetCore.xml");
                swg.IncludeXmlComments(xmlPath, true);//这个是controller的注释

                //model的Xml文件
                var xmlModelPath = Path.Combine(bashPath, "Study.NetCore.Model.xml");
                swg.IncludeXmlComments(xmlModelPath);
            });
            #endregion
  • 如果要隐藏某个接口,直接在action或controller上添加特性[ApiExplorerSettings(IgnoreApi = true)]

四、版本控制

  说到版本控制,我们第一时间想到的是Git、SVN等的源代码版本管理器,版本控制,顾名思义,就是对程序代码,文件等的变更管理,多个版本保证代码更改后有迹可循,可实时恢复之前版本;这就是项目的版本控制,而我们今天说的是对API的版本控制,下面我们借助swagger实现对api的版本控制。

  1. 首先先建一个用于区分版本的枚举类如下:
    namespace Study.NetCore.SwaggerHelper
    {
        /// <summary>
        /// 版本控制
        /// </summary>
        public class VersionControl
        {
            /// <summary>
            /// 接口版本号
            /// </summary> 
            public enum ApiVersion
            {
                /// <summary>
                /// v1版本
                /// </summary>
                v1 = 1,
    
                /// <summary>
                /// v2版本
                /// </summary>
                v2 = 2,
            }
        }
    }
  2. 接下来,我们打开StartUp.cs类,在ConfigureServices配置中心,修改Swagger的配置如下:
                
      private const string apiName = "Study.NetCore";
       #region Swagger配置 var bashPath = PlatformServices.Default.Application.ApplicationBasePath; services.AddSwaggerGen(swg => { //遍历版本号展示 typeof(ApiVersion).GetEnumNames().ToList().ForEach(version => { swg.SwaggerDoc(version, new Swashbuckle.AspNetCore.Swagger.Info { Version = version, Title = $"{apiName} API", Description = $"{apiName} API" + version, TermsOfService = "None", Contact = new Swashbuckle.AspNetCore.Swagger.Contact { Name = $"{apiName}", Email = "", Url = "" } }); }); var xmlPath = Path.Combine(bashPath, "Study.NetCore.xml"); swg.IncludeXmlComments(xmlPath, true);//这个是controller的注释 var xmlModelPath = Path.Combine(bashPath, "Study.NetCore.Model.xml");//model的Xml文件 swg.IncludeXmlComments(xmlModelPath); }); #endregion
  3. 接着,找到配置启动项的方法configure,修改Swagger启动代码如下:
                #region 启动Swagger
                app.UseSwagger();
                /*
                 * 之前只有一个版本,所以固定写死
                 * 遍历接口版本,并倒叙展示
                 */
                app.UseSwaggerUI(swg =>
                {
                    typeof(ApiVersion).GetEnumNames().OrderByDescending(ver => ver).ToList().ForEach(version =>
                    {
                        swg.SwaggerEndpoint($"/swagger/{version}/swagger.json", $"StudyNetCore API {version}");
    
                        swg.RoutePrefix = "";
                    });
                });
                #endregion
  4. 运行如下(借助Swagger来实现对API多版本的展示)如下:
  5. 自定义路由,新建ApiRouteAttribute特性类,如下:
    namespace Study.NetCore.SwaggerHelper
    {
        /// <summary>
        /// 自定义路由 /api/{version}/[controler]/[action]
        /// </summary>
        [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = true, Inherited = true)]
        public class ApiRouteAttribute : RouteAttribute, IApiDescriptionGroupNameProvider
        {
            /// <summary>
            /// 分组名称,是来实现接口 IApiDescriptionGroupNameProvider
            /// </summary>
            public string GroupName { get; set; }
    
            /// <summary>
            /// 自定义路由构造函数,继承基类路由
            /// </summary>
            /// <param name="actionName"></param>
            public ApiRouteAttribute(string actionName = "[action]") : base("/api/{version}/[controller]/" + actionName)
            {
            }
            ///// <summary>
            /// 自定义版本+路由构造函数,继承基类路由
            /// </summary>
            /// <param name="actionName"></param>
            /// <param name="version"></param>
            public ApiRouteAttribute(ApiVersion version, string actionName = "") : base($"/api/{version.ToString()}/[controller]/{actionName}")
            {
                GroupName = version.ToString();
            }
        }
    }
  6. 接口版本控制的使用
    • 对要区分版本的接口添加特性如:
      namespace Study.NetCore.Controllers
      {
          [Route("api/[controller]")]
          [ApiController]
          public class ValuesController : ControllerBase
          {
              /// <summary>
              /// 测试注释有没有加上1
              /// </summary>
              /// <returns></returns>
              [HttpGet]
              public ActionResult<IEnumerable<string>> Get()
              {
                  return new string[] { "value1", "value2" };
              }
      
              [HttpGet]
              //和上边的版本控制以及路由地址都是一样的
              [ApiRouteAttribute(ApiVersion.v2, "TestV2")]
              public string TestV2()
              {
                  return "我是老二";
      
              }
      
              [HttpGet("Test")]
              public string Test()
              {
                  return "我是老大";
      
              }
      
      
          }
      }

       

    • 对要区分同名的接口:在 controller 文件夹下,新建两个文件夹, v1、v2,然后添加相同的接口控制器,自定义即可,如下:
    • 运行,切换swaggerUI 版本查看。  

 

posted @ 2019-11-18 22:59  敲代码使我秃了头  阅读(1751)  评论(0编辑  收藏  举报