java注释是一个非常重要的模块,懂得java注释对理解spring、hibernate、struts、Mybatis等主流框架运行原理有非常重要的作用。
为了方便测试,java提供@Test(单元测试),用main方法测试,一个main方法中测试太多的内容,又多又杂。用@Test一个方法就是一个main.今天我们主要是用自定义标签实现@Test @Before @After 的功能。
@Test 运行添加@Test注释的方法
@Before 在运行@Test方法之前调用
@After 在运行@Test方法之后调用
一、 添加三个自定义标签:分别表示@Test @Before @After
1、@Before
package demo;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 自定义注释 模拟@Before
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface BeforeAnnotation {
}
2、@Test
package demo;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 自定义注释 模拟@Test
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface TestAnnotation {
}
3、@After
package demo;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 自定义注释 模拟@After
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface AfterAnnotation {
}
二、写一个测试类进行测试,如果感觉笔者@TestAnnotation注释的内容比较复杂,你可以改成一条输出语句。重点关注run()对自定义注释的解析过程。
package demo;
/**
* 模拟 @Before @Test @After 这两个注释的用法
*/
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.List;
import org.junit.Test;
public class Demo02 {
/*模拟@Before:@Test注释的方法之前调用该方法*/
@BeforeAnnotation
public void test01(){
System.out.println("自定义注释@BeforeAnnotation被执行");
}
//打印一个类中,加了注释的方法名及注释名
/*模拟@Test*/
@TestAnnotation
public void test02()throws Exception{
Class c1=this.getClass();
// c1.getDeclaredMethods 获取类的所有方法 包括 protected default private
Method[] methods=c1.getDeclaredMethods();
for(Method m:methods){
//取消Java 语言访问控制检查的能力
m.setAccessible(true);
//输出方法名
System.out.print("方法名:"+m.getName());
//获取方法上所有的注释信息
Annotation[] annotations=m.getAnnotations();
if(annotations.length>0){
for(Annotation a:annotations){
//输入注释信息
System.out.print(" 注释: "+a);
}
}
//换行
System.out.println();
}
}
/*模拟@After*/
@AfterAnnotation
public void test03(){
System.out.println("自定义注释@AfterAnnotation被执行");
}
//控件自定义注释程序 用@Test启动程序
@Test
public void run()throws Throwable{
Class c1=Thread.currentThread().getContextClassLoader().loadClass("demo.Demo02");
// c1.getDeclaredMethods 获取类的所有方法 包括 protected default private
Method[] methods=c1.getDeclaredMethods();
//存储@BeforeAnnotation注释的方法
List<Method> befm=new ArrayList<Method>();
//存储@TestAnnotation注释的方法
List<Method> tesm=new ArrayList<Method>();
//存储@AfterAnnotation注释的方法
List<Method> aftm=new ArrayList<Method>();
for(Method method:methods){
//取消Java 语言访问控制检查的能力
method.setAccessible(true);
//判断该程序元素上是否包含指定元素的注释
if(method.isAnnotationPresent(BeforeAnnotation.class)){
befm.add(method);
}
if(method.isAnnotationPresent(TestAnnotation.class)){
tesm.add(method);
}
if(method.isAnnotationPresent(AfterAnnotation.class)){
aftm.add(method);
}
}
//实例化对象
Object obj=c1.newInstance();
//执行注释了@BeforeAnnotation的方法
for(Method m:befm){
m.invoke(obj);
}
//执行注释了@TestAnnotation的方法
for(Method m:tesm){
m.invoke(obj);
}
//执行注释了@AfterAnnotation的方法
for(Method m:aftm){
m.invoke(obj);
}
}
}