Java@interface -自定义注解
一 声明一个注解标签
须知 :
首先,自定义注解我们必须了解四个元注解,什么是元注解?元注解指作用于注解之上的元数据或者元信息,简单通俗的讲,元注解就是注解的注解 .
Documented与Inherited是典型的标识性注解,也就是说在注解内部并没有成员变量,没有成员变量的注解称为标识注解
Documented
指明拥有这个注解的元素可以被javadoc此类的工具文档化。这种类型应该用于注解那些影响客户使用带注释的元素声明的类型。如果一种声明使用Documented进行注解,这种类型的注解被作为被标注的程序成员的公共API 。
Inherited
指明该注解类型被自动继承。如果用户在当前类中查询这个元注解类型并且当前类的声明中不包含这个元注解类型,那么也将自动查询当前类的父类是否存在Inherited元注解,这个动作将被重复执行直到这个标注类型被找到,或者是查询到顶层的父类。
Retention
指明在什么级别显示此注解
Retention主要的参数类型包括以下几种:
RetentionPolicy.SOURCE 注解存在于源代码中,编译时会被抛弃
RetentionPolicy.CLASS 注解会被编译到class文件中,但是JVM会忽略
RetentionPolicy.RUNTIME JVM会读取注解,同时会保存到class文件中
Target
指明该类型的注解可以注解的程序元素的范围
Target主要的参数类型包括以下几种:
ElementType.TYPE 用于类,接口,枚举但不能是注解
ElementType.FIELD 作用于字段,包含枚举值
ElementType.METHOD 作用于方法,不包含构造方法
ElementType.PARAMETER 作用于方法的参数
ElementType.CONSTRUCTOR 作用于构造方法
ElementType.LOCAL_VERIABLE 作用于本地变量或者catch语句
ElementType.ANNOTATION_TYPE 作用于注解
ElementType.PACKAGE 作用于包
示例 :
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public@interface TestInterface {
String key();
Class<?> clazz()default Object.class;
}
二 注解标签引用
publicclass TestLoadInterface {
@TestInterface(key="MoonLo",clazz=TestEntity.class)
publicvoid loadInterface(TestEntityentity) {
System.out.println("注解引用测试方法. . . . . .");
}
}
三 注解功能内容实现
关于@Aspect :
1、Spring除了支持Schema方式配置AOP,还支持注解方式:使用@Aspect来配置
2、Spring默认不支持@Aspect风格的切面声明,通过如下配置开启@Aspect支持:
< 启动对@AspectJ注解的支持 >
<aop:aspectj-autoproxy proxy-target-class="true"/>
3、通过以上配置,Spring就能发现用@Aspect注解的切面内并把它应用到目标对象上。
4、需要对调用注解类路径进行监控拦截
示例 :
@Component
@Aspect
publicclass InterfaceImpl {
privatefinal String TFACE = "excution(TestLoadInterface())&&@annotation(TestInterface)";
/**
* 通知标签 :
* @Before(TFACE) : 方法执行前执行
* @AfterReturning(TFACE) : 方法执行完执行
* @AfterThrowing(TFACE) : 方法异常时执行
* @After(TFACE) : 方法最后执行
* @Around(TFACE) : 方法环绕执行
*/
@Around(value = TFACE)
public Object testIface(ProceedingJoinPointpjp) throws Throwable {
// 取注解参数
TestInterface anno = getAnnotation(pjp,TestInterface.class);
// 取key
String key =anno.key();
Object value = null;
value =pjp.proceed();
if (value != null) {
// 访问目标方法的参数:
Object[] args =pjp.getArgs();
if (args != null && args.length > 0 && args[0]!= null
&& args[0].getClass() == anno.calzz()){
System.out.println ("注解功能实现测试. . . . . ." + key);
}
}
return value;
}
/**
* 获取注解参数
*/
private <T extends Annotation> T
getAnnotation(ProceedingJoinPointjp,Class<T> clazz) {
MethodSignature joinPointObject = (MethodSignature)jp.getSignature();
Method method = joinPointObject.getMethod();
return method.getAnnotation(clazz);
}
}