AOP自定義注解實現指定字段加密脫敏


一、自定義注解

解密自定義注解略

1.方法上注解

@Documented
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface CryptMethod {
}

2.字段上注解

@Documented
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface CryptData {
}

自定義注解解析

  • 1.@Documented:注解類型信息會被 JavaDoc 工具提取到幫助文檔中。
  • 2.@Target:指定一個注解的使用范圍,value 是 java.lang.annotation.ElementType 枚舉類型的數組
名稱 說明
CONSTRUCTOR 用於構造方法
FIELD 用於成員變量(包括枚舉常量)
LOCAL_VARIABLE 用於局部變量
METHOD 用於方法
PACKAGE 用於包
PARAMETER 用於類型參數(JDK 1.8新增)
TYPE 用於類、接口(包括注解類型)或 enum 聲明
  • 3.@Retention:用於描述注解的生命周期,也就是該注解被保留的時間長短 value 是 java.lang.annotation.RetentionPolicy枚舉類型的數組
名稱 說明 使用
SOURCE 在源文件中有效 檢查性的操作
CLASS 在 class 文件中有效 編譯時進行預處理操作
RUNTIME 在運行時有效 運行時去動態獲取注解信息

SOURCE < CLASS < RUNTIME

  • 4.@Inherited:使用被該注解修飾的注解的Class類,其子類擁有該注解
  • 5.@Repeatable:在需要對同一種注解多次使用時,使用此注解修飾
  • 6.@Order:優先級,Ordered枚舉默認為LOWEST_PRECEDENCE還有HIGHEST_PRECEDENCE

二、構造AOP邏輯

@Aspect
@Component
@Log4j2
public class CryptAop {
    @Pointcut("@annotation(com.example.demo.annotation.crypt.CryptMethod)")
    public void cryptPointCut(){
    }

    @Pointcut("@annotation(com.example.demo.annotation.crypt.EnCryptMethod)")
    public void encryptPointCut(){
    }

    @Around("cryptPointCut()")
    public Object around(ProceedingJoinPoint joinPoint){
        Object responseObj = null;
        try {
            responseObj = joinPoint.proceed();
            Field[] fields = responseObj.getClass().getDeclaredFields();
            log.info(fields.length);
            for (Field field : fields) {
                log.info(field.getName());
                if (field.isAnnotationPresent(CryptData.class)){
                    if (!field.isAccessible()){
                        field.setAccessible(true);
                    }
                    Object o = field.get(responseObj);
                    System.out.println("獲取的字段值"+ JSONObject.toJSONString(o));
                    field.set(responseObj, "加密啦");
                }
            }
        } catch (Throwable e) {
            e.printStackTrace();
        }
        return responseObj;
    }

    @Around("encryptPointCut()")
    public Object encrypt(ProceedingJoinPoint joinPoint){
        Object responseObj = null;
        try {
            responseObj = joinPoint.proceed();
            Field[] fields = responseObj.getClass().getDeclaredFields();
            log.info(fields.length);
            for (Field field : fields) {
                log.info(field.getName());
                if (field.isAnnotationPresent(EnCryptData.class)){
                    if (!field.isAccessible()){
                        field.setAccessible(true);
                    }
                    Object o = field.get(responseObj);
                    System.out.println("獲取的字段值"+ JSONObject.toJSONString(o));
                    field.set(responseObj, "解密啦");
                }
            }
        } catch (Throwable e) {
            e.printStackTrace();
        }
        return responseObj;
    }
}

三、調用方法

@Service
public class PersonServiceImpl implements PersonService {
    @Override
    @CryptMethod
    public Person setNewPerson() {
        Person person = new Person();
        person.setPhoneNumber("110");
        return person;
    }

    @Override
    @EnCryptMethod
    public Person getPerson() {
        Person person = new Person();
        person.setPhoneNumber("110");
        return person;
    }
}

四、實體類

@Data
public class Person implements Serializable {
    private static final long serialVersionUID = 6496689746718741955L;
    //id
    private Integer id;
    //姓名
    private String name;
    //手機號
    @CryptData
    @EnCryptData
    private String phoneNumber;
}


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM