Selaa lähdekoodia

优化权限控制逻辑 fix #164

zhouhao 4 vuotta sitten
vanhempi
commit
098016dbe4

+ 22 - 13
hsweb-authorization/hsweb-authorization-basic/src/main/java/org/hswebframework/web/authorization/basic/handler/DefaultAuthorizingHandler.java

@@ -155,10 +155,11 @@ public class DefaultAuthorizingHandler implements AuthorizingHandler {
         Set<String> actionsDef = definition.getActions();
         Set<String> rolesDef = definition.getRoles();
         Set<String> usersDef = definition.getUser();
-
+        boolean anyHandled = false;
 
         // 控制权限
-        if (!definition.getPermissions().isEmpty()) {
+        if (!permissionsDef.isEmpty()) {
+            anyHandled = true;
             if (logger.isInfoEnabled()) {
                 logger.info("执行权限控制:权限{},操作{}.",
                         permissionsDef,
@@ -191,23 +192,27 @@ public class DefaultAuthorizingHandler implements AuthorizingHandler {
                     CollectionUtils.isNotEmpty(permissions) :
                     //权限数量和配置的数量相同
                     permissions.size() == permissionsDef.size();
-        } else {
-            access = false;
         }
         //控制角色
         if (!rolesDef.isEmpty()) {
+
             Set<String> roleIds = authentication.getRoles().stream().map(Role::getId).collect(Collectors.toSet());
 
             Function<Predicate<String>, Boolean> func = logicalIsOr
                     ? roleIds.stream()::anyMatch
                     : roleIds.stream()::allMatch;
+            if (anyHandled) {
+                access = logicalIsOr
+                        ? access || func.apply(rolesDef::contains)
+                        : access && func.apply(rolesDef::contains);
+            } else {
+                access = func.apply(rolesDef::contains);
+            }
 
-            access = logicalIsOr
-                    ? access || func.apply(rolesDef::contains)
-                    : access && func.apply(rolesDef::contains);
             if (logger.isInfoEnabled()) {
                 logger.info("执行角色权限控制{},当前角色:{},限制角色:{}.", access ? "通过" : "拒绝", roleIds, rolesDef);
             }
+            anyHandled = true;
         }
         //控制用户
         if (!usersDef.isEmpty()) {
@@ -215,15 +220,19 @@ public class DefaultAuthorizingHandler implements AuthorizingHandler {
             Function<Predicate<String>, Boolean> func = logicalIsOr
                     ? usersDef.stream()::anyMatch
                     : usersDef.stream()::allMatch;
-            access = logicalIsOr
-                    ? access || func.apply(username::equals)
-                    : access && func.apply(username::equals);
+            if (anyHandled) {
+                access = logicalIsOr
+                        ? access || func.apply(username::equals)
+                        : access && func.apply(username::equals);
+            } else {
+                access = func.apply(username::equals);
+            }
             if (logger.isInfoEnabled()) {
                 logger.info("执行用户权限控制{},当前用户:{},限制用户:{}.", access ? "通过" : "拒绝", username, usersDef);
             }
-            if (!access) {
-                throw new AccessDenyException(definition.getMessage());
-            }
+        }
+        if (!access) {
+            throw new AccessDenyException(definition.getMessage());
         }
     }
 }

+ 30 - 5
hsweb-authorization/hsweb-authorization-basic/src/test/groovy/org/hswebframework/web/authorization/AuthorizeTests.java

@@ -41,6 +41,9 @@ public class AuthorizeTests {
     @Mock
     private MethodInterceptorContext handleRole;
 
+    @Mock
+    private MethodInterceptorContext handleEmpty;
+
     @Mock
     private Authentication authentication;
 
@@ -78,6 +81,10 @@ public class AuthorizeTests {
         when(handleRole.getParameter("paramEntity")).thenReturn(Optional.of(entity));
 
 
+        //mock MethodInterceptorContext
+        when(handleEmpty.getMethod()).thenReturn(TestClass.class.getMethod("handleEmpty"));
+        when(handleEmpty.getTarget()).thenReturn(testClass);
+
         //过滤字段
         AbstractDataAccessConfig fieldFilter = new SimpleFieldFilterDataAccessConfig("password", "salt");
         fieldFilter.setAction(Permission.ACTION_QUERY);
@@ -120,6 +127,20 @@ public class AuthorizeTests {
         authorizingContext.setDefinition(definition);
         authorizingContext.setParamContext(queryById);
 
+        handler.handRBAC(authorizingContext);
+    }
+
+    @Test
+    public void testIssue164() {
+        DefaultAuthorizingHandler handler = new DefaultAuthorizingHandler();
+
+        AuthorizeDefinition definition = parser.parse(handleRole.getTarget().getClass(), handleRole.getMethod());
+
+        AuthorizingContext authorizingContext = new AuthorizingContext();
+        authorizingContext.setAuthentication(authentication);
+        authorizingContext.setDefinition(definition);
+        authorizingContext.setParamContext(handleRole);
+
         try {
             handler.handRBAC(authorizingContext);
             Assert.fail("role access handle fail");
@@ -127,21 +148,20 @@ public class AuthorizeTests {
 
         }
     }
-
     @Test
-    public void testIssue164() {
+    public void testIssue164Empty() {
         DefaultAuthorizingHandler handler = new DefaultAuthorizingHandler();
 
-        AuthorizeDefinition definition = parser.parse(handleRole.getTarget().getClass(), handleRole.getMethod());
+        AuthorizeDefinition definition = parser.parse(handleEmpty.getTarget().getClass(), handleEmpty.getMethod());
 
         AuthorizingContext authorizingContext = new AuthorizingContext();
         authorizingContext.setAuthentication(authentication);
         authorizingContext.setDefinition(definition);
         authorizingContext.setParamContext(handleRole);
-
         handler.handRBAC(authorizingContext);
     }
 
+
     /**
      * 测试数据权限控制s
      */
@@ -218,11 +238,16 @@ public class AuthorizeTests {
         }
 
 
-        @Authorize(role = "admin")
+        @Authorize(role = "admin",merge = false)
         public void handleRoleDeny(QueryParamEntity paramEntity) {
             System.out.println(JSON.toJSON(paramEntity));
         }
 
+        @Authorize(merge = false)
+        public void handleEmpty() {
+
+        }
+
     }
 
     public interface TestClassSuper {