Prechádzať zdrojové kódy

接口权限控制实现

zouguihou 2 rokov pred
rodič
commit
2bf076349a

+ 13 - 1
src/main/java/com/welampiot/controller/UserController.java

@@ -28,7 +28,7 @@ public class UserController {
      * @param vo
      * @return
      */
-    @RequestMapping(value = "/login",method = RequestMethod.POST)
+    @RequestMapping(value = "/userlogin",method = RequestMethod.POST)
     public BaseResult<UserDTO> login(@Valid LoginVO vo){
         vo.setPassword(MD5Utils.encoderMD5(vo.getPassword()));
         UserDTO user = userService.getUserByUserName(vo);
@@ -45,4 +45,16 @@ public class UserController {
         int num = userService.countUser();
         return BaseResult.success(num);
     }
+    @RequestMapping(value = "/doIt",method = RequestMethod.POST)
+    @PreAuthorize(value = "isAuthenticated()")//需要登录才可以访问
+    public BaseResult<?> doIt(){
+        int num = userService.countUser();
+        return BaseResult.success(num);
+    }
+    @RequestMapping(value = "/amazing",method = RequestMethod.POST)
+    @PreAuthorize(value = "isAuthenticated()")//需要登录才可以访问
+    public BaseResult<?> amazing(){
+        int num = userService.countUser();
+        return BaseResult.success(num);
+    }
 }

+ 5 - 1
src/main/java/com/welampiot/dao/UserDao.java

@@ -1,6 +1,8 @@
 package com.welampiot.dao;
 
 import com.welampiot.dto.MenuDTO;
+import com.welampiot.dto.PathDTO;
+import com.welampiot.dto.RoleDTO;
 import com.welampiot.dto.UserDTO;
 import com.welampiot.vo.LoginVO;
 import org.apache.ibatis.annotations.Param;
@@ -11,5 +13,7 @@ public interface UserDao {
     UserDTO getUserByUserName(LoginVO vo);
     UserDTO findUserByUserName(@Param("username") String username);
     UserDTO loadUserByUsername(@Param("username") String username);
-    List<MenuDTO> queryMenuList(List<String> idList);
+    List<MenuDTO> queryMenuList(@Param("username") String username);
+    List<PathDTO> queryUserGrantUrl(@Param("username") String username);
+    List<RoleDTO> queryUserRole(@Param("username") String username);
 }

+ 14 - 0
src/main/java/com/welampiot/dto/BaseDTO.java

@@ -0,0 +1,14 @@
+package com.welampiot.dto;
+
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.Date;
+@Data
+public class BaseDTO implements Serializable {
+    private int id;
+    private String createdBy;
+    private Date createdDate;
+    private String updatedBy;
+    private Date updatedDate;
+}

+ 9 - 0
src/main/java/com/welampiot/dto/PathDTO.java

@@ -0,0 +1,9 @@
+package com.welampiot.dto;
+
+import lombok.Data;
+
+@Data
+public class PathDTO extends BaseDTO {
+    private String url;
+    private String description;
+}

+ 9 - 0
src/main/java/com/welampiot/dto/RoleDTO.java

@@ -0,0 +1,9 @@
+package com.welampiot.dto;
+
+import lombok.Data;
+
+@Data
+public class RoleDTO extends BaseDTO{
+    private String roleName;
+    private String roleDescription;
+}

+ 1 - 0
src/main/java/com/welampiot/dto/UserDTO.java

@@ -16,6 +16,7 @@ public class UserDTO implements UserDetails{
     private String password;
     private int status;
     private String privilegeList;
+    private String url;
 
     @Override
     public Collection<? extends GrantedAuthority> getAuthorities() {

+ 1 - 1
src/main/java/com/welampiot/security/CustomizeAccessDecisionManager.java

@@ -19,7 +19,7 @@ public class CustomizeAccessDecisionManager implements AccessDecisionManager {
     @Override
     public void decide(Authentication authentication, Object o, Collection<ConfigAttribute> collection)
             throws AccessDeniedException, InsufficientAuthenticationException {
-//        Iterator<ConfigAttribute> iterator = collection.iterator();
+        Iterator<ConfigAttribute> iterator = collection.iterator();
 //        while (iterator.hasNext()) {
 //            ConfigAttribute ca = iterator.next();
 //            //当前请求需要的权限

+ 1 - 2
src/main/java/com/welampiot/security/CustomizeAuthenticationSuccessHandler.java

@@ -33,8 +33,7 @@ public class CustomizeAuthenticationSuccessHandler implements AuthenticationSucc
             throws IOException, ServletException {
         User userDetails = (User) SecurityContextHolder.getContext().getAuthentication().getPrincipal();
         UserDTO userDTO = userService.getUserByUserName(userDetails.getUsername());
-        List<String> idList = Arrays.asList(userDTO.getPrivilegeList().split(","));
-        List<MenuDTO> menuDTOList = userService.queryMenuList(idList);
+        List<MenuDTO> menuDTOList = userService.queryMenuList(userDTO.getUsername());
         List<MenuVO> voList = new ArrayList<>();
         for(MenuDTO dto:menuDTOList){
             MenuVO vo = new MenuVO();

+ 29 - 4
src/main/java/com/welampiot/security/CustomizeFilterInvocationSecurityMetadataSource.java

@@ -1,14 +1,22 @@
 package com.welampiot.security;
 
+import com.welampiot.common.BusinessException;
+import com.welampiot.common.ResultEnum;
+import com.welampiot.dto.PathDTO;
+import com.welampiot.dto.UserDTO;
 import com.welampiot.service.UserService;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.security.access.ConfigAttribute;
+import org.springframework.security.core.context.SecurityContextHolder;
+import org.springframework.security.core.userdetails.User;
 import org.springframework.security.web.FilterInvocation;
 import org.springframework.security.web.access.intercept.FilterInvocationSecurityMetadataSource;
 import org.springframework.stereotype.Component;
 import org.springframework.util.AntPathMatcher;
+import org.springframework.util.CollectionUtils;
 
 import java.util.Collection;
+import java.util.List;
 
 /**
  * 安全元数据源
@@ -23,12 +31,29 @@ public class CustomizeFilterInvocationSecurityMetadataSource implements FilterIn
     public Collection<ConfigAttribute> getAttributes(Object o) throws IllegalArgumentException {
         //获取请求地址
         String requestUrl = ((FilterInvocation) o).getRequestUrl();
+        if(requestUrl.equals("/error")){
+            return null;
+        }
+        Object user = SecurityContextHolder.getContext().getAuthentication().getPrincipal();
+        if(user instanceof String && user.equals("anonymousUser")){
+            //禁止匿名访问(禁止未登录访问)
+//            throw  new BusinessException(ResultEnum.USER_NOT_LOGIN);
+            return null;
+        }
+        User userDetails = (User) user;
         //查询具体某个接口的权限
-//        List<SysPermission> permissionList =  sysPermissionService.selectListByPath(requestUrl);
-//        if(permissionList == null || permissionList.size() == 0){
+        List<PathDTO> permissionList = userService.queryUserGrantUrl(userDetails.getUsername());
+        if(CollectionUtils.isEmpty(permissionList)){
             //请求路径没有配置权限,表明该请求接口可以任意访问
-            return null;
-//        }
+//            return null;
+            throw new BusinessException(ResultEnum.NOT_AUTH);
+        }
+        PathDTO path = permissionList.stream().filter(e->e.getUrl().equals(requestUrl)).findFirst().orElse(null);
+        if(path==null){
+            throw new BusinessException(ResultEnum.NOT_AUTH);
+        }
+        //表明该请求接口可以访问
+        return null;
 //        String[] attributes = new String[permissionList.size()];
 //        for(int i = 0;i<permissionList.size();i++){
 //            attributes[i] = permissionList.get(i).getPermissionCode();

+ 1 - 1
src/main/java/com/welampiot/security/WebSecurityConfig.java

@@ -76,7 +76,7 @@ public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
     @Override
     protected void configure(HttpSecurity http) throws Exception {
         http.cors().and().csrf().disable();
-        http.authorizeRequests().antMatchers("/login").anonymous().anyRequest().authenticated().
+        http.authorizeRequests().antMatchers("/login").permitAll().anyRequest().authenticated().
 //                antMatchers("/login").anonymous().
 //                antMatchers("/**").fullyAuthenticated().
                         withObjectPostProcessor(new ObjectPostProcessor<FilterSecurityInterceptor>() {

+ 3 - 1
src/main/java/com/welampiot/service/UserService.java

@@ -1,6 +1,7 @@
 package com.welampiot.service;
 
 import com.welampiot.dto.MenuDTO;
+import com.welampiot.dto.PathDTO;
 import com.welampiot.dto.UserDTO;
 import com.welampiot.vo.LoginVO;
 
@@ -9,6 +10,7 @@ import java.util.List;
 public interface UserService {
     UserDTO getUserByUserName(LoginVO vo);
     UserDTO getUserByUserName(String username);
-    List<MenuDTO> queryMenuList(List<String> list);
+    List<MenuDTO> queryMenuList(String username);
     int countUser();
+    List<PathDTO> queryUserGrantUrl(String username);
 }

+ 5 - 4
src/main/java/com/welampiot/service/impl/UserDetailsServiceImpl.java

@@ -3,6 +3,7 @@ package com.welampiot.service.impl;
 import com.welampiot.common.BusinessException;
 import com.welampiot.common.ResultEnum;
 import com.welampiot.dao.UserDao;
+import com.welampiot.dto.RoleDTO;
 import com.welampiot.dto.UserDTO;
 import org.apache.commons.lang3.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -31,12 +32,12 @@ public class UserDetailsServiceImpl implements UserDetailsService {
         if (user == null) {
             throw new BusinessException(ResultEnum.USERNAME_ERROR);
         }
-        List<GrantedAuthority> grantedAuthorities = new ArrayList<>();
         //获取该用户所拥有的权限
-        List<String> list = Arrays.asList(user.getPrivilegeList().split(","));
+        List<RoleDTO> urlList = userDao.queryUserRole(username);
+        List<GrantedAuthority> grantedAuthorities = new ArrayList<>();
         // 声明用户授权
-        list.forEach(sysPermission -> {
-            GrantedAuthority grantedAuthority = new SimpleGrantedAuthority(sysPermission);
+        urlList.forEach(role -> {
+            GrantedAuthority grantedAuthority = new SimpleGrantedAuthority(role.getRoleName());
             grantedAuthorities.add(grantedAuthority);
         });
         return new User(username,user.getPassword(),true,true,true,true,grantedAuthorities);

+ 9 - 3
src/main/java/com/welampiot/service/impl/UserServiceImpl.java

@@ -2,6 +2,7 @@ package com.welampiot.service.impl;
 
 import com.welampiot.dao.UserDao;
 import com.welampiot.dto.MenuDTO;
+import com.welampiot.dto.PathDTO;
 import com.welampiot.dto.UserDTO;
 import com.welampiot.service.UserService;
 import com.welampiot.vo.LoginVO;
@@ -27,16 +28,21 @@ public class UserServiceImpl implements UserService {
 
     /**
      * 查询菜单
-     * @param list
+     * @param username
      * @return
      */
     @Override
-    public List<MenuDTO> queryMenuList(List<String> list) {
-        return userDao.queryMenuList(list);
+    public List<MenuDTO> queryMenuList(String username) {
+        return userDao.queryMenuList(username);
     }
 
     @Override
     public int countUser() {
         return 0;
     }
+
+    @Override
+    public List<PathDTO> queryUserGrantUrl(String username) {
+        return userDao.queryUserGrantUrl(username);
+    }
 }

+ 1 - 1
src/main/resources/application.yml

@@ -7,7 +7,7 @@ spring:
   application:
     name: welampiot
   datasource:
-    driver-class-name: com.mysql.jdbc.Driver
+#    driver-class-name: com.mysql.jdbc.Driver
     url: jdbc:mysql://139.196.213.241:3306/welampiot?characterEncoding=utf-8&useSSL=false
     username: welampiot
     password: welampiot@2023

+ 42 - 2
src/main/resources/mapper/UserMapper.xml

@@ -12,10 +12,50 @@
         select username,role,status,privilege_list privilegeList from user where username=#{username,jdbcType=VARCHAR}
     </select>
     <select id="queryMenuList" parameterType="list" resultType="com.welampiot.dto.MenuDTO">
-        select id,parentid parentId,name,en_name enName,ru_name ruName,level,action from privilnode where status=1
+        <!--select id,parentid parentId,name,en_name enName,ru_name ruName,level,action from privilnode where status=1
         and id in
         <foreach collection="list" item="id" separator="," open="(" close=")">
             id
-        </foreach>
+        </foreach>-->
+        SELECT
+        p.id,
+        p.parentid parentId,
+        p.`level`,
+        p.`name`,
+        p.en_name enName,
+        p.ru_name
+        FROM
+        user u
+        LEFT JOIN t_user_role_relation ur ON u.id = ur.user_id
+        LEFT JOIN t_role_menu_relation rm ON ur.role_id = rm.role_id
+        LEFT JOIN privilnode p ON rm.menu_id = p.id
+        WHERE
+        u.username=#{username,jdbcType=VARCHAR}
+    </select>
+
+    <select id="queryUserGrantUrl" resultType="com.welampiot.dto.PathDTO">
+        SELECT
+        r.url,
+        r.description
+        FROM
+        user u
+        LEFT JOIN t_user_role_relation ur ON u.id = ur.user_id
+        LEFT JOIN t_role_menu_relation rm ON ur.role_id = rm.role_id
+        LEFT JOIN t_menu_path_relation mp ON rm.menu_id = mp.menu_id
+        LEFT JOIN t_request_path r ON mp.path_id = r.id
+        WHERE
+        u.username=#{username,jdbcType=VARCHAR}
+    </select>
+
+    <select id="queryUserRole" resultType="com.welampiot.dto.RoleDTO">
+        SELECT
+        r.role_name roleName,
+        r.role_description roleDescription
+        FROM
+        user u
+        LEFT JOIN t_user_role_relation ur ON u.id = ur.user_id
+        LEFT JOIN t_role r ON ur.role_id = r.id
+        WHERE
+        u.username = #{username,jdbcType=VARCHAR};
     </select>
 </mapper>