🔨 移动common下部分模块至starter下

This commit is contained in:
b2baccline
2020-06-03 21:33:10 +08:00
parent a9f9788885
commit 9270a2b26f
75 changed files with 28 additions and 36 deletions

View File

@@ -0,0 +1,50 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>ballcat-starters</artifactId>
<groupId>com.hccake</groupId>
<version>${revision}</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>ballcat-spring-boot-starter-swagger</artifactId>
<dependencies>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<exclusions>
<exclusion>
<groupId>io.swagger</groupId>
<artifactId>swagger-models</artifactId>
</exclusion>
</exclusions>
<version>2.9.2</version>
</dependency>
<dependency>
<groupId>io.swagger</groupId>
<artifactId>swagger-models</artifactId>
<version>1.5.21</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-autoconfigure</artifactId>
</dependency>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<scope>compile</scope>
</dependency>
</dependencies>
</project>

View File

@@ -0,0 +1,62 @@
package com.hccake.ballcat.common.swagger;
import com.hccake.ballcat.common.swagger.property.SwaggerAggregatorProperties;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Import;
import org.springframework.context.annotation.Primary;
import org.springframework.util.CollectionUtils;
import springfox.documentation.swagger.web.InMemorySwaggerResourcesProvider;
import springfox.documentation.swagger.web.SwaggerResource;
import springfox.documentation.swagger.web.SwaggerResourcesProvider;
import java.util.ArrayList;
import java.util.List;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 20:03
*/
@Import(SwaggerConfiguration.class)
@ConditionalOnProperty(name = "swagger.enabled", havingValue = "true", matchIfMissing = true)
public class SwaggerAggregatorAutoConfiguration {
@Bean
@ConditionalOnMissingBean
public SwaggerAggregatorProperties swaggerAggregatorProperties() {
return new SwaggerAggregatorProperties();
}
/**
* 聚合文档
*
* @param defaultResourcesProvider
* @return
*/
@Primary
@Bean
@ConditionalOnBean(SwaggerAggregatorProperties.class)
public SwaggerResourcesProvider swaggerResourcesProvider(
InMemorySwaggerResourcesProvider defaultResourcesProvider,
SwaggerAggregatorProperties swaggerAggregatorProperties) {
return () -> {
// 聚合者自己的 Resources
List<SwaggerResource> resources = new ArrayList<>(defaultResourcesProvider.get());
// 提供者的 Resources
List<SwaggerResource> providerResources = swaggerAggregatorProperties.getProviderResources();
if (!CollectionUtils.isEmpty(providerResources)){
resources.addAll(providerResources);
}
return resources;
};
}
}

View File

