diff --git a/pom.xml b/pom.xml
index 929117de614be23a737d8fde5d5f44dc653fcdf8..6021fe54366f71a391a609b49485fbdd4e538d55 100644
--- a/pom.xml
+++ b/pom.xml
@@ -24,6 +24,15 @@ along with this program. If not, see .-->
neatlogic-framework
0.4.0.0-SNAPSHOT
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+
+ none
+
+
+
src/main/java
@@ -43,4 +52,4 @@ along with this program. If not, see .-->
-
\ No newline at end of file
+
diff --git a/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApi.java b/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApi.java
new file mode 100644
index 0000000000000000000000000000000000000000..a24609ad4017d12dd492013ee63e9a0a9e760170
--- /dev/null
+++ b/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApi.java
@@ -0,0 +1,10 @@
+package neatlogic.framework.annotationprocessor;
+
+import java.lang.annotation.*;
+
+@Target(ElementType.TYPE)
+@Retention(RetentionPolicy.RUNTIME)
+@Inherited
+public @interface NeatLogicApi {
+ String value() default "";
+}
diff --git a/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApiAnnotationProcessor.java b/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApiAnnotationProcessor.java
new file mode 100644
index 0000000000000000000000000000000000000000..3ec98b4ad70620dace2a7b5737975e008556a364
--- /dev/null
+++ b/src/main/java/neatlogic/framework/annotationprocessor/NeatLogicApiAnnotationProcessor.java
@@ -0,0 +1,130 @@
+package neatlogic.framework.annotationprocessor;
+
+import neatlogic.framework.restful.core.IApiComponent;
+import neatlogic.framework.restful.core.IBinaryStreamApiComponent;
+import neatlogic.framework.restful.core.IJsonStreamApiComponent;
+import neatlogic.framework.restful.core.IRawApiComponent;
+import org.apache.commons.collections4.CollectionUtils;
+
+import javax.annotation.processing.*;
+import javax.lang.model.SourceVersion;
+import javax.lang.model.element.AnnotationMirror;
+import javax.lang.model.element.Element;
+import javax.lang.model.element.TypeElement;
+import javax.lang.model.type.DeclaredType;
+import javax.lang.model.type.TypeKind;
+import javax.lang.model.type.TypeMirror;
+import javax.lang.model.util.ElementFilter;
+import javax.lang.model.util.Elements;
+import javax.lang.model.util.Types;
+import javax.tools.Diagnostic;
+import java.util.List;
+import java.util.Objects;
+import java.util.Set;
+
+@SupportedAnnotationTypes("neatlogic.framework.annotationprocessor.NeatLogicApi")
+@SupportedSourceVersion(SourceVersion.RELEASE_17)
+public class NeatLogicApiAnnotationProcessor extends AbstractProcessor {
+
+ @Override
+ public boolean process(Set extends TypeElement> annotations, RoundEnvironment roundEnv) {
+ if (annotations.isEmpty()) {
+ return false;
+ }
+ Elements elementUtils = processingEnv.getElementUtils();
+ Types typeUtils = processingEnv.getTypeUtils();
+ TypeElement componentTypeElement = processingEnv.getElementUtils().getTypeElement("org.springframework.stereotype.Component");
+ TypeElement serviceTypeElement = processingEnv.getElementUtils().getTypeElement("org.springframework.stereotype.Service");
+ TypeElement repositoryTypeElement = processingEnv.getElementUtils().getTypeElement("org.springframework.stereotype.Repository");
+ TypeElement controllerTypeElement = processingEnv.getElementUtils().getTypeElement("org.springframework.stereotype.Controller");
+ TypeElement authActionTypeElement = processingEnv.getElementUtils().getTypeElement("neatlogic.framework.auth.core.AuthAction");
+ TypeElement authActionsTypeElement = processingEnv.getElementUtils().getTypeElement("neatlogic.framework.auth.core.AuthActions");
+ TypeElement neatLogicApiTypeElement = elementUtils.getTypeElement("neatlogic.framework.annotationprocessor.NeatLogicApi");
+ Set extends Element> neatLogicApiElements = roundEnv.getElementsAnnotatedWith(neatLogicApiTypeElement);
+ Set neatLogicApiClasses = ElementFilter.typesIn(neatLogicApiElements);
+ if (componentTypeElement != null
+ && serviceTypeElement != null
+ && repositoryTypeElement != null
+ && controllerTypeElement != null
+ && authActionTypeElement != null
+ && authActionsTypeElement != null
+ && CollectionUtils.isNotEmpty(neatLogicApiClasses)
+ ) {
+ TypeElement apiComponentTypeElement = elementUtils.getTypeElement(IApiComponent.class.getName());
+ TypeElement binaryStreamApiComponentTypeElement = elementUtils.getTypeElement(IBinaryStreamApiComponent.class.getName());
+ TypeElement jsonStreamApiComponentTypeElement = elementUtils.getTypeElement(IJsonStreamApiComponent.class.getName());
+ TypeElement rawApiComponentTypeElement = elementUtils.getTypeElement(IRawApiComponent.class.getName());
+ TypeMirror apiComponentTypeMirror = apiComponentTypeElement.asType();
+ TypeMirror binaryStreamApiComponentTypeMirror = binaryStreamApiComponentTypeElement.asType();
+ TypeMirror jsonStreamApiComponentTypeMirror = jsonStreamApiComponentTypeElement.asType();
+ TypeMirror rawApiComponentTypeMirror = rawApiComponentTypeElement.asType();
+ for (TypeElement neatLogicApiClass : neatLogicApiClasses) {
+ if (implementsInterface(neatLogicApiClass, apiComponentTypeMirror, typeUtils)
+ || implementsInterface(neatLogicApiClass, binaryStreamApiComponentTypeMirror, typeUtils)
+ || implementsInterface(neatLogicApiClass, jsonStreamApiComponentTypeMirror, typeUtils)
+ || implementsInterface(neatLogicApiClass, rawApiComponentTypeMirror, typeUtils)
+ ) {
+ boolean isBean = false;
+ List extends AnnotationMirror> annotationMirrors = neatLogicApiClass.getAnnotationMirrors();
+ for (AnnotationMirror annotationMirror : annotationMirrors) {
+ Element element = annotationMirror.getAnnotationType().asElement();
+ if (Objects.equals(element, componentTypeElement)
+ || Objects.equals(element, serviceTypeElement)
+ || Objects.equals(element, repositoryTypeElement)
+ || Objects.equals(element, controllerTypeElement))
+ {
+ isBean = true;
+ break;
+ }
+ }
+ if (isBean) {
+ boolean hasAuthAction = false;
+ for (AnnotationMirror annotationMirror : annotationMirrors) {
+ Element element = annotationMirror.getAnnotationType().asElement();
+ if (Objects.equals(element, authActionTypeElement) || Objects.equals(element, authActionsTypeElement)) {
+ hasAuthAction = true;
+ break;
+ }
+ }
+ if (!hasAuthAction) {
+ processingEnv.getMessager().printMessage(
+ Diagnostic.Kind.ERROR,
+ neatLogicApiClass.getQualifiedName() + "接口类需要加上@AuthAction注解进行权限控制, 如果未创建权限类, 可以先临时加上@AuthAction(action = NoAuth.class)使得编译通过",
+ neatLogicApiClass
+ );
+ }
+ }
+ }
+ }
+ }
+
+ return true;
+ }
+
+ // 检查元素是否实现了指定的接口
+ private boolean implementsInterface(TypeElement typeElement, TypeMirror interfaceType, Types typeUtils) {
+ // 检查直接实现的接口
+ for (TypeMirror implementedInterface : typeElement.getInterfaces()) {
+ if (typeUtils.isSameType(implementedInterface, interfaceType)) {
+ return true;
+ }
+
+ // 检查接口继承关系
+ if (implementedInterface.getKind() == TypeKind.DECLARED) {
+ TypeElement interfaceElement = (TypeElement) ((DeclaredType) implementedInterface).asElement();
+ if (implementsInterface(interfaceElement, interfaceType, typeUtils)) {
+ return true;
+ }
+ }
+ }
+
+ // 检查父类的接口实现
+ TypeMirror superClass = typeElement.getSuperclass();
+ if (superClass.getKind() != TypeKind.NONE) {
+ TypeElement superClassElement = (TypeElement) ((DeclaredType) superClass).asElement();
+ return implementsInterface(superClassElement, interfaceType, typeUtils);
+ }
+
+ return false;
+ }
+}
diff --git a/src/main/java/neatlogic/framework/auth/core/AuthActionChecker.java b/src/main/java/neatlogic/framework/auth/core/AuthActionChecker.java
index 6844701a0325d263ba31fb2eee5f387fb29ca40f..cc1e88378783ada856e30ece3c5d5173ba053fc7 100644
--- a/src/main/java/neatlogic/framework/auth/core/AuthActionChecker.java
+++ b/src/main/java/neatlogic/framework/auth/core/AuthActionChecker.java
@@ -17,6 +17,7 @@ package neatlogic.framework.auth.core;
import neatlogic.framework.asynchronization.threadlocal.UserContext;
import neatlogic.framework.auth.init.MaintenanceMode;
+import neatlogic.framework.auth.label.NoAuth;
import neatlogic.framework.common.RootComponent;
import neatlogic.framework.common.config.Config;
import neatlogic.framework.common.constvalue.systemuser.SystemUserFactory;
@@ -130,6 +131,9 @@ public class AuthActionChecker {
if (CollectionUtils.isEmpty(actionList)) {
return false;
}
+ if (actionList.contains(NoAuth.class.getSimpleName())) {
+ return true;
+ }
//判断从数据库查询的用户权限是否满足
AuthenticationInfoVo authenticationInfoVo;
if (UserContext.get() != null) {
diff --git a/src/main/java/neatlogic/framework/auth/core/AuthFactory.java b/src/main/java/neatlogic/framework/auth/core/AuthFactory.java
index 3ac00e3879a20700017798a946914413e564a201..713a6769c0f1e8e4d1bdbe8111b4f02bb208aa3c 100644
--- a/src/main/java/neatlogic/framework/auth/core/AuthFactory.java
+++ b/src/main/java/neatlogic/framework/auth/core/AuthFactory.java
@@ -15,6 +15,7 @@ along with this program. If not, see .*/
package neatlogic.framework.auth.core;
+import neatlogic.framework.auth.label.NoAuth;
import neatlogic.framework.common.util.ModuleUtil;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.logging.Log;
@@ -37,7 +38,7 @@ public class AuthFactory {
for (Class extends AuthBase> c : authClass) {
try {
//排除抽象类
- if (!Modifier.isAbstract(c.getModifiers())) {
+ if (!Modifier.isAbstract(c.getModifiers()) && c != NoAuth.class) {
AuthBase authIns = c.newInstance();
if (ModuleUtil.getModuleGroup(authIns.getAuthGroup()) == null || (authIns instanceof AuthCSBase && ModuleUtil.isModuleInvalidated(authIns.getAuthModule()))) {
continue;
diff --git a/src/main/java/neatlogic/framework/restful/core/ApiValidateAndHelpBase.java b/src/main/java/neatlogic/framework/restful/core/ApiValidateAndHelpBase.java
index 863e101cb368a7f29fa28547613b11c2cd0c42b0..aee9cee9a2ebd3f356f7ae509a9640dd16ac8366 100644
--- a/src/main/java/neatlogic/framework/restful/core/ApiValidateAndHelpBase.java
+++ b/src/main/java/neatlogic/framework/restful/core/ApiValidateAndHelpBase.java
@@ -19,6 +19,7 @@ import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.serializer.SerializerFeature;
+import neatlogic.framework.annotationprocessor.NeatLogicApi;
import neatlogic.framework.asynchronization.threadlocal.TenantContext;
import neatlogic.framework.asynchronization.threadlocal.UserContext;
import neatlogic.framework.auth.core.AuthAction;
@@ -63,6 +64,7 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
+@NeatLogicApi
public class ApiValidateAndHelpBase {
private static final Logger logger = LoggerFactory.getLogger(ApiValidateAndHelpBase.class);
@@ -245,10 +247,6 @@ public class ApiValidateAndHelpBase {
private boolean isApiAuth(Class> apiClass, List authNameList, AuthAction[] actions) {
boolean isAuth = false;
for (AuthAction action : actions) {
- if (action.action() == NoAuth.class) {
- isAuth = true;
- break;
- }
if (StringUtils.isNotBlank(action.action().getSimpleName())) {
String actionName = action.action().getSimpleName();
// 判断用户角色是否拥有接口权限
diff --git a/src/main/java/neatlogic/framework/restful/core/privateapi/PrivateApiComponentFactory.java b/src/main/java/neatlogic/framework/restful/core/privateapi/PrivateApiComponentFactory.java
index 16abeaed2836985e675f71bf682ec3c708a77a9c..65178450d377946ced8469698c6c87a993f536b7 100644
--- a/src/main/java/neatlogic/framework/restful/core/privateapi/PrivateApiComponentFactory.java
+++ b/src/main/java/neatlogic/framework/restful/core/privateapi/PrivateApiComponentFactory.java
@@ -429,18 +429,19 @@ public class PrivateApiComponentFactory extends ModuleInitializedListenerBase {
logger.warn(clazz.getName() + "接口没有OperationType注解");
}
- //System.out.println(clazz.getSimpleName());
+// System.out.println(clazz.getSimpleName());
//跳过匿名接口
- if (component instanceof IApiComponent && ((IApiComponent) component).supportAnonymousAccess().isSupportAnonymousAccess()) {
- return;
- }
- if (!Objects.equals(context.getId(), "framework") && !Objects.equals(context.getId(), "tenant")) {
+// if (component instanceof IApiComponent && ((IApiComponent) component).supportAnonymousAccess().isSupportAnonymousAccess()) {
+// return;
+// }
+// if (!Objects.equals(context.getId(), "framework") && !Objects.equals(context.getId(), "tenant")) {
AuthAction authAction = clazz.getAnnotation(AuthAction.class);
AuthActions authActions = clazz.getAnnotation(AuthActions.class);
if (authAction == null && authActions == null) {
- logger.warn(clazz.getName() + "接口没有AuthAction注解");
+ System.err.println(clazz.getName() + "接口类需要加上@AuthAction注解进行权限控制, 如果未创建权限类, 可以先临时加上@AuthAction(action = NoAuth.class)使得应用服务正常启动");
+ System.exit(1);
}
- }
+// }
}
}
diff --git a/src/main/java/neatlogic/module/framework/restful/api/AuthSearchApi.java b/src/main/java/neatlogic/module/framework/restful/api/AuthSearchApi.java
index 43df14be50c4b6afcb98cf3dc217ccdcd1e170c1..0a2ad1c3890bf94fc6a2420df97678af456265b3 100755
--- a/src/main/java/neatlogic/module/framework/restful/api/AuthSearchApi.java
+++ b/src/main/java/neatlogic/module/framework/restful/api/AuthSearchApi.java
@@ -17,8 +17,10 @@ package neatlogic.module.framework.restful.api;
import com.alibaba.fastjson.JSONObject;
import neatlogic.framework.asynchronization.threadlocal.TenantContext;
+import neatlogic.framework.auth.core.AuthAction;
import neatlogic.framework.auth.core.AuthBase;
import neatlogic.framework.auth.core.AuthFactory;
+import neatlogic.framework.auth.label.NoAuth;
import neatlogic.framework.common.constvalue.ApiParamType;
import neatlogic.framework.common.util.ModuleUtil;
import neatlogic.framework.dto.AuthGroupVo;
@@ -33,7 +35,7 @@ import java.util.List;
import java.util.Map;
@Service
-
+@AuthAction(action = NoAuth.class)
@OperationType(type = OperationTypeEnum.SEARCH)
public class AuthSearchApi extends PrivateApiComponentBase {
diff --git a/src/main/java/neatlogic/module/framework/restful/api/LogoutApi.java b/src/main/java/neatlogic/module/framework/restful/api/LogoutApi.java
index 78b62502333a8e3cf2b22a9ac8c693c9c27f116a..df2ba33bd525ba93bae5c0140f80793c75c5b78f 100755
--- a/src/main/java/neatlogic/module/framework/restful/api/LogoutApi.java
+++ b/src/main/java/neatlogic/module/framework/restful/api/LogoutApi.java
@@ -16,6 +16,8 @@ along with this program. If not, see .*/
package neatlogic.module.framework.restful.api;
import com.alibaba.fastjson.JSONObject;
+import neatlogic.framework.auth.core.AuthAction;
+import neatlogic.framework.auth.label.NoAuth;
import neatlogic.framework.common.config.Config;
import neatlogic.framework.exception.login.LoginAuthNotFoundException;
import neatlogic.framework.filter.core.ILoginAuthHandler;
@@ -30,6 +32,7 @@ import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
@Service
+@AuthAction(action = NoAuth.class)
@OperationType(type = OperationTypeEnum.OPERATE)
public class LogoutApi extends PrivateApiComponentBase {
diff --git a/src/main/java/neatlogic/module/framework/restful/api/ModuleListApi.java b/src/main/java/neatlogic/module/framework/restful/api/ModuleListApi.java
index a6196cb7ef23a04edb1cef32d3059a6f4929796b..688f1af7cf7476bb734d11b4422d5790ba71b259 100644
--- a/src/main/java/neatlogic/module/framework/restful/api/ModuleListApi.java
+++ b/src/main/java/neatlogic/module/framework/restful/api/ModuleListApi.java
@@ -19,6 +19,8 @@ import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import neatlogic.framework.asynchronization.threadlocal.TenantContext;
import neatlogic.framework.asynchronization.threadlocal.UserContext;
+import neatlogic.framework.auth.core.AuthAction;
+import neatlogic.framework.auth.label.NoAuth;
import neatlogic.framework.common.constvalue.ApiParamType;
import neatlogic.framework.dao.mapper.UserMapper;
import neatlogic.framework.dto.AuthenticationInfoVo;
@@ -37,6 +39,7 @@ import java.util.List;
import java.util.Set;
@Service
+@AuthAction(action = NoAuth.class)
@OperationType(type = OperationTypeEnum.SEARCH)
public class ModuleListApi extends PrivateApiComponentBase {
@Autowired