java - 如何为 Controller 中的许多方法添加权限检查? (过滤器、 Action )

标签 java spring-boot spring-mvc aop dry

我在许多方法的开头有以下内容。

    if ((user.privilege & User.Privilege.WRITE) == 0) {
        session.setAttribute("alert", "You do not have permission to save.");
        return new ModelAndView("redirect:/admin/home");
    }

如何提取它并将其放入一个单独的方法中,该方法在许多其他 Controller 方法之前调用,类似于 Ruby on Rails before_action :validate_privilege, [:save, :weekly_report, ...]?

我在文档中找到了这个,但它没有给出任何示例。

https://docs.spring.io/spring-boot/docs/1.5.19.RELEASE/reference/htmlsingle/#boot-features-embedded-container-servlets-filters-listeners

<小时/>

我根据@Deadpool的回答找到了一种方法。看起来它比简单的注释更复杂。

@Bean
public GenericFilterBean beforeAction() {
    String[] actions = new String[]{"/admin/censor", "/admin/weekly-report", "/admin/email-blast-submit"};
    return new GenericFilterBean() {
        @Override
        public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
            HttpServletRequest req = (HttpServletRequest) request;
//              System.out.println("requestURI:"+req.getRequestURI());
            boolean found = Arrays.stream(actions).anyMatch(req.getRequestURI()::equals);
            if (found) {
                User user = (User) req.getSession().getAttribute("user");
                if (user != null && (user.privilege & User.Privilege.WRITE) == 0) {
                    req.getSession().setAttribute("alert", "You do not have permission to save.");
                    HttpServletResponse res = (HttpServletResponse) response;
                    res.sendRedirect("/admin/home");
                    return;
                }
            }
            chain.doFilter(request, response);
        }
    };
}
<小时/>

对于使用 OAuth2 的 API,我使用了

@Override
public ResponseEntity<...> delete(Principal principal, @RequestBody ...) throws ApiException {
    isAuthorized(principal, "ROLE_USER");
    ...

/** If not authorized, throw ApiException. */
private void isAuthorized(Principal principal, String role) throws ApiException {
    OauthClientDetail cd = userMapper.getOauthClientDetails(principal.getName());
    if (cd == null || cd.authorities == null || !cd.authorities.equals(role)) {
        throw new ApiException(HttpStatus.UNAUTHORIZED, ...);
    }
}

(ApiException、OauthClientDetail (POJO) 和 UserMapper (MyBatis) 是自定义类。)

最佳答案

如果您正在寻找Filter来检查每个授权请求,您可以使用Filter

@Component
public class AuthFilter implements Filter {

@Override
public void doFilter
  ServletRequest request, 
  ServletResponse response, 
  FilterChain chain) throws IOException, ServletException {

    HttpServletRequest req = (HttpServletRequest) request;
    LOG.info(
      "Starting a transaction for req : {}", 
      req.getRequestURI());

    chain.doFilter(request, response);
    LOG.info(
      "Committing a transaction for req : {}", 
      req.getRequestURI());
    }

     // other methods 
  }

GenericFilterBean

public class CustomFilter extends GenericFilterBean {

@Override
public void doFilter(
  ServletRequest request, 
  ServletResponse response,
  FilterChain chain) throws IOException, ServletException {
    chain.doFilter(request, response);
       }
   }

关于java - 如何为 Controller 中的许多方法添加权限检查? (过滤器、 Action ),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56981226/

相关文章:

java - "No Session found for current thread"更改 session 访问方法后

java - 为什么hibernate不插入子表?

java - 如何禁用 javac 文件名检查?

java - Spring 应用程序上下文为空

java - app.yaml vs appengine-web.xml 使用哪一个?

java - UsernamePasswordAuthenticationFilter 跳过成功处理程序

java - 使用相同的请求映射重载 spring Controller 方法

java - 从 ResultSet 中的资源获取 URI

java - Log4j 未添加到 Ant 中的类路径

java - 如何使javax验证只显示一条错误信息