@@ -0,0 +1,94 @@
package com.hccake.ballcat.common.swagger;
import com.hccake.ballcat.common.swagger.property.SwaggerProperties;
import io.swagger.annotations.ApiOperation;
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.*;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spi.service.contexts.SecurityContext;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 19:43
*/
@Configuration
@EnableSwagger2
public class SwaggerConfiguration {
@Bean
public SwaggerProperties swaggerProperties() {
return new SwaggerProperties();
}
@Bean
public Docket api(SwaggerProperties swaggerProperties) {
return new Docket(DocumentationType.SWAGGER_2)
.host(swaggerProperties.getHost())
.apiInfo(apiInfo(swaggerProperties))
.groupName(swaggerProperties.getGroupName())
.select()
.apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class))
.build()
.securitySchemes(Collections.singletonList(securitySchema()))
.securityContexts(Collections.singletonList(securityContext()))
.pathMapping("/");
}
/**
* 配置默认的全局鉴权策略的开关通过正则表达式进行匹配默认匹配所有URL
*
* @return
*/
private SecurityContext securityContext() {
return SecurityContext.builder()
.securityReferences(defaultAuth())
.forPaths(PathSelectors.regex(swaggerProperties().getAuthorization().getAuthRegex()))
.build();
}
/**
* 默认的全局鉴权策略
*
* @return
*/
private List<SecurityReference> defaultAuth() {
ArrayList<AuthorizationScope> authorizationScopeList = new ArrayList<>();
swaggerProperties().getAuthorization().getAuthorizationScopeList().forEach(authorizationScope -> authorizationScopeList.add(new AuthorizationScope(authorizationScope.getScope(), authorizationScope.getDescription())));
AuthorizationScope[] authorizationScopes = new AuthorizationScope[authorizationScopeList.size()];
return Collections.singletonList(SecurityReference.builder()
.reference(swaggerProperties().getAuthorization().getName())
.scopes(authorizationScopeList.toArray(authorizationScopes))
.build());
}
private OAuth securitySchema() {
ArrayList<AuthorizationScope> authorizationScopeList = new ArrayList<>();
swaggerProperties().getAuthorization().getAuthorizationScopeList().forEach(authorizationScope -> authorizationScopeList.add(new AuthorizationScope(authorizationScope.getScope(), authorizationScope.getDescription())));
ArrayList<GrantType> grantTypes = new ArrayList<>();
swaggerProperties().getAuthorization().getTokenUrlList().forEach(tokenUrl -> grantTypes.add(new ResourceOwnerPasswordCredentialsGrant(tokenUrl)));
return new OAuth(swaggerProperties().getAuthorization().getName(), authorizationScopeList, grantTypes);
}
private ApiInfo apiInfo(SwaggerProperties swaggerProperties) {
return new ApiInfoBuilder()
.title(swaggerProperties.getTitle())
.description(swaggerProperties.getDescription())
.license(swaggerProperties.getLicense())
.licenseUrl(swaggerProperties.getLicenseUrl())
.termsOfServiceUrl(swaggerProperties.getTermsOfServiceUrl())
.contact(new Contact(swaggerProperties.getContact().getName(), swaggerProperties.getContact().getUrl(), swaggerProperties.getContact().getEmail()))
.version(swaggerProperties.getVersion())
.build();
}
}

View File

@@ -0,0 +1,48 @@
package com.hccake.ballcat.common.swagger;
import com.hccake.ballcat.common.swagger.property.SwaggerProviderProperties;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Import;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;
import org.springframework.web.filter.CorsFilter;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 20:03
*/
@Import(SwaggerConfiguration.class)
@ConditionalOnProperty(name = "swagger.enabled", havingValue = "true", matchIfMissing = true)
public class SwaggerProviderAutoConfiguration {
@Bean
@ConditionalOnMissingBean
public SwaggerProviderProperties swaggerProviderProperties() {
return new SwaggerProviderProperties();
}
/**
* 允许swagger文档跨域访问
* 解决聚合文档导致的跨域问题
* @return
*/
@Bean
@ConditionalOnBean(SwaggerProviderProperties.class)
public FilterRegistrationBean corsFilter(SwaggerProviderProperties swaggerProviderProperties) {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true);
config.addAllowedHeader("*");
config.addAllowedMethod("*");
config.addAllowedOrigin(swaggerProviderProperties.getAggregatorOrigin());
source.registerCorsConfiguration("/v2/api-docs**", config);
FilterRegistrationBean bean = new FilterRegistrationBean(new CorsFilter(source));
bean.setOrder(0);
return bean;
}
}

View File

@@ -0,0 +1,20 @@
package com.hccake.ballcat.common.swagger.annotation;
import com.hccake.ballcat.common.swagger.SwaggerAggregatorAutoConfiguration;
import org.springframework.context.annotation.Import;
import java.lang.annotation.*;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 19:43
* 聚合者的swagger开启注解
*/
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@Import({SwaggerAggregatorAutoConfiguration.class})
public @interface EnableSwagger2Aggregator {
}

View File

