• 使用Spring Aop验证方法参数是否合法


    先定义两个注解类ValidateGroup 和 ValidateFiled

    ValidateGroup .java

    [java] view plain copy
     
    1. package com.zf.ann;  
    2.   
    3. import java.lang.annotation.ElementType;  
    4. import java.lang.annotation.Retention;  
    5. import java.lang.annotation.RetentionPolicy;  
    6. import java.lang.annotation.Target;  
    7.   
    8. @Retention(RetentionPolicy.RUNTIME)  
    9. @Target(ElementType.METHOD)  
    10. public @interface ValidateGroup {  
    11.     public ValidateFiled[] fileds() ;  
    12. }  


    ValidateFiled.java

    [java] view plain copy
     
    1. package com.zf.ann;  
    2.   
    3. import java.lang.annotation.ElementType;  
    4. import java.lang.annotation.Retention;  
    5. import java.lang.annotation.RetentionPolicy;  
    6. import java.lang.annotation.Target;  
    7.   
    8. @Retention(RetentionPolicy.RUNTIME)  
    9. @Target(ElementType.METHOD)  
    10. public @interface ValidateFiled {  
    11.       
    12.     /** 
    13.      * 参数索引位置 
    14.      */  
    15.     public int index() default -1 ;  
    16.       
    17.     /** 
    18.      * 如果参数是基本数据类型或String ,就不用指定该参数,如果参数是对象,要验证对象里面某个属性,就用该参数指定属性名 
    19.      */  
    20.     public String filedName() default "" ;  
    21.       
    22.     /** 
    23.      * 正则验证 
    24.      */  
    25.     public String regStr() default "";  
    26.       
    27.     /** 
    28.      * 是否能为空  , 为true表示不能为空 , false表示能够为空 
    29.      */  
    30.     public boolean notNull() default false;  
    31.       
    32.     /** 
    33.      * 是否能为空  , 为true表示不能为空 , false表示能够为空 
    34.      */  
    35.     public int maxLen() default -1 ;  
    36.       
    37.     /** 
    38.      * 最小长度 , 用户验证字符串 
    39.      */  
    40.     public int minLen() default -1 ;  
    41.       
    42.     /** 
    43.      *最大值 ,用于验证数字类型数据 
    44.      */  
    45.     public int maxVal() default -1 ;  
    46.       
    47.     /** 
    48.      *最小值 ,用于验证数值类型数据 
    49.      */  
    50.     public int minVal() default -1 ;  
    51.       
    52. }  

    注解处理类

    ValidateAspectHandel.java

    [java] view plain copy
     
    1. package com.zf.aspet;  
    2. import java.lang.annotation.Annotation;  
    3. import java.lang.reflect.InvocationTargetException;  
    4. import java.lang.reflect.Method;  
    5.   
    6. import org.aspectj.lang.ProceedingJoinPoint;  
    7. import org.aspectj.lang.annotation.Around;  
    8. import org.aspectj.lang.annotation.Aspect;  
    9. import org.springframework.stereotype.Component;  
    10. import org.springframework.web.servlet.ModelAndView;  
    11.   
    12. import com.zf.ann.ValidateFiled;  
    13. import com.zf.ann.ValidateGroup;  
    14. /** 
    15.  * 验证注解处理类 
    16.  * @author zhoufeng 
    17.  */  
    18. @Component  
    19. @Aspect  
    20. public class ValidateAspectHandel {  
    21.   
    22.     /** 
    23.      * 使用AOP对使用了ValidateGroup的方法进行代理校验 
    24.      * @throws Throwable  
    25.      */  
    26.     @SuppressWarnings({ "finally", "rawtypes" })  
    27.     @Around("@annotation(com.zf.ann.ValidateGroup)")  
    28.     public Object validateAround(ProceedingJoinPoint joinPoint) throws Throwable  {  
    29.         boolean flag = false ;  
    30.         ValidateGroup an = null;  
    31.         Object[] args =  null ;  
    32.         Method method = null;  
    33.         Object target = null ;  
    34.         String methodName = null;  
    35.         try{  
    36.             methodName = joinPoint.getSignature().getName();  
    37.             target = joinPoint.getTarget();  
    38.             method = getMethodByClassAndName(target.getClass(), methodName);    //得到拦截的方法  
    39.             args = joinPoint.getArgs();     //方法的参数   
    40.             an = (ValidateGroup)getAnnotationByMethod(method ,ValidateGroup.class );  
    41.             flag = validateFiled(an.fileds() , args);  
    42.         }catch(Exception e){  
    43.             flag = false;  
    44.         }finally{  
    45.             if(flag){  
    46.                 System.out.println("验证通过");  
    47.                 return joinPoint.proceed();  
    48.             }else{  //这里使用了Spring MVC ,所有返回值应该为Strng或ModelAndView ,如果是用Struts2,直接返回一个String的resutl就行了  
    49.                 System.out.println("验证未通过");  
    50.                 Class returnType = method.getReturnType();  //得到方法返回值类型  
    51.                 if(returnType == String.class){ //如果返回值为Stirng  
    52.                     return "/error.jsp";        //返回错误页面  
    53.                 }else if(returnType == ModelAndView.class){  
    54.                     return new ModelAndView("/error.jsp");//返回错误页面  
    55.                 }else{  //当使用Ajax的时候 可能会出现这种情况  
    56.                     return null ;  
    57.                 }  
    58.             }  
    59.         }  
    60.     }  
    61.   
    62.     /** 
    63.      * 验证参数是否合法 
    64.      */  
    65.     public boolean validateFiled( ValidateFiled[] valiedatefiles , Object[] args) throws SecurityException, IllegalArgumentException, NoSuchMethodException, IllegalAccessException, InvocationTargetException{  
    66.         for (ValidateFiled validateFiled : valiedatefiles) {  
    67.             Object arg = null;  
    68.             if("".equals(validateFiled.filedName()) ){  
    69.                 arg = args[validateFiled.index()];  
    70.             }else{  
    71.                 arg = getFieldByObjectAndFileName(args[validateFiled.index()] ,  
    72.                         validateFiled.filedName() );  
    73.             }  
    74.   
    75.             if(validateFiled.notNull()){        //判断参数是否为空  
    76.                 if(arg == null )  
    77.                     return false;  
    78.             }else{      //如果该参数能够为空,并且当参数为空时,就不用判断后面的了 ,直接返回true  
    79.                 if(arg == null )  
    80.                     return true;  
    81.             }  
    82.   
    83.             if(validateFiled.maxLen() > 0){      //判断字符串最大长度  
    84.                 if(((String)arg).length() > validateFiled.maxLen())  
    85.                     return false;  
    86.             }  
    87.   
    88.             if(validateFiled.minLen() > 0){      //判断字符串最小长度  
    89.                 if(((String)arg).length() < validateFiled.minLen())  
    90.                     return false;  
    91.             }  
    92.   
    93.             if(validateFiled.maxVal() != -1){   //判断数值最大值  
    94.                 if( (Integer)arg > validateFiled.maxVal())   
    95.                     return false;  
    96.             }  
    97.   
    98.             if(validateFiled.minVal() != -1){   //判断数值最小值  
    99.                 if((Integer)arg < validateFiled.minVal())  
    100.                     return false;  
    101.             }  
    102.   
    103.             if(!"".equals(validateFiled.regStr())){ //判断正则  
    104.                 if(arg instanceof String){  
    105.                     if(!((String)arg).matches(validateFiled.regStr()))  
    106.                         return false;  
    107.                 }else{  
    108.                     return false;  
    109.                 }  
    110.             }  
    111.         }  
    112.         return true;  
    113.     }  
    114.   
    115.     /** 
    116.      * 根据对象和属性名得到 属性 
    117.      */  
    118.     public Object getFieldByObjectAndFileName(Object targetObj , String fileName) throws SecurityException, NoSuchMethodException, IllegalArgumentException, IllegalAccessException, InvocationTargetException{  
    119.         String tmp[] = fileName.split("\.");  
    120.         Object arg = targetObj ;  
    121.         for (int i = 0; i < tmp.length; i++) {  
    122.             Method methdo = arg.getClass().  
    123.                     getMethod(getGetterNameByFiledName(tmp[i]));  
    124.             arg = methdo.invoke(arg);  
    125.         }  
    126.         return arg ;  
    127.     }  
    128.   
    129.     /** 
    130.      * 根据属性名 得到该属性的getter方法名 
    131.      */  
    132.     public String getGetterNameByFiledName(String fieldName){  
    133.         return "get" + fieldName.substring(0 ,1).toUpperCase() + fieldName.substring(1) ;  
    134.     }  
    135.   
    136.     /** 
    137.      * 根据目标方法和注解类型  得到该目标方法的指定注解 
    138.      */  
    139.     public Annotation getAnnotationByMethod(Method method , Class annoClass){  
    140.         Annotation all[] = method.getAnnotations();  
    141.         for (Annotation annotation : all) {  
    142.             if (annotation.annotationType() == annoClass) {  
    143.                 return annotation;  
    144.             }  
    145.         }  
    146.         return null;  
    147.     }  
    148.   
    149.     /** 
    150.      * 根据类和方法名得到方法 
    151.      */  
    152.     public Method getMethodByClassAndName(Class c , String methodName){  
    153.         Method[] methods = c.getDeclaredMethods();  
    154.         for (Method method : methods) {  
    155.             if(method.getName().equals(methodName)){  
    156.                 return method ;  
    157.             }  
    158.         }  
    159.         return null;  
    160.     }  
    161.   
    162. }  



    需要验证参数的Control方法

    [java] view plain copy
     
    1. package com.zf.service;  
    2. import org.springframework.stereotype.Controller;  
    3. import org.springframework.web.bind.annotation.RequestMapping;  
    4. import org.springframework.web.servlet.ModelAndView;  
    5. import com.zf.ann.ValidateFiled;  
    6. import com.zf.ann.ValidateGroup;  
    7. import com.zf.vo.Person;  
    8.   
    9. @Controller("PersonControl")  
    10. public class PersonControl {  
    11.       
    12.     //下面方法 ,是需要验证参数的方法  
    13.     @ValidateGroup(fileds = {  
    14.             //index=0 表示下面方法的第一个参数,也就是person  nutNull=true 表示不能为空  
    15.             @ValidateFiled(index=0 , notNull=true ) ,  
    16.             //index=0 表示第一个参数  filedName表示该参数的一个属性 ,也就是person.id 最小值为3 也就是 person.id 最小值为3  
    17.             @ValidateFiled(index=0 , notNull=true , filedName="id" , minVal = 3) ,  
    18.             //表示第一个参数的name 也就是person.name属性最大长度为10,最小长度为3  
    19.             @ValidateFiled(index=0 , notNull=true , filedName="name" , maxLen = 10 , minLen = 3 ) ,  
    20.             //index=1 表示第二个参数最大长度为5,最小长度为2  
    21.             @ValidateFiled(index=1 , notNull=true , maxLen = 5 , minLen = 2 ) ,  
    22.             @ValidateFiled(index=2 , notNull=true , maxVal = 100 , minVal = 18),  
    23.             @ValidateFiled(index=3 , notNull=false , regStr= "^\w+@\w+\.com$" )  
    24.     })  
    25.     @RequestMapping("savePerson")  
    26.     public ModelAndView savePerson(Person person , String name , int age , String email){  
    27.         ModelAndView mav = new ModelAndView("/index.jsp");  
    28.         System.out.println("addPerson()方法调用成功!");  
    29.         return mav ;        //返回index.jsp视图  
    30.     }  
    31.       
    32. }  

    application.xml配置


    测试

    [html] view plain copy
     
    1. package com.zf.test;  
    2. import org.springframework.context.ApplicationContext;  
    3. import org.springframework.context.support.ClassPathXmlApplicationContext;  
    4. import com.zf.service.PersonControl;  
    5. import com.zf.vo.Person;  
    6. public class PersonTest {  
    7.     public static void main(String[] args) {  
    8.         ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");  
    9.         PersonControl ps = (PersonControl) ac.getBean("PersonControl"); //测试  
    10.         ps.savePerson(new Person(3, "qqq") , "sss" , 100 , "243970446@qq.com");  
    11.     }  
    12. }  
    [html] view plain copy
     
      1. <?xml version="1.0" encoding="UTF-8"?>  
      2. <beans xmlns="http://www.springframework.org/schema/beans"  
      3.     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"  
      4.     xmlns:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx"  
      5.     xmlns:context="http://www.springframework.org/schema/context"  
      6.     xsi:schemaLocation="http://www.springframework.org/schema/beans  
      7.            http://www.springframework.org/schema/beans/spring-beans-3.0.xsd  
      8.            http://www.springframework.org/schema/tx  
      9.            http://www.springframework.org/schema/tx/spring-tx-3.0.xsd  
      10.            http://www.springframework.org/schema/aop  
      11.            http://www.springframework.org/schema/aop/spring-aop-3.0.xsd  
      12.            http://www.springframework.org/schema/context  
      13.            http://www.springframework.org/schema/context/spring-context-3.0.xsd">  
      14.     <context:component-scan base-package="com.*"></context:component-scan>  
      15.     <aop:aspectj-autoproxy proxy-target-class="true"></aop:aspectj-autoproxy>  
      16. </beans>  
  • 相关阅读:
    EasyUI
    intellij idea打包maven项目
    struts2框架详解
    java电子书
    查看mysql安装路径
    springboot 集成 vue
    C#中的属性
    C#中的时间戳
    int.TryParse非预期执行引发的思考
    IQueryable 和 IEnumerable 的区别
  • 原文地址:https://www.cnblogs.com/yhtboke/p/5749053.html
Copyright © 2020-2023  润新知