文章目录
Spring boot 2.0 升级到 3.3.1 的相关问题 (三)
Swagger 2 升级到 Springdoc-openapi 2.6.0
必须要升级,老的swagger使用的servlet-api,在JDK21的环境下已经不支持,启动会报错。java.lang.TypeNotPresentException: Type javax.servlet.http.HttpServletRequest not present
问题介绍
1、注解变动的问题。
原来的注解全部废弃了,需要全部使用新的注解。
2、配置变动的问题。
原来的配置方式全部失效,需要使用新的配置方式
3、项目中的注解如何批量迁移的问题。
编写工具,对所有的代码进行注解的转换。
解决方案
参考官方资料:https://springdoc.org/#migrating-from-springfox
废弃之前的所有swagger相关的依赖,改为引入springdoc-openapi-starter-webmvc-ui
依赖
<dependency>
<groupId>org.springdoc</groupId>
<artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
<version>2.6.0</version>
</dependency>
注意不要参考网上的其他例子引入
springdoc-openapi-ui
这个依赖。
配置变动
原配置
//@Configuration
//@EnableSwagger2
@Slf4j
public class Swagger2Config {
@Value(value = "${spring.profiles.active}")
String environment;
@Value(value = "${spring.application.name}")
String applicationName;
@Value(value = "${spring.application.version}")
String applicationVersion;
@Value(value = "${spring.application.controller.packages}")
String[] controllerPackages;
String applicationDescription;
@Value(value = "${spring.application.description}")
private void setApplicationDescription(String applicationDescription) {
this.applicationDescription = "";
if (StringUtils.isBlank(applicationDescription)) {
return;
}
byte[] data = applicationDescription.getBytes(StandardCharsets.ISO_8859_1);
this.applicationDescription = new String(data, StandardCharsets.UTF_8);
}
/**
* 业务系统的固定请求头
*/
public List<RequestParameter> getTokenPar() {
RequestParameterBuilder tokenPar = new RequestParameterBuilder();
List<RequestParameter> pars = new ArrayList<>();
tokenPar
.name(FrameConstant.HTTP_HEADER_AUTHORIZATION)
.description("认证信息")
.in(ParameterType.HEADER)
.required(true)
.build();
pars.add(tokenPar.build());
RequestParameterBuilder clientTypePar = new RequestParameterBuilder();
clientTypePar.name(FrameConstant.HTTP_HEADER_CLIENT_TYPE)
.description("客户端版本类型")
.in(ParameterType.HEADER)
.required(true)
.build();
pars.add(clientTypePar.build());
RequestParameterBuilder clientVersionPar = new RequestParameterBuilder();
clientVersionPar.name(FrameConstant.HTTP_HEADER_CLIENT_VERSION)
.description("客户端版本号")
.in(ParameterType.HEADER)
.required(true)
.build();
pars.add(clientVersionPar.build());
return pars;
}
@Bean
public Docket createRestApi() {
ApiSelectorBuilder builder = new Docket(DocumentationType.SWAGGER_2)
.enable(("dev".equals(environment) || "test".equals(environment)))
.apiInfo(apiInfo())
.globalRequestParameters(getTokenPar())
.select();
if(controllerPackages!=null && controllerPackages.length >0){
Stream.of(controllerPackages)
.map(RequestHandlerSelectors::basePackage)
.forEach(builder::apis);
}
Docket api = builder
.paths(PathSelectors.any())
.build();
String serverServletContextPath = SpringContextUtil.getApplicationContext().getEnvironment().getProperty("server.servlet.context-path");
if(StringUtils.isNotBlank(serverServletContextPath)){
api.pathMapping(serverServletContextPath+"/");
}
return api;
}
private ApiInfo apiInfo() {
return new ApiInfoBuilder()
.title(applicationName)
.description(applicationDescription)
.termsOfServiceUrl("http://")
.version(applicationVersion).build();
}
}
新配置
/**
* SpringDoc的配置
*/
@Configuration @Slf4j public class SpringDocConfig {
@Value(value = "${spring.application.name}") String applicationName;
@Value(value = "${spring.application.version}") String applicationVersion;
@Value(value = "${spring.application.controller.packages}") String[] controllerPackages;
String applicationDescription;
@Value(value = "${spring.application.description}")
private void setApplicationDescription(String applicationDescription) {
this.applicationDescription = "";
if (StringUtils.isBlank(applicationDescription)) {
return;
}
byte[] data = applicationDescription.getBytes(StandardCharsets.ISO_8859_1);
this.applicationDescription = new String(data, StandardCharsets.UTF_8);
}
// @Bean
// @Profile("!prod")
// public OpenAPI customOpenAPI() {
// return new OpenAPI()
// .components(new Components()
// .addHeaders(FrameConstant.HTTP_HEADER_AUTHORIZATION, new Header().required(true).description("认证信息"))
// .addHeaders(FrameConstant.HTTP_HEADER_CLIENT_TYPE, new Header().required(true).description("客户端版本类型"))
// .addHeaders(FrameConstant.HTTP_HEADER_CLIENT_VERSION, new Header().required(true).description("客户端版本号"))
// )
// .info(new Info()
// .title(applicationName)
// .description(applicationDescription)
// .termsOfService("http://")
// .version(applicationVersion));
//
// }
@Bean @Profile("!prod") public GroupedOpenApi customOpenAPI() {
return GroupedOpenApi.builder()
.group(applicationName)
.packagesToScan(controllerPackages)
.addOperationCustomizer((operation, handlerMethod) -> {
operation.addParametersItem(
new HeaderParameter().name(FrameConstant.HTTP_HEADER_AUTHORIZATION).description("认证信息")
.required(true));
operation.addParametersItem(
new HeaderParameter().name(FrameConstant.HTTP_HEADER_CLIENT_TYPE).description("客户端版本类型")
.required(true));
operation.addParametersItem(
new HeaderParameter().name(FrameConstant.HTTP_HEADER_CLIENT_VERSION).description("客户端版本号")
.required(true));
return operation;
}).addOpenApiCustomizer(openApi -> openApi
.info(
new Info().title(applicationName).description(applicationDescription).version(applicationVersion)
)
)
.build();
}
}
注释掉的代码的方式也是可以的
批量注解转换工具
编写了一个独立的工具,使用JavaParser
来完成解析Java代码并修改更新Java的处理。最终将所有使用swagge2的注解的代码转换为SpringDoc的注解。
开源项目地址:https://gitcode.net/qiutongcunyi/swagger2springdoc-converter
该项目目前只做了我这边项目使用的一些注解的转换,如果你们有其他的注解需要转换,那么直接在这个项目基础上修改就可以了。
相关资料
SpringDoc官方文档:https://springdoc.org/#Introduction
本站资源均来自互联网,仅供研究学习,禁止违法使用和商用,产生法律纠纷本站概不负责!如果侵犯了您的权益请与我们联系!
转载请注明出处: 免费源码网-免费的源码资源网站 » Spring boot 2.0 升级到 3.3.1 的相关问题 (三)
发表评论 取消回复