@@ -0,0 +1,20 @@
package com.hccake.ballcat.common.swagger.annotation;
import com.hccake.ballcat.common.swagger.SwaggerProviderAutoConfiguration;
import org.springframework.context.annotation.Import;
import java.lang.annotation.*;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 19:43
* 提供者的swagger开启注解
*/
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@Import({SwaggerProviderAutoConfiguration.class})
public @interface EnableSwagger2Provider {
}

View File

@@ -0,0 +1,27 @@
package com.hccake.ballcat.common.swagger.constant;
import java.util.Arrays;
import java.util.List;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 20:03
*/
public final class SwaggerConstants {
private SwaggerConstants(){}
/**
* 默认的排除路径排除Spring Boot默认的错误处理路径和端点
*/
public static final List<String> DEFAULT_EXCLUDE_PATH = Arrays.asList("/error", "/actuator/**");
/**
* 默认扫描路径
*/
public static final String BASE_PATH = "/**";
/**
* 默认的文档提供路径
*/
public static final String API_URI = "/v2/api-docs";
}

View File

@@ -0,0 +1,23 @@
package com.hccake.ballcat.common.swagger.property;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import springfox.documentation.swagger.web.SwaggerResource;
import java.util.ArrayList;
import java.util.List;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 20:05
*/
@Data
@ConfigurationProperties("swagger.aggregator")
public class SwaggerAggregatorProperties {
/**
* 聚合文档源信息
*/
private List<SwaggerResource> providerResources = new ArrayList<>();
}

View File

@@ -0,0 +1,131 @@
package com.hccake.ballcat.common.swagger.property;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.boot.context.properties.ConfigurationProperties;
import java.util.ArrayList;
import java.util.List;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 19:37
*/
@Data
@ConfigurationProperties("swagger")
public class SwaggerProperties {
/**
* 是否开启swagger
*/
private Boolean enabled;
/**
* 分组名称
*/
private String groupName;
/**
* swagger会解析的包路径
**/
private String basePackage = "";
/**
* swagger会解析的url规则
**/
private List<String> basePath = new ArrayList<>();
/**
* 在basePath基础上需要排除的url规则
**/
private List<String> excludePath = new ArrayList<>();
/**
* 标题
**/
private String title = "";
/**
* 描述
**/
private String description = "";
/**
* 版本
**/
private String version = "";
/**
* 许可证
**/
private String license = "";
/**
* 许可证URL
**/
private String licenseUrl = "";
/**
* 服务条款URL
**/
private String termsOfServiceUrl = "";
/**
* host信息
**/
private String host = "";
/**
* 联系人信息
*/
private Contact contact = new Contact();
/**
* 全局统一鉴权配置
**/
private Authorization authorization = new Authorization();
@Data
@NoArgsConstructor
public static class Contact {
/**
* 联系人
**/
private String name = "";
/**
* 联系人url
**/
private String url = "";
/**
* 联系人email
**/
private String email = "";
}
@Data
@NoArgsConstructor
public static class Authorization {
/**
* 鉴权策略ID需要和SecurityReferences ID保持一致
*/
private String name = "";
/**
* 需要开启鉴权URL的正则
*/
private String authRegex = "^.*$";
/**
* 鉴权作用域列表
*/
private List<AuthorizationScope> authorizationScopeList = new ArrayList<>();
private List<String> tokenUrlList = new ArrayList<>();
}
@Data
@NoArgsConstructor
public static class AuthorizationScope {
/**
* 作用域名称
*/
private String scope = "";
/**
* 作用域描述
*/
private String description = "";
}
}

View File

@@ -0,0 +1,20 @@
package com.hccake.ballcat.common.swagger.property;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
/**
* @author Hccake
* @version 1.0
* @date 2019/11/1 20:05
*/
@Data
@ConfigurationProperties("swagger.provider")
public class SwaggerProviderProperties {
/**
* 聚合者的来源,用于控制跨域放行
*/
private String aggregatorOrigin = "*";
}