mirror of https://gitee.com/stylefeng/roses
【resource】资源模块加上viewFlag标识,用来区分控制器返回视图还是json,视图控制器默认以/view判定
parent
cb4a3126fb
commit
007194fb1e
|
@ -58,6 +58,14 @@ public @interface ApiResource {
|
||||||
*/
|
*/
|
||||||
boolean requiredPermission() default true;
|
boolean requiredPermission() default true;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否是视图类型:true-是,false-否
|
||||||
|
* 如果是视图类型,url需要以 '/view' 开头,
|
||||||
|
* 视图类型的接口会渲染出html界面,而不是json数据,
|
||||||
|
* 视图层一般会在前后端不分离项目出现
|
||||||
|
*/
|
||||||
|
boolean viewFlag() default false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 资源的响应类型,用于生成api文档
|
* 资源的响应类型,用于生成api文档
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -53,6 +53,14 @@ public @interface GetResource {
|
||||||
*/
|
*/
|
||||||
boolean requiredPermission() default true;
|
boolean requiredPermission() default true;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否是视图类型:true-是,false-否
|
||||||
|
* 如果是视图类型,url需要以 '/view' 开头,
|
||||||
|
* 视图类型的接口会渲染出html界面,而不是json数据,
|
||||||
|
* 视图层一般会在前后端不分离项目出现
|
||||||
|
*/
|
||||||
|
boolean viewFlag() default false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 资源的响应类型,用于生成api文档
|
* 资源的响应类型,用于生成api文档
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -53,6 +53,14 @@ public @interface PostResource {
|
||||||
*/
|
*/
|
||||||
boolean requiredPermission() default true;
|
boolean requiredPermission() default true;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否是视图类型:true-是,false-否
|
||||||
|
* 如果是视图类型,url需要以 '/view' 开头,
|
||||||
|
* 视图类型的接口会渲染出html界面,而不是json数据,
|
||||||
|
* 视图层一般会在前后端不分离项目出现
|
||||||
|
*/
|
||||||
|
boolean viewFlag() default false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 资源的响应类型,用于生成api文档
|
* 资源的响应类型,用于生成api文档
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -28,4 +28,9 @@ public interface ScannerConstants {
|
||||||
*/
|
*/
|
||||||
Integer REPORT_RESOURCE_LISTENER_SORT = 200;
|
Integer REPORT_RESOURCE_LISTENER_SORT = 200;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 视图类型的控制器url路径开头
|
||||||
|
*/
|
||||||
|
String VIEW_CONTROLLER_PATH_START_WITH = "/view";
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -64,6 +64,14 @@ public class ResourceDefinition implements Serializable {
|
||||||
*/
|
*/
|
||||||
private String ipAddress;
|
private String ipAddress;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否是视图类型:true-是,false-否
|
||||||
|
* 如果是视图类型,url需要以 '/view' 开头,
|
||||||
|
* 视图类型的接口会渲染出html界面,而不是json数据,
|
||||||
|
* 视图层一般会在前后端不分离项目出现
|
||||||
|
*/
|
||||||
|
private Boolean viewFlag;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 资源的请求路径
|
* 资源的请求路径
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -7,6 +7,7 @@ import cn.stylefeng.roses.kernel.resource.api.ResourceCollectorApi;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.annotation.ApiResource;
|
import cn.stylefeng.roses.kernel.resource.api.annotation.ApiResource;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.annotation.GetResource;
|
import cn.stylefeng.roses.kernel.resource.api.annotation.GetResource;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.annotation.PostResource;
|
import cn.stylefeng.roses.kernel.resource.api.annotation.PostResource;
|
||||||
|
import cn.stylefeng.roses.kernel.resource.api.constants.ScannerConstants;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.exception.ScannerException;
|
import cn.stylefeng.roses.kernel.resource.api.exception.ScannerException;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.holder.IpAddrHolder;
|
import cn.stylefeng.roses.kernel.resource.api.holder.IpAddrHolder;
|
||||||
import cn.stylefeng.roses.kernel.resource.api.pojo.resource.ResourceDefinition;
|
import cn.stylefeng.roses.kernel.resource.api.pojo.resource.ResourceDefinition;
|
||||||
|
@ -173,11 +174,11 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
* @author fengshuonan
|
* @author fengshuonan
|
||||||
* @date 2020/12/9 11:22
|
* @date 2020/12/9 11:22
|
||||||
*/
|
*/
|
||||||
private ResourceDefinition createDefinition(Class<?> clazz, Method method, Annotation apiResource) {
|
private ResourceDefinition createDefinition(Class<?> controllerClass, Method method, Annotation apiResource) {
|
||||||
ResourceDefinition resourceDefinition = new ResourceDefinition();
|
ResourceDefinition resourceDefinition = new ResourceDefinition();
|
||||||
|
|
||||||
// 填充控制器类的名称
|
// 填充控制器类的名称
|
||||||
resourceDefinition.setClassName(clazz.getSimpleName());
|
resourceDefinition.setClassName(controllerClass.getSimpleName());
|
||||||
|
|
||||||
// 填充方法名称
|
// 填充方法名称
|
||||||
resourceDefinition.setMethodName(method.getName());
|
resourceDefinition.setMethodName(method.getName());
|
||||||
|
@ -186,14 +187,14 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
String className = resourceDefinition.getClassName();
|
String className = resourceDefinition.getClassName();
|
||||||
int controllerIndex = className.indexOf("Controller");
|
int controllerIndex = className.indexOf("Controller");
|
||||||
if (controllerIndex == -1) {
|
if (controllerIndex == -1) {
|
||||||
String userTip = StrUtil.format(ERROR_CONTROLLER_NAME.getUserTip(), clazz.getName());
|
String userTip = StrUtil.format(ERROR_CONTROLLER_NAME.getUserTip(), controllerClass.getName());
|
||||||
throw new ScannerException(ERROR_CONTROLLER_NAME, userTip);
|
throw new ScannerException(ERROR_CONTROLLER_NAME, userTip);
|
||||||
}
|
}
|
||||||
String modular = className.substring(0, controllerIndex);
|
String modular = className.substring(0, controllerIndex);
|
||||||
resourceDefinition.setModularCode(modular);
|
resourceDefinition.setModularCode(modular);
|
||||||
|
|
||||||
// 填充模块的中文名称
|
// 填充模块的中文名称
|
||||||
ApiResource classApiAnnotation = clazz.getAnnotation(ApiResource.class);
|
ApiResource classApiAnnotation = controllerClass.getAnnotation(ApiResource.class);
|
||||||
resourceDefinition.setModularName(classApiAnnotation.name());
|
resourceDefinition.setModularName(classApiAnnotation.name());
|
||||||
|
|
||||||
// 如果控制器类上标识了appCode则应用标识上的appCode,如果控制器上没标识则用配置文件中的appCode
|
// 如果控制器类上标识了appCode则应用标识上的appCode,如果控制器上没标识则用配置文件中的appCode
|
||||||
|
@ -213,16 +214,33 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
|
|
||||||
// 填充其他属性
|
// 填充其他属性
|
||||||
String name = invokeAnnotationMethod(apiResource, "name", String.class);
|
String name = invokeAnnotationMethod(apiResource, "name", String.class);
|
||||||
String[] path = invokeAnnotationMethod(apiResource, "path", String[].class);
|
String[] methodPath = invokeAnnotationMethod(apiResource, "path", String[].class);
|
||||||
RequestMethod[] requestMethods = invokeAnnotationMethod(apiResource, "method", RequestMethod[].class);
|
RequestMethod[] requestMethods = invokeAnnotationMethod(apiResource, "method", RequestMethod[].class);
|
||||||
Boolean menuFlag = invokeAnnotationMethod(apiResource, "menuFlag", Boolean.class);
|
|
||||||
Boolean requiredLogin = invokeAnnotationMethod(apiResource, "requiredLogin", Boolean.class);
|
Boolean requiredLogin = invokeAnnotationMethod(apiResource, "requiredLogin", Boolean.class);
|
||||||
Boolean requiredPermission = invokeAnnotationMethod(apiResource, "requiredPermission", Boolean.class);
|
Boolean requiredPermission = invokeAnnotationMethod(apiResource, "requiredPermission", Boolean.class);
|
||||||
|
Boolean viewFlag = invokeAnnotationMethod(apiResource, "viewFlag", Boolean.class);
|
||||||
|
|
||||||
resourceDefinition.setRequiredLoginFlag(requiredLogin);
|
resourceDefinition.setRequiredLoginFlag(requiredLogin);
|
||||||
resourceDefinition.setRequiredPermissionFlag(requiredPermission);
|
resourceDefinition.setRequiredPermissionFlag(requiredPermission);
|
||||||
resourceDefinition.setResourceName(name);
|
resourceDefinition.setResourceName(name);
|
||||||
resourceDefinition.setUrl(getControllerClassRequestPath(clazz, path[0]));
|
|
||||||
|
// 根据控制器和控制器方法的path组装最后的url
|
||||||
|
String controllerMethodPath = createControllerPath(controllerClass, methodPath[0]);
|
||||||
|
resourceDefinition.setUrl(createFinalUrl(controllerMethodPath));
|
||||||
|
|
||||||
|
// 如果注解标识是视图类型,则判断该资源是视图类型(优先级最高)
|
||||||
|
if (viewFlag) {
|
||||||
|
resourceDefinition.setViewFlag(true);
|
||||||
|
}
|
||||||
|
// 如果资源url是以/view开头,则是视图类型
|
||||||
|
else if (StrUtil.isNotBlank(controllerMethodPath)) {
|
||||||
|
resourceDefinition.setViewFlag(controllerMethodPath.toLowerCase().startsWith(ScannerConstants.VIEW_CONTROLLER_PATH_START_WITH));
|
||||||
|
}
|
||||||
|
// 其他都是非视图类型
|
||||||
|
else {
|
||||||
|
resourceDefinition.setViewFlag(false);
|
||||||
|
}
|
||||||
|
|
||||||
StringBuilder methodNames = new StringBuilder();
|
StringBuilder methodNames = new StringBuilder();
|
||||||
for (RequestMethod requestMethod : requestMethods) {
|
for (RequestMethod requestMethod : requestMethods) {
|
||||||
methodNames.append(requestMethod.name()).append(",");
|
methodNames.append(requestMethod.name()).append(",");
|
||||||
|
@ -272,12 +290,12 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
/**
|
/**
|
||||||
* 根据控制器类上的RequestMapping注解的映射路径,以及方法上的路径,拼出整个接口的路径
|
* 根据控制器类上的RequestMapping注解的映射路径,以及方法上的路径,拼出整个接口的路径
|
||||||
*
|
*
|
||||||
* @param clazz 控制器类
|
* @param clazz 控制器的类
|
||||||
* @param path 当前被扫描接口的path路径
|
* @param path 控制器方法注解上的路径
|
||||||
* @author fengshuonan
|
* @author fengshuonan
|
||||||
* @date 2020/12/14 22:17
|
* @date 2021/1/5 14:43
|
||||||
*/
|
*/
|
||||||
private String getControllerClassRequestPath(Class<?> clazz, String path) {
|
private String createControllerPath(Class<?> clazz, String path) {
|
||||||
String controllerPath;
|
String controllerPath;
|
||||||
|
|
||||||
ApiResource controllerRequestMapping = clazz.getDeclaredAnnotation(ApiResource.class);
|
ApiResource controllerRequestMapping = clazz.getDeclaredAnnotation(ApiResource.class);
|
||||||
|
@ -292,6 +310,23 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 控制器上的path要以/开头
|
||||||
|
if (!controllerPath.startsWith("/")) {
|
||||||
|
controllerPath = "/" + controllerPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
return controllerPath + path;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 根据appCode和contextPath等,拼出整个接口的路径
|
||||||
|
*
|
||||||
|
* @param controllerMethodPath 控制器和控制器方法的path的组合
|
||||||
|
* @author fengshuonan
|
||||||
|
* @date 2020/12/14 22:17
|
||||||
|
*/
|
||||||
|
private String createFinalUrl(String controllerMethodPath) {
|
||||||
|
|
||||||
// 拼接最终url的时候,依据如下规则拼接:/appCode/contextPath/xxx
|
// 拼接最终url的时候,依据如下规则拼接:/appCode/contextPath/xxx
|
||||||
// 第一部分是appCode
|
// 第一部分是appCode
|
||||||
String appCode = "";
|
String appCode = "";
|
||||||
|
@ -306,7 +341,7 @@ public class ApiResourceScanner implements BeanPostProcessor {
|
||||||
}
|
}
|
||||||
|
|
||||||
// 依据如下规则拼接:/appCode/contextPath/xxx
|
// 依据如下规则拼接:/appCode/contextPath/xxx
|
||||||
String resultPath = appCode + contextPath + controllerPath + path;
|
String resultPath = appCode + contextPath + controllerMethodPath;
|
||||||
|
|
||||||
// 前缀多个左斜杠替换为一个
|
// 前缀多个左斜杠替换为一个
|
||||||
resultPath = resultPath.replaceAll("/+", "/");
|
resultPath = resultPath.replaceAll("/+", "/");
|
||||||
|
|
|
@ -78,6 +78,15 @@ public class SysResource extends BaseEntity {
|
||||||
@TableField("ip_address")
|
@TableField("ip_address")
|
||||||
private String ipAddress;
|
private String ipAddress;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 是否是视图类型:Y-是,N-否
|
||||||
|
* 如果是视图类型,url需要以 '/view' 开头,
|
||||||
|
* 视图类型的接口会渲染出html界面,而不是json数据,
|
||||||
|
* 视图层一般会在前后端不分离项目出现
|
||||||
|
*/
|
||||||
|
@TableField("view_flag")
|
||||||
|
private String viewFlag;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 资源url
|
* 资源url
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -9,7 +9,6 @@ import cn.stylefeng.roses.kernel.rule.enums.YesOrNotEnum;
|
||||||
import com.alibaba.fastjson.JSON;
|
import com.alibaba.fastjson.JSON;
|
||||||
import com.alibaba.fastjson.parser.Feature;
|
import com.alibaba.fastjson.parser.Feature;
|
||||||
import com.alibaba.fastjson.serializer.SerializerFeature;
|
import com.alibaba.fastjson.serializer.SerializerFeature;
|
||||||
import org.springframework.beans.BeanUtils;
|
|
||||||
|
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
|
@ -29,7 +28,7 @@ public class ResourceFactory {
|
||||||
*/
|
*/
|
||||||
public static SysResource createResource(ResourceDefinition resourceDefinition) {
|
public static SysResource createResource(ResourceDefinition resourceDefinition) {
|
||||||
SysResource resource = new SysResource();
|
SysResource resource = new SysResource();
|
||||||
BeanUtils.copyProperties(resourceDefinition, resource);
|
BeanUtil.copyProperties(resourceDefinition, resource, CopyOptions.create().ignoreError());
|
||||||
resource.setResourceCode(resourceDefinition.getResourceCode());
|
resource.setResourceCode(resourceDefinition.getResourceCode());
|
||||||
|
|
||||||
if (resourceDefinition.getRequiredLoginFlag()) {
|
if (resourceDefinition.getRequiredLoginFlag()) {
|
||||||
|
@ -44,6 +43,12 @@ public class ResourceFactory {
|
||||||
resource.setRequiredPermissionFlag(YesOrNotEnum.N.name());
|
resource.setRequiredPermissionFlag(YesOrNotEnum.N.name());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (resourceDefinition.getViewFlag()) {
|
||||||
|
resource.setViewFlag(YesOrNotEnum.Y.name());
|
||||||
|
} else {
|
||||||
|
resource.setViewFlag(YesOrNotEnum.N.name());
|
||||||
|
}
|
||||||
|
|
||||||
// 转化校验组
|
// 转化校验组
|
||||||
if (ObjectUtil.isNotEmpty(resourceDefinition.getValidateGroups())) {
|
if (ObjectUtil.isNotEmpty(resourceDefinition.getValidateGroups())) {
|
||||||
resource.setValidateGroups(JSON.toJSONString(resourceDefinition.getValidateGroups(), SerializerFeature.WriteClassName));
|
resource.setValidateGroups(JSON.toJSONString(resourceDefinition.getValidateGroups(), SerializerFeature.WriteClassName));
|
||||||
|
@ -81,6 +86,9 @@ public class ResourceFactory {
|
||||||
// 设置是否需要权限认证标识,Y为需要权限认证
|
// 设置是否需要权限认证标识,Y为需要权限认证
|
||||||
resourceDefinition.setRequiredPermissionFlag(YesOrNotEnum.Y.name().equals(sysResource.getRequiredPermissionFlag()));
|
resourceDefinition.setRequiredPermissionFlag(YesOrNotEnum.Y.name().equals(sysResource.getRequiredPermissionFlag()));
|
||||||
|
|
||||||
|
// 设置是否是视图类型
|
||||||
|
resourceDefinition.setViewFlag(YesOrNotEnum.Y.name().equals(sysResource.getViewFlag()));
|
||||||
|
|
||||||
// 转化校验组
|
// 转化校验组
|
||||||
if (ObjectUtil.isNotEmpty(sysResource.getValidateGroups())) {
|
if (ObjectUtil.isNotEmpty(sysResource.getValidateGroups())) {
|
||||||
resourceDefinition.setValidateGroups(JSON.parseObject(sysResource.getValidateGroups(), Set.class, Feature.SupportAutoType));
|
resourceDefinition.setValidateGroups(JSON.parseObject(sysResource.getValidateGroups(), Set.class, Feature.SupportAutoType));
|
||||||
|
|
Loading…
Reference in New Issue