0


Swagger 的使用

文章目录

Swagger 的使用

前言

后端时代

  • 前端:只用管理静态页面:html。
  • 后端:模板引擎 JSP,后端是主力

前后端分离时代

主流框架:Vue + SpringBoot

  • 后端:后端控制层,服务层,数据访问层【后端团队】
  • 前端:前端控制层,视图层【前端团队】 - 伪造后端数据:json假数据。不需要请求后端,仅前端工程已经可以启动并操作。

前后端通过 API 接口进行交互,相对独立,松耦合,可以部署在不同的服务器上

前端后分离存在的问题:

  • 前后端集成联调,前端人员和后端人员无法做到“及时协商,尽早解决”,最终导致问题集中爆发;

解决方案:

  • 首先制定 schema (计划的提纲),试试更新最新 API ,降低集成风险;
  • 早期:制定word计划文档;
  • 前后端分离: - 后端接口测试工具:postman- 后端向前端提供接口,需要实时更新罪行的消息及改动!

Swagger 简介

  • 号称世界上最流程的 Api 框架;
  • 在线自动生成 RestFul Api 文档,该文档与 Api 接口信息同步更新;
  • 直接运行,可在线测试 Api 接口;
  • 支持多种语言:Java、Php ...

官网:

  • https://swagger.io/

使用:

  • 在项目中使用 Swagger 需要两个 springfox 依赖: - springfox-swagger2- springfox-swagger-ui

SpringBoot 集成 Swagger 2.x

  1. 新建一个 SpringBoot 项目(web 项目);
  2. 导入依赖<!-- https://mvnrepository.com/artifact/io.springfox/springfox-swagger2 --><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger2</artifactId><version>2.9.2</version><exclusions><exclusion><!-- io.springfox:springfox-swagger2:2.9.2中依赖了swagger-models的1.5.20版本, 通过排除springfox-swagger2中的swagger-models依赖,导入io.swagger:swagger-models的1.5.22版本. 解决io.swagger.models.parameters.AbstractSerializableParameter实例化参数时example为空字符串""而报错的问题. 因为1.5.20的example只判断是否为null,1.5.22判断了是否为null和"" --><groupId>io.swagger</groupId><artifactId>swagger-models</artifactId></exclusion></exclusions></dependency><!-- https://mvnrepository.com/artifact/io.swagger/swagger-models --><dependency><groupId>io.swagger</groupId><artifactId>swagger-models</artifactId><version>1.5.22</version></dependency><!-- https://mvnrepository.com/artifact/io.springfox/springfox-swagger-ui --><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger-ui</artifactId><version>2.9.2</version></dependency>
  3. 编写一个 Hello 工程;
  4. 在主程序上添加注解,开启 Swagger2``````@SpringBootApplication//开启 Swagger2@EnableSwagger2publicclassSwaggerDemoApplication{publicstaticvoidmain(String[] args){SpringApplication.run(SwaggerDemoApplication.class, args);}}
  5. 测试运行,访问 Swagger UI 界面http://localhost:8080/swagger-ui.html

SpringBoot 集成 Swagger 3.0

  1. 新建一个 SpringBoot 项目(web项目);
  2. 导入依赖<!-- https://mvnrepository.com/artifact/io.springfox/springfox-boot-starter --><dependency><groupId>io.springfox</groupId><artifactId>springfox-boot-starter</artifactId><version>3.0.0</version></dependency>
  3. 编写一个 Hello 工程;
  4. 在主程序上添加注解,开启Swagger@SpringBootApplication//开启 Swagger@EnableOpenApipublicclassSwaggerDemoApplication{publicstaticvoidmain(String[] args){SpringApplication.run(SwaggerDemoApplication.class, args);}}
  5. 测试运行,访问 Swagger UI 界面 注意:路径同 Swagger 2.x 不同http://localhost:8080/swagger-ui/index.html

配置 Swagger

配置文档信息

Swagger 的 bean 实例:

Docket
Docket.apiInfo(ApiInfo apiInfo)方法

具体配置

@ConfigurationpublicclassSwaggerConfig{/**
     * 配置 Swagger Docket 的 bean实例
     *
     * @return Docket 的 bean实例
     */@BeanpublicDocketdocket(){returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo());}/**
     * 配置 swagger 的信息:ApiInfo
     *
     * @return ApiInfo 的 bean实例
     */publicApiInfoapiInfo(){//作者信息Contact contact =newContact("小聪","https://blog.csdn.net/weixin_52610802?type=blog","[email protected]");returnnewApiInfo("Aladdin的SwaggerAPI文档","不负韶华,未来可期","V1.0","https://blog.csdn.net/weixin_52610802?type=blog",
                contact,"Apache 2.0","http://www.apache.org/licenses/LICENSE-2.0",newArrayList());}}

配置扫描接口

Docket.select()方法

具体配置

