spring boot 利用注解实现权限验证的实现代码

 更新时间:2018年11月25日 09:38:40   作者:兰茗翔  
这篇文章主要介绍了spring boot 利用注解实现权限验证的实现代码,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧

这里使用 aop 来实现权限验证

引入依赖

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-aop</artifactId>
</dependency>

定义注解

package com.lmxdawn.api.admin.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

/**
 * 后台登录授权/权限验证的注解
 */
//此注解只能修饰方法
@Target(ElementType.METHOD)
//当前注解如何去保持
@Retention(RetentionPolicy.RUNTIME)
public @interface AuthRuleAnnotation {
  String value();
}

拦截实现登录和权限验证

package com.lmxdawn.api.admin.aspect;

import com.lmxdawn.api.admin.annotation.AuthRuleAnnotation;
import com.lmxdawn.api.admin.enums.ResultEnum;
import com.lmxdawn.api.admin.exception.JsonException;
import com.lmxdawn.api.admin.service.auth.AuthLoginService;
import com.lmxdawn.api.common.utils.JwtUtils;
import io.jsonwebtoken.Claims;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.lang.reflect.Method;
import java.util.List;

/**
 * 登录验证 AOP
 */
@Aspect
@Component
@Slf4j
public class AuthorizeAspect {

  @Resource
  private AuthLoginService authLoginService;

  @Pointcut("@annotation(com.lmxdawn.api.admin.annotation.AuthRuleAnnotation)")
  public void adminLoginVerify() {
  }

  /**
   * 登录验证
   *
   * @param joinPoint
   */
  @Before("adminLoginVerify()")
  public void doAdminAuthVerify(JoinPoint joinPoint) {

    ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
    if (attributes == null) {
      throw new JsonException(ResultEnum.NOT_NETWORK);
    }
    HttpServletRequest request = attributes.getRequest();

    String id = request.getHeader("X-Adminid");

    Long adminId = Long.valueOf(id);

    String token = request.getHeader("X-Token");
    if (token == null) {
      throw new JsonException(ResultEnum.LOGIN_VERIFY_FALL);
    }

    // 验证 token
    Claims claims = JwtUtils.parse(token);
    if (claims == null) {
      throw new JsonException(ResultEnum.LOGIN_VERIFY_FALL);
    }
    Long jwtAdminId = Long.valueOf(claims.get("admin_id").toString());
    if (adminId.compareTo(jwtAdminId) != 0) {
      throw new JsonException(ResultEnum.LOGIN_VERIFY_FALL);
    }

    // 判断是否进行权限验证
    MethodSignature signature = (MethodSignature) joinPoint.getSignature();
    //从切面中获取当前方法
    Method method = signature.getMethod();
    //得到了方,提取出他的注解
    AuthRuleAnnotation action = method.getAnnotation(AuthRuleAnnotation.class);
    // 进行权限验证
    authRuleVerify(action.value(), adminId);
  }

  /**
   * 权限验证
   *
   * @param authRule
   */
  private void authRuleVerify(String authRule, Long adminId) {

    if (authRule != null && authRule.length() > 0) {

      List<String> authRules = authLoginService.listRuleByAdminId(adminId);
      // admin 为最高权限
      for (String item : authRules) {
        if (item.equals("admin") || item.equals(authRule)) {
          return;
        }
      }
      throw new JsonException(ResultEnum.AUTH_FAILED);
    }

  }

}

Controller 中使用

使用 AuthRuleAnnotation 注解, value 值就是在数据库里面定义的 权限规则名称

/**
 * 获取管理员列表
 */
