Swagger2.X配置多种spec

前言

当前记录 swagger2spingboot 中配置多个 spec

其中包括:

  • yml 配置全局的 Docket
  • yml 配置局部的 Docket,不同的 spec 使用不同的描述
  • Docket 扫描基础包
  • SpringBoot自定义配置(ListMap

新建一个 module

主要依赖

<swagger.version>2.9.2</swagger.version>

1
2
3
4
5
6
7
8
9
10
11

<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<version>${swagger.version}</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>${swagger.version}</version>
</dependency>

自定义配置类

ApiInfoProperties

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
/**
* ApiInfoProperties
*
* @author maxzhao
* @date 2021-04-21 08:37
*/
@Configuration("apiInfoProperties")
@ConfigurationProperties(prefix = "gt.boot.swagger.api-info")
@Data
public class ApiInfoProperties {
/**
* 标题
*/
private String title;
/**
* 描述
*/
private String description;
/**
* 版本
*/
private String version;
/**
* 服务地址
*/
private String termsOfServiceUrl;
/**
* 许可
*/
private String license;
/**
* 许可地址
*/
private String licenseUrl;
/**
* 联系人
*/
private ContactProperties contact;
/**
* 供应商扩展
*/
private List<StringVendorExtension> vendorExtensions;
/**
* app into 扩展
* groupName-AppInfo
*/
private Map<String, ApiInfoProperties> docketAppInfos;
}

ContactProperties

1
2
3
4
5
6
7
8
9
10
11
12
/**
* swagger 联系人信息
*
* @author maxzhao
* @date 2021-04-21 08:42
*/
@Data
public class ContactProperties {
private String name;
private String url;
private String email;
}

Docket动态配置

ApiInfoConfig

当前类中包含了全局配置与局部配置。

getApiInfoByGroupName 获取局部配置,局部配置不存在,则使用全局配置。

InitializingBean作用在于初始化 bean 时,会在之前构建 ApiInfo 信息。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
import lombok.Data;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.Contact;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;

/**
* ApiInfoConfig
*
* @author maxzhao
* @date 2021-04-21 08:33
*/
@Configuration
@Data
public class ApiInfoConfig implements InitializingBean {
@Resource(name = "apiInfoProperties")
private ApiInfoProperties apiInfoProperties;
/**
* 构建 ApiInfo 信息的构建工具
*/
private static final ApiInfoBuilder apiInfoBuilder = new ApiInfoBuilder();
/**
* 构建 Docket 专属 ApiInfo 信息的构建工具
*/
private static final Map<String, ApiInfoBuilder> docketApiInfo = new HashMap<>();

@Override
public void afterPropertiesSet() throws Exception {
/*构建全局 ApiInfo*/
initGlobal(apiInfoBuilder, apiInfoProperties);
/*构建局部 ApiInfo */
Map<String, ApiInfoProperties> groupAppInfos = apiInfoProperties.getDocketAppInfos();
if (groupAppInfos == null || groupAppInfos.isEmpty()) {
return;
}
/*临时:Docket 专属 ApiInfo*/
ApiInfoBuilder apiInfoBuilderTemp;
/*循环专属 ApiInfo */
for (Map.Entry<String, ApiInfoProperties> docket : groupAppInfos.entrySet()) {
apiInfoBuilderTemp = new ApiInfoBuilder();
/*初始化*/
initGlobal(apiInfoBuilderTemp, docket.getValue());
/*结果*/
docketApiInfo.put(docket.getKey(), apiInfoBuilderTemp);
}
}

/**
* 获取 ApiInfo
*
* @param title 标题
* @return ApiInfo 对象
*/
public static ApiInfo getApiInfo(String title) {
return apiInfoBuilder.title(title).build();
}

/**
* 根据 GroupName 获取 ApiInfo
* <p>如果项目的配置文件中没有专属的配置,则会使用全局配置</p>
*
* @param groupName Docket 分组名称
* @return ApiInfo 对象
*/
public static ApiInfo getApiInfoByGroupName(String groupName) {
return Optional.ofNullable(docketApiInfo.get(groupName))
.orElse(apiInfoBuilder.title(groupName))
.build();
}

/**
* 获取 ApiInfo
*
* @param title 标题
* @param description 描述
* @return ApiInfo 对象
*/
public static ApiInfo getApiInfo(String title, String description) {
return apiInfoBuilder.title(title)
.description(description).build();
}


/**
* 构建 apiInfoBuilder 对象
*
* @param apiInfoBuilder apiInfo 对象
* @param apiInfoProperties apiInfo 配置的属性
*/
private static void initGlobal(ApiInfoBuilder apiInfoBuilder, ApiInfoProperties apiInfoProperties) {
ContactProperties contact = apiInfoProperties.getContact();
apiInfoBuilder.title(apiInfoProperties.getTitle())
.description(apiInfoProperties.getDescription());
/*创建人*/
if (contact != null) {
apiInfoBuilder.contact(new Contact(contact.getName(),
contact.getUrl(), contact.getEmail()));
}
apiInfoBuilder.version(apiInfoProperties.getVersion())
.termsOfServiceUrl(apiInfoProperties.getTermsOfServiceUrl())
.license(apiInfoProperties.getLicense())
.licenseUrl(apiInfoProperties.getLicenseUrl());
}
}

Docket 注册

下面注册一个 FileServer 的文档

1
2
3
4
5
6
7
8
9
10
11
12
13
14
@Bean("file-server")
public Docket fileServerApi(){
log.debug("=================== swagger2 docket create file-server =================");
// 指定api类型为swagger2
return new Docket(DocumentationType.SWAGGER_2)
.groupName("FileServer")
// 用于定义api文档汇总信息
.apiInfo(ApiInfoConfig.getApiInfoByGroupName("FileServer"))
.select()
//指定提供接口所在的基包 any 全部
.apis(RequestHandlerSelectors.basePackage("gt.maxzhao.boot.file.server"))
.paths(PathSelectors.any())
.build();
}

本文地址: https://github.com/maxzhao-it/blog/post/57187/