/**
 * 配置 Swagger Docket 的 bean实例
 *
 * @return Docket 的 bean实例
 */@BeanpublicDocketdocket(){returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo()).select()/*
            RequestHandlerSelectors 配置扫描接口的方式
                basePackage():指定要扫描的包(通常指定包扫描)
                any():扫描全部
                none():不扫描
                withMethodAnnotation():扫描方法上的注解
                withClassAnnotation():方法类上的注解
             */.apis(RequestHandlerSelectors.basePackage("com.aladdin.swagger.controller"))/*
            PathSelectors 请求路径匹配的方式
                regex():正则匹配
                any():扫描全部
                none():不扫描
                ant():路径匹配
             */.paths(PathSelectors.ant("/aladdin/**")).build();}

配置功能是否启动

Docket.enable(boolean externallyConfiguredFlag)方法

具体配置

/**
 * 配置 Swagger Docket 的 bean实例
 *
 * @return Docket 的 bean实例
 */@BeanpublicDocketdocket(){returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo())//是否启动 Swagger,如果为 false,则 UI界面提示:【😱 Could not render e, see the console.】,无法在浏览器中访问 Swagger.enable(false).select().apis(RequestHandlerSelectors.basePackage("com.aladdin.swagger.controller")).paths(PathSelectors.ant("/aladdin/**")).build();}

实用案例

  • 根据服务环境动态配置 Swagger 是否开启。
