Swagger学习笔记

Swagger

学习目标:

  • 了解Swagger的作用和概念
  • 了解前后端分离
  • 在SpringBoot中继承Swagger

Swagger简介

前后端分离

Vue + SpringBoot

后端时代:

​ 前端只用管理静态页面(html),再交给后端。后端通过模板引擎(如jsp)将页面重构,后端是主力!

前后端分离时代:

  • 后端:后端控制层,服务层,数据访问层 【后端团队】

  • 前端:前端控制层,视图层 【前端团队】

    • 伪造后端数据,json。数据已经存在了,不需要后端,前端工程依旧可以跑起来。
  • 前后端如何交互?===> API

  • 前后端相对独立,松耦合;

  • 前后端甚至可以部署在不同服务器上。

产生一个问题:

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

  • 首先指定schema,实时更新API,降低集成风险;

  • 早些年:指定word计划文档;

  • 前后端分离:

    • 前端测试后端接口使用:postman
    • 后端提供接口,需要实时更新最新的消息及改动!

Swagger

  • 号称世界上最流行的API框架

  • Restful API文档在线自动生成工具=> API文档与API定义同步更新

  • 直接运行,可以在线测试API接口;

  • 支持多种语言:(java、php...)

官网:https://swagger.io/

在项目中使用Swagger需要springfox:

  • swagger2
  • ui

SpringBoot集成Swagger

目录结构:

1、新建springboot项目

2、导入依赖

<!-- https://mvnrepository.com/artifact/io.springfox/springfox-swagger2 -->
        <dependency>
            <groupId>io.springfox</groupId>
            <artifactId>springfox-swagger2</artifactId>
            <version>2.9.2</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、编写helloworld

4、配置Swagger===>Config

@Configuration
@EnableSwagger2      //开启swagger2
public class SwaggerConfig {

}

5、测试运行:http://localhost:8080/swagger-ui.html

配置Swagger

配置了Swagger的docket的bean实例

@Configuration
@EnableSwagger2      //开启swagger2
public class SwaggerConfig {

    //配置了swagger的docket的bean实例
    @Bean
    public Docket docket(){
        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo());
    }

    

配置swagger的信息

    //配置swagger信息ApiInfo
    private ApiInfo apiInfo(){
        
        //作者信息
        Contact CONTACT = new Contact("ztx", "https://www.cnblogs.com/", "123445@qq.com");
        
		//要返回的swagger信息=apiInfo
        return new ApiInfo("小帅哥的swaggerAPI文档",
                "这个帅哥确实帅",
                "1.0",
                "https://www.bilibili.com/video/BV1Y441197Lw?p=2",
                CONTACT,
                "Apache 2.0",
                "http://www.apache.org/licenses/LICENSE-2.0",
                new ArrayList());
    }
}

之前的swagger信息是默认的,以上代码是我们对swagger信息的重新定义!

自定义后的swagger信息,如下:

Swagger配置扫描接口

Docket.select

用法: .select() + ( .apis(xxx) / .path(xxx) ) + .build() 必须要和 .build() 方法搭配使用!!!

    //配置了swagger的docket的bean实例
    @Bean
    public Docket docket(){
        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                .select()
                //RequestHandlerSelectors,配置要扫描接口的方式
                //basePackage():指定要扫描的包
                        //.basePackage("com.ztx.swagger.controller")
                //withClassAnnotation():扫描类上的注解,参数是一个注解的反射对象
                        //.withClassAnnotation(RestController.class)
                //withMethodAnnotation():扫描方法上的注解
                        //.withMethodAnnotation(RequestMapping.class)
                //any():扫描全部,无参数
                //none():不扫描,无参数              
                .apis(RequestHandlerSelectors.basePackage("com.ztx.swagger.controller"))
                //path():过滤什么路径
                //.paths(PathSelectors.ant("/ztx/**"))
                .build();
    }

因为在配置扫描接口方式时,我们定义的是只扫描"com.ztx.swagger.controller"包下面的,所以页面中接口信息部分如下:

配置是否开启Swagger

    @Bean
    public Docket docket(){
        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                //enable:是否开启swagger,如果为false,则swagger不开启,不能在浏览器中访问到swagger页面
                .enable(false)
                .select()
                .apis(RequestHandlerSelectors.basePackage("com.ztx.swagger.controller"))
                .build();
    }

浏览器中访问不到swagger页面

问题:如何做到我只希望我的swagger在生产环境中使用,在发布时不使用?

  • 判断是不是生产环境 flag = false or flag = true
  • 注入enable(flag)

当前项目环境设为: 开发环境 !

设置开发环境和生产环境服务器端口号!

判断当前环境是否开发环境,从而决定是否开启swagger!

    @Bean  //获取当前环境需要用到environment对象
    public Docket docket(Environment environment){

        //设置要显示的Swagger环境,是否处于dev或test环境
        Profiles profiles = Profiles.of("dev","test");
        //通过environment.acceptsProfiles判断是否处在自己设定的环境当中
        boolean flag = environment.acceptsProfiles(profiles);

        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                //是否开启swagger
                .enable(flag)
                .select()
                .apis(RequestHandlerSelectors.basePackage("com.ztx.swagger.controller"))
                .build();
    }

可以发现swagger页面只有在开发环境下的8081端口才可以显示,在生产环境的8082端口无效:


配置swaggerAPI文档分组

当多人协作开发时,每个人负责各自不同的业务区,这时为了便于显示每个人的业务是否合规,就需要用到分组功能,一个docket对应一个人:

    @Bean   
    public Docket docket1(){
        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                .groupName("李华")
            	。。。。。
                .enable(false);
    }

    @Bean
    public Docket docket2(){
        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                .groupName("旺仔")
           		。。。。。
                .enable(true);
    }
    
    //配置了swagger的docket的bean实例
    @Bean
    public Docket docket(Environment environment){

        //设置要显示的Swagger环境
        Profiles profiles = Profiles.of("dev","test");
        //通过environment.acceptsProfiles判断是否处在自己设定的环境当中
        boolean flag = environment.acceptsProfiles(profiles);

        return new Docket(DocumentationType.SWAGGER_2)
                .apiInfo(apiInfo())
                .groupName("狂神")
                .enable(flag)
                .select()
                .apis(RequestHandlerSelectors.basePackage("com.ztx.swagger.controller"))
                .build();
    }

前端页面展示:(可以看到有三个定义的组,且每个组对应的swagger页面内容也是不同的)

配置文档注释

创建一个实体类User:

public class User {

    public String username;
    public String password;

}

在controller中添加如下方法:

    //只要我们的接口中,返回值中存在实体类,它就会被扫描到swagger中
    @PostMapping("/user")
    public User user(){
        return new User();

在User实体类添加Api相关注解:

@ApiModel("用户实体类")
public class User {

    @ApiModelProperty("用户名")
    public String username;
    @ApiModelProperty("密码")
    public String password;

}

加与没加Api注解的对比,如下图:


发现@Api注解 主要起到注释的作用!

在HelloController下使用Api注解:

@RestController
public class HelloController {

    @GetMapping("/hello")
    public String hello(){
        return "hello";
    }

    //只要我们的接口中,返回值中存在实体类,它就会被扫描到swagger中
    @PostMapping("/user")
    public User user(){
        return new User();
    }

    //Operation接口,不是放在类上,是方法上
    @ApiOperation("这是一个hello2方法")
    @GetMapping("/hello2")
    public String hello2(@ApiParam("用户名") String username){
        return "hello2"+username;
    }
}

前端页面显示:发现使用api注解的地方都出现了注释!!!

补充一点:

@Api(tags = "hello控制器")  //添加在类上,该控制器注释同样会出现在页面文档中,由于该处是后加的,故上面截图就没体现出来
@RestController
public class HelloController {....}

常用注解

Swagger的所有注解定义在io.swagger.annotations包下

下面列一些经常用到的,未列举出来的可以另行查阅说明:

Swagger注解 简单说明
@Api(tags = "xxx模块说明") 作用在模块类上
@ApiOperation("xxx接口说明") 作用在接口方法上
@ApiModel("xxxPOJO说明") 作用在模型类上:如VO、BO
@ApiModelProperty(value = "xxx属性说明",hidden = true) 作用在类方法和属性上,hidden设置为true可以隐藏该属性
@ApiParam("xxx参数说明") 作用在参数、方法和字段上,类似@ApiModelProperty

总结

  1. 我们可以通过swagger给一些比较难理解的属性或者接口,增加注释信息
  2. 接口文档实时更新
  3. 可以在线测试
posted @ 2020-06-17 14:55  大盘鸡嘹咋咧  阅读(366)  评论(0编辑  收藏  举报