@AuthRuleAnnotation("admin/auth/admin/index")
@GetMapping("/admin/auth/admin/index")
public ResultVO index(@Valid AuthAdminQueryForm authAdminQueryForm,
           BindingResult bindingResult) {

  if (bindingResult.hasErrors()) {
    return ResultVOUtils.error(ResultEnum.PARAM_VERIFY_FALL, bindingResult.getFieldError().getDefaultMessage());
  }

  if (authAdminQueryForm.getRoleId() != null) {
    List<AuthRoleAdmin> authRoleAdmins = authRoleAdminService.listByRoleId(authAdminQueryForm.getRoleId());
    List<Long> ids = new ArrayList<>();
    if (authRoleAdmins != null && !authRoleAdmins.isEmpty()) {
      ids = authRoleAdmins.stream().map(AuthRoleAdmin::getAdminId).collect(Collectors.toList());
    }
    authAdminQueryForm.setIds(ids);
  }
  List<AuthAdmin> authAdminList = authAdminService.listAdminPage(authAdminQueryForm);

  // 查询所有的权限
  List<Long> adminIds = authAdminList.stream().map(AuthAdmin::getId).collect(Collectors.toList());
  List<AuthRoleAdmin> authRoleAdminList = authRoleAdminService.listByAdminIdIn(adminIds);

  // 视图列表
  List<AuthAdminVo> authAdminVoList = authAdminList.stream().map(item -> {
    AuthAdminVo authAdminVo = new AuthAdminVo();
    BeanUtils.copyProperties(item, authAdminVo);
    List<Long> roles = authRoleAdminList.stream()
        .filter(authRoleAdmin -> authAdminVo.getId().equals(authRoleAdmin.getAdminId()))
        .map(AuthRoleAdmin::getRoleId)
        .collect(Collectors.toList());
    authAdminVo.setRoles(roles);
    return authAdminVo;
  }).collect(Collectors.toList());

  PageInfo<AuthAdmin> authAdminPageInfo = new PageInfo<>(authAdminList);
  PageSimpleVO<AuthAdminVo> authAdminPageSimpleVO = new PageSimpleVO<>();
  authAdminPageSimpleVO.setTotal(authAdminPageInfo.getTotal());
  authAdminPageSimpleVO.setList(authAdminVoList);

  return ResultVOUtils.success(authAdminPageSimpleVO);

}

相关地址

GitHub 地址: https://github.com/lmxdawn/vue-admin-java

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

相关文章

  • SpringMVC实现文件上传与下载、拦截器、异常处理器等功能

    SpringMVC实现文件上传与下载、拦截器、异常处理器等功能

    这篇文章主要给大家介绍了关于SpringMVC实现文件上传与下载、拦截器、异常处理器等功能的相关资料,这些功能在我们日常开发中经常会遇到,本文通过示例代码介绍的非常详细,需要的朋友可以参考下
    2021-09-09
  • Spring Boot 与 mybatis配置方法

    Spring Boot 与 mybatis配置方法

    这篇文章主要介绍了Spring Boot 与 mybatis配置方法,需要的朋友可以参考下
    2017-06-06
  • Java 关系运算符详情及案例(下)

    Java 关系运算符详情及案例(下)

    这篇文章主要介绍了Java 关系运算符详情及案例的实现,主要续上篇文章,上一篇文章我们讲到“等于”运算符 (==)、“不等于”运算符(!=)、“大于”运算符(>) ,这篇文章继续给大家讲解相关知识,需要的朋友可以参考一下
    2021-12-12
  • log4j控制台不打印日志故障的详细解决方案

    log4j控制台不打印日志故障的详细解决方案

    这篇文章主要给大家介绍了关于log4j控制台不打印日志故障的详细解决方案,log4j不提供默认配置,因为在某些环境中可能禁止输出到控制台或文件系统,需要的朋友可以参考下
    2023-08-08
  • 解决springcloud-eureka注册时的ip问题

    解决springcloud-eureka注册时的ip问题

    这篇文章主要介绍了解决springcloud-eureka注册时的ip问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2021-08-08
  • 解析SpringBoot中使用LoadTimeWeaving技术实现AOP功能

    解析SpringBoot中使用LoadTimeWeaving技术实现AOP功能

    这篇文章主要介绍了SpringBoot中使用LoadTimeWeaving技术实现AOP功能,AOP面向切面编程,通过为目标类织入切面的方式,实现对目标类功能的增强,本文给大家介绍的非常详细,需要的朋友可以参考下
    2022-09-09
  • Javac/javap 自带工具简单使用讲解

    Javac/javap 自带工具简单使用讲解

    这篇文章主要介绍了Javac/javap 自带工具简单使用讲解,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-03-03
  • java中double类型运算结果异常的解决方法

    java中double类型运算结果异常的解决方法

    下面小编就为大家带来一篇java中double类型运算结果异常的解决方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2016-12-12
  • Java中equals和==的区别详解

    Java中equals和==的区别详解

    这篇文章主要介绍了详解 Java 中 equals 和 == 的区别的相关资料,equals 和 == 都是用来检测两个字符串是否相等,返回值也都是布尔型,但是两者在内部比较的处理中却不尽相同需要的朋友可以参考下
    2021-09-09
  • Java EventBus手把手带你实现

    Java EventBus手把手带你实现

    EventBus是Guava的事件处理机制,是设计模式中观察者模式(生产/消费者编程模型)的优雅实现。本文就来和大家聊聊EventBus的使用,需要的可以参考一下
    2023-01-01

最新评论