Swagger-UI 是 HTML、Javascript、CSS 的一个集合,可以动态地根据注解生成在线 Api 文档;swagger-bootstrap-UI 则可以美化 swagger-ui,页面更清爽!本篇就是实现 SpringBoot 整合 Swagger3 实现在线 Api 文档。
项目源码实现前分支地址:https://toscode.gitee.com/li_ziheng/lizhengi-samples/tree/feature%2Fspring-boot-1.0.1/
项目源码实现后分支地址:https://toscode.gitee.com/li_ziheng/lizhengi-samples/tree/feature%2Fspring-boot-1.0.2/
~
本篇内容包括:项目介绍与条件准备、项目搭建与构造、效果验证
@Api 注解:用于修饰 Controller 类,生成 Controller 相关文档信息;@ApiOperation 注解:用于修饰 Controller 类中的方法,生成接口方法相关文档信息;@ApiParam 注解:用于修饰接口中的参数,生成接口参数相关文档信息;@ApiModelProperty 注解:用于修饰实体类的属性,当实体类是请求参数或返回结果时,直接生成相关文档信息。├── config — 配置文件POJO
├── controller — 控制层(将请求通过 url 匹配,分配到不同的接收器/方法进行处理,然后返回结果)
├── service — 服务层接口
└── impl — 服务层实现
├── mapper — 数据访问层,与数据库交互为 service 提供接口
├── entity — 实体对象
├── converter — 实体对象转换器
├── dto — 持久层需要的实体对象(用于服务层与持久层之间的数据传输对象)
└── vo — 视图层需要的实体对象(用于服务层与视图层之间的数据传输对象)
├── utils — 工具类
└── Application.java — 入口启动类
# 添加项目 maven 依赖,pom.xml 文件添加内容如下:
<!--Swagger-UI API文档生产工具--><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger2</artifactId><version>2.7.0</version></dependency><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger-ui</artifactId><version>2.7.0</version></dependency><!--Swagger-UI 优化界面UI --><dependency><groupId>com.github.xiaoymin</groupId><artifactId>swagger-bootstrap-ui</artifactId><version>1.9.6</version></dependency>
# 启动类添加 @EnableWebMvc 注解
package com.lizhengi;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;/*** @author lizhengi*/
@SpringBootApplication
@EnableWebMvc
public class LizhengiSampleSpringBootApplication {public static void main(String[] args) {SpringApplication.run(LizhengiSampleSpringBootApplication.class, args);}}
# Swagger2 API 文档的配置
package com.lizhengi.config;import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;/*** @author liziheng* @version 1.0.0* @description Swagger2 API 文档的配置* @date 2022-12-09 12:12 上午**/
@Configuration
@EnableSwagger2
public class Swagger2Config {@Beanpublic Docket createRestApi() {return new Docket(DocumentationType.SWAGGER_2).apiInfo(apiInfo()).select()//为当前包下controller生成API文档.apis(RequestHandlerSelectors.basePackage("com.lizhengi.controller"))//为有@Api注解的Controller生成API文档
// .apis(RequestHandlerSelectors.withClassAnnotation(Api.class))//为有@ApiOperation注解的方法生成API文档
// .apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class)).paths(PathSelectors.any()).build();}private ApiInfo apiInfo() {return new ApiInfoBuilder().title("SwaggerUI演示").description("SwaggerUI演示").contact("lizhengi").version("1.0").build();}
}
# Swagger3Config Swagger3 API 文档的配置
package com.lizhengi.config;import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.ReflectionUtils;
import org.springframework.web.servlet.mvc.method.RequestMappingInfoHandlerMapping;import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.Contact;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.spring.web.plugins.WebFluxRequestHandlerProvider;
import springfox.documentation.spring.web.plugins.WebMvcRequestHandlerProvider;import java.lang.reflect.Field;
import java.util.Collections;
import java.util.List;
import java.util.stream.Collectors;/*** @author liziheng* @version 1.0.0* @description Swagger3 API 文档的配置* @date 2022-12-09 03:12 上午**/
@Configuration
public class Swagger3Config {/*** API 文档信息** @return -*/@Beanpublic Docket api() {// 自动生成文档接口:http://localhost:8080/v3/api-docs// API接口文档界面:http://localhost:8080/swagger-ui/index.html// Swagger UI 界面:http://localhost:8080/doc.htmlreturn new Docket(DocumentationType.SWAGGER_2).apiInfo(apiInfo()).select().apis(RequestHandlerSelectors.basePackage("com.liziheng.demo.controller")).paths(PathSelectors.regex("/article/*.*|/api/v1/*.*|/*.*")).build();}private ApiInfo apiInfo() {return new ApiInfo("Swagger API 文档","后台管理系统相关的接口","v1","协议地址",new Contact("li", "https://github.com/", "@163.com"),"MIT License", "http://opensource.org/licenses/MIT",Collections.emptyList());}/*** 解决swagger在springboot2.7以后的空指针异常** @return -*/@Beanpublic static BeanPostProcessor springfoxHandlerProviderBeanPostProcessor() {return new BeanPostProcessor() {@Overridepublic Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {if (bean instanceof WebMvcRequestHandlerProvider || bean instanceof WebFluxRequestHandlerProvider) {customizeSpringfoxHandlerMappings(getHandlerMappings(bean));}return bean;}private <T extends RequestMappingInfoHandlerMapping> void customizeSpringfoxHandlerMappings(List<T> mappings) {List<T> copy = mappings.stream().filter(mapping -> mapping.getPatternParser() == null).collect(Collectors.toList());mappings.clear();mappings.addAll(copy);}@SuppressWarnings("unchecked")private List<RequestMappingInfoHandlerMapping> getHandlerMappings(Object bean) {try {Field field = ReflectionUtils.findField(bean.getClass(), "handlerMappings");assert field != null;field.setAccessible(true);return (List<RequestMappingInfoHandlerMapping>) field.get(bean);} catch (IllegalArgumentException | IllegalAccessException e) {throw new IllegalStateException(e);}}};}
}
# EventVO Event-事件 视图层实体对象实现
package com.lizhengi.entity.vo;import io.swagger.annotations.ApiModelProperty;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;import java.util.List;/*** @author liziheng* @version 1.0.0* @description Event-事件 视图层实体对象实现* @date 2022-12-09 0:58 上午**/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class EventVO {/*** 事件名称*/@ApiModelProperty("事件名称")private String eventName;/*** 事件类型*/@ApiModelProperty("事件类型")private String eventType;/*** 事件发生时间*/@ApiModelProperty("事件发生时间")private String eventDate;/*** 事件地点*/@ApiModelProperty("事件地点")private String eventLocation;/*** 事件人物** @see CharacterVO*/@ApiModelProperty("事件人物")private List<CharacterVO> characters;/*** 事件描述*/@ApiModelProperty("事件描述")private String eventDescription;
}
# CharacterVO Character-人物 视图层实体对象实现
package com.lizhengi.entity.vo;import io.swagger.annotations.ApiModelProperty;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;/*** @author liziheng* @version 1.0.0* @description Character-人物 视图层实体对象实现* @date 2022-12-09 00:59 上午**/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class CharacterVO {@ApiModelProperty("人物名称")private String name;@ApiModelProperty("人物介绍")private String profile;@ApiModelProperty("人物登场时间(负数表示公元前)")private Integer appearanceDate;
}
# EventController Event-事件 Controller
package com.lizhengi.controller;import com.lizhengi.entity.vo.EventVO;
import com.lizhengi.service.impl.EventServiceImpl;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;import java.util.List;/*** @author liziheng* @version 1.0.0* @description Event-事件 Controller* @date 2022-12-07 8:17 下午**/
@Api(tags = "EventController")
@RestController
@RequestMapping("/api/lizhengi/event")
public class EventController {EventServiceImpl eventService;@Autowiredpublic void setEventService(EventServiceImpl eventService) {this.eventService = eventService;}@ApiOperation("全量获取事件信息")@RequestMapping(path = {"/list"}, method = RequestMethod.GET)public List<EventVO> getEventDtoList() {return eventService.getEventDtoList();}
}
# SwaggerPrintConfig 控制台输出 Swagger 接口文档地址
package com.lizhengi.config;import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.web.context.WebServerInitializedEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.stereotype.Component;import java.net.Inet4Address;
import java.net.UnknownHostException;/*** @author liziheng* @version 1.0.0* @description 控制台输出 Swagger 接口文档地址* @date 2022-12-09 3:28 上午**/
@Component
@Slf4j
public class SwaggerPrintConfig implements ApplicationListener<WebServerInitializedEvent> {@Overridepublic void onApplicationEvent(WebServerInitializedEvent event) {try {// 获取IPString hostAddress = Inet4Address.getLocalHost().getHostAddress();// 获取端口号int port = event.getWebServer().getPort();// 获取应用名String applicationName = event.getApplicationContext().getApplicationName();// 打印 swagger 文档地址log.info("项目启动启动成功!swagger3 接口文档地址: http://" + hostAddress + ":" + port + applicationName + "/swagger-ui/index.html");// 打印 swagger2 文档地址log.info("项目启动启动成功!swaggerUI 接口文档地址: http://" + hostAddress + ":" + port + applicationName + "/doc.html");} catch (UnknownHostException e) {e.printStackTrace();}}
}