/**
 * 配置 Swagger Docket 的 bean实例
 *
 * @return Docket 的 bean实例
 */@BeanpublicDocketdocket(Environment environment){//配置要显示 Swagger 的环境Profiles profiles =Profiles.of("dev","test");//通过environment.acceptsProfiles()方法判断当前是否处在自己设定的环境中boolean flag = environment.acceptsProfiles(profiles);returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo())//是否开启 Swagger,如果为 false,则 UI界面提示:【😱 Could not render e, see the console.】,无法在浏览器中访问 Swagger.enable(flag).select().apis(RequestHandlerSelectors.basePackage("com.aladdin.swagger.controller")).paths(PathSelectors.ant("/aladdin/**")).build();}

配置 API 文档的分组

Docket.groupName(String groupName)方法

具体配置

/**
 * 配置 Swagger Docket 的 bean实例
 *
 * @return Docket 的 bean实例
 */@BeanpublicDocketdocket(Environment environment){returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo()).enable(true)//设置组名称,一个 Docket bean 对应一个组名称.groupName("阿拉丁").apis(RequestHandlerSelectors.basePackage("com.aladdin.swagger.controller"))//.paths(PathSelectors.ant("/aladdin/**")).build();}

配置多个分组

配置多个分组,需配置多个

Docket bean

,每个

bean

配置各自的

groupName

packagecom.aladdin.swagger.config;importorg.springframework.context.annotation.Bean;importorg.springframework.context.annotation.Configuration;importorg.springframework.core.env.Environment;importorg.springframework.core.env.Profiles;importspringfox.documentation.builders.RequestHandlerSelectors;importspringfox.documentation.service.ApiInfo;importspringfox.documentation.service.Contact;importspringfox.documentation.spi.DocumentationType;importspringfox.documentation.spring.web.plugins.Docket;importjava.util.ArrayList;@ConfigurationpublicclassSwaggerConfig{/**
     * 配置 Swagger Docket 的 bean实例
     *
     * @return Docket 的 bean实例
     */@BeanpublicDocketdocket(Environment environment){returnnewDocket(DocumentationType.SWAGGER_2).apiInfo(apiInfo()).enable(true).groupName("阿拉丁").select().apis(RequestHandlerSelectors.basePackage("com.aladdin.swagger.controller"))//.paths(PathSelectors.ant("/aladdin/**")).build();}/**
     * 配置 swagger 的信息:ApiInfo
     *
     * @return ApiInfo 的 bean实例
     */publicApiInfoapiInfo(){//作者信息Contact contact =newContact("阿拉丁","https://blog.csdn.net/weixin_52610802?type=blog","[email protected]");returnnewApiInfo("Aladdin的SwaggerAPI文档","不负韶华,未来可期","V1.0","https://blog.csdn.net/weixin_52610802?type=blog",
                contact,"Apache 2.0","http://www.apache.org/licenses/LICENSE-2.0",newArrayList());}@BeanpublicDocketdocket1(){returnnewDocket(DocumentationType.SWAGGER_2).groupName("分组1");}@BeanpublicDocketdocket2(){returnnewDocket(DocumentationType.SWAGGER_2).groupName("分组2");}@BeanpublicDocketdocket3(){returnnewDocket(DocumentationType.SWAGGER_2).groupName("分组3");}}

模型类模块(Models)

  • Swagger 页面 Models 模块为实体类信息
  • 如果 Swagger 分组扫描的接口返回值存在实体类,则此实体类就会被扫描到该分组中1. 新建实体类publicclassUser{privateString username;privateString password;...}2. 增加返回值为 User 类的接口@RestControllerpublicclassHelloController{@GetMapping("/hello")publicStringhello(){return"Hello";}@PostMapping("/user")publicUseruser(){returnnewUser("123","qwe");}}3. 重启项目,访问 Swagger 页面,则会看见 Models 中加载了 User 实体类

文档注释

可使用

Swagger

注解为生成的

Api

在线文档添加注释信息
作用范围API使用位置描述返回对象的意义@ApiModel用在返回对象类上对象属性@ApiModelProperty用在出入参数对象的字段上作用范围API使用位置协议集描述@Api用于controller类上协议描述@ApiOperation用在controller的方法上Response集@ApiResponses用在controller的方法上Response@ApiResponse用在 @ApiResponses里边非对象参数集@ApiImplicitParams用在controller的方法上非对象参数描述@ApiImplicitParam用在@ApiImplicitParams的方法里边

  • @Api:用在controller上,对controller进行注释;
  • @ApiOperation:用在API方法上,对该API做注释,说明API的作用;
  • @ApiResponses:通常用来包含接口的一组响应注解,可以简单的理解为响应注解的集合声明;
  • @ApiResponse:用在@ApiResponses中,一般用于表达一个错误的响应信息;- code:即httpCode,例如400;- message:信息,例如"请求参数没填好";> 即使只有一个@ApiResponse,也需要使用@ApiResponses包住。
  • @ApiImplicitParams:用来包含API的一组参数注解,可以简单的理解为参数注解的集合声明;
  • @ApiImplicitParam:用在 @ApiImplicitParams 注解中,也可以单独使用,说明一个请求参数的各个方面,该注解包含的常用选项有:属性取值作用paramType查询参数类型path以地址的形式提交数据query直接跟参数完成自动映射赋值body以流的形式提交 仅支持POSTheader参数在request headers 里边提交form以form表单的形式提交,仅支持POSTdataType参数的数据类型 只作为标志说明,并没有实际验证LongStringname接收参数名value接收参数的意义描述required参数是否必填true必填false非必填defaultValue默认值代码> 1. form域中的值需要使用@RequestParam获取> 2. header域中的值需要使用@RequestHeader来获取> 3. path域中的值需要使用@PathVariable来获取> 4. body域中的值使用@RequestBody来获取,否则可能出错;而且如果paramType是body,name就不能是body,否则有问题,与官方文档中的 “If paramType is "body", the name should be "body" 不符。

Swagger Demo


部分示范代码

packagecom.aladdin.swagger.pojo;importio.swagger.annotations.ApiModel;importio.swagger.annotations.ApiModelProperty;@ApiModel("用户实体类")publicclassUser{@ApiModelProperty(value ="用户名", example ="123123", required =true)privateString username;@ApiModelProperty(value ="密码", example ="aaa123", required =true)privateString password;...}
packagecom.aladdin.swagger.controller;importcom.aladdin.swagger.pojo.User;importio.swagger.annotations.*;importorg.springframework.http.MediaType;importorg.springframework.web.bind.annotation.*;@Api("Hello 控制类")@RestControllerpublicclassHelloController{@ApiOperation("测试query")@ApiResponses({@ApiResponse(code =1000, message ="操作成功"),@ApiResponse(code =9999, message ="系统异常"),@ApiResponse(code =8888, message ="权限不足")})@ApiImplicitParams({@ApiImplicitParam(paramType ="query", dataType ="String", name ="str", value ="字符串", required =true)})@GetMapping("/hello")publicStringhello(String str){return"Hello: "+ str;}@ApiOperation("测试path")@ApiImplicitParams({@ApiImplicitParam(paramType ="path", dataType ="Long", name ="id", value ="信息id", required =true)})@GetMapping("/hello2/{id}")publicStringhello2(@PathVariable("id")Long id){return"Hello: "+ id;}@ApiOperation("测试header")@ApiImplicitParams({@ApiImplicitParam(paramType ="header", dataType ="Long", name ="id", value ="信息id", required =true)})@GetMapping("/hello3")publicStringhello3(@RequestHeader("id")Long id){return"Hello: "+ id;}@ApiOperation("测试form")@ApiImplicitParams({@ApiImplicitParam(paramType ="form", dataType ="Long", name ="id", value ="信息id", required =true)})@PostMapping(value ="/hello4", consumes =MediaType.APPLICATION_FORM_URLENCODED_VALUE)publicStringhello4(@RequestParam("id")Long id){return"Hello: "+ id;}@ApiOperation("测试body")@ApiImplicitParams({@ApiImplicitParam(paramType ="body", dataType ="User", name ="user", value ="用户信息参数", required =true)})@PostMapping("/user")publicUseruser(@RequestBodyUser user){return user;}}

总结

  1. 可通过 Swagger 给一些比较难理解的属性或者接口增加注释信息;
  2. 接口文档实时更新;
  3. 可以在线测试。

注意:出于安全考虑,在正式发布的时候,关闭 Swagger,同时也会节省运行内存。


本文转载自: https://blog.csdn.net/weixin_52610802/article/details/126295620
版权归原作者 不负韶华 未来可期 所有, 如有侵权,请联系我们删除。

“Swagger 的使用”的评论:

还没有评论