基础部份:

接下来讲编译JAVA时,生成自定义class

我们用 javax.annotation.processing.AbstractProcessor 来处理

public abstract class AbstractProcessor implements Processor {

    protected ProcessingEnvironment processingEnv;

    public Set<String> getSupportedOptions() {
SupportedOptions so = this.getClass().getAnnotation(SupportedOptions.class);
if (so == null)
return Collections.emptySet();
else
return arrayToSet(so.value());
} public Set<String> getSupportedAnnotationTypes() {
SupportedAnnotationTypes sat = this.getClass().getAnnotation(SupportedAnnotationTypes.class);
if (sat == null) {
//省略
return Collections.emptySet();
}
else
return arrayToSet(sat.value());
}
public SourceVersion getSupportedSourceVersion() {
SupportedSourceVersion ssv = this.getClass().getAnnotation(SupportedSourceVersion.class);
SourceVersion sv = null;
if (ssv == null) {
sv = SourceVersion.RELEASE_6;
//省略
} else
sv = ssv.value();
return sv;
}
}

继承AbstractProcessor 需要关心几个地方

1.@SupportedSourceVersion 支持java源码版本,扫描项目java文件过滤

2.@SupportedAnnotationTypes 过滤的 Annotation class

3.属性ProcessingEnvironment

  其中有个概念Element包含 class、method、field等信息

我们只关心以下几种类型:

1.TypeElement 对象包含class 信息

2.VariableElement 对象包含 field, constant, method or constructor parameter, local variable 等信息

  其中通过getEnclosingElement 能获取到目标TypeElement

实现部份:

由于 process(Set<? extends TypeElement> annotations, RoundEnvironment env) annotations参数只是 @SupportedAnnotationTypes 上绑定的anno class 没有提取到相关的处理类

可以通过env.getRootElements()获取全部的类,或内部带过滤的方法 env.getElementsAnnotatedWith

@SupportedAnnotationTypes({ "com.eyu.TestAnnotation" })
@SupportedSourceVersion(SourceVersion.RELEASE_7)
public class MyProcessor extends AbstractProcessor {
/***
* {@link ElementFilter}
*/
public static final Set<ElementKind> CONSTRUCTOR_KIND = Collections.unmodifiableSet(EnumSet.of(ElementKind.CONSTRUCTOR));
public static final Set<ElementKind> FIELD_KINDS = Collections.unmodifiableSet(EnumSet.of(ElementKind.FIELD, ElementKind.ENUM_CONSTANT));
public static final Set<ElementKind> METHOD_KIND = Collections.unmodifiableSet(EnumSet.of(ElementKind.METHOD));
public static final Set<ElementKind> PACKAGE_KIND = Collections.unmodifiableSet(EnumSet.of(ElementKind.PACKAGE));
public static final Set<ElementKind> TYPE_KINDS = Collections.unmodifiableSet(EnumSet.of(ElementKind.CLASS, ElementKind.ENUM, ElementKind.INTERFACE, ElementKind.ANNOTATION_TYPE)); @Override
public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment env) {
Set<? extends Element> elememts = env.getElementsAnnotatedWith(com.eyu.TestAnnotation.class);
Set<Class<?>> clz = new HashSet<>();
for (Element ele : elememts) {
String key = null;
if (TYPE_KINDS.contains(ele.getKind())) {
  TypeElement classElement = (TypeElement) ele;
  key = classElement.getQualifiedName().toString();
} else if (FIELD_KINDS.contains(ele.getKind()) || METHOD_KIND.contains(ele.getKind())) {
  VariableElement varELe = (VariableElement) ele;
   TypeElement enclosingElement = (TypeElement) varELe.getEnclosingElement();
  key = enclosingElement.getQualifiedName().toString();
}
if (key == null) {
  continue;
}
try {
  clz.add(Class.forName(key));
} catch (ClassNotFoundException e) {
  e.printStackTrace();
}
}
for (Class<?> key : clz) {
System.err.println(key);
}
return false;
}
}

执行部份:

执行自定义AbstractProcessor有两种方式

1.在maven项目 pom.xml 添加

     <plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.0</version>
<configuration>
<annotationProcessors>
<annotationProcessor>com.eyu.MyProcessor</annotationProcessor>
</annotationProcessors>
<debug>true</debug>
<optimize>true</optimize>
<source>1.8</source>
<target>1.8</target>
<compilerArguments>
<AaddGeneratedAnnotation>true</AaddGeneratedAnnotation>
<Adebug>true</Adebug>
</compilerArguments>
</configuration>
</plugin>

2.在resource/META-INF/services 新建 javax.annotation.processing.Processor 文件

内容为自定义处理类 com.eyu.MyProcessor

然后创建maven build 配置 Goals输入install即可 在实际测试中只有删除/添加java文件才触发一次执行

细心的读者会发者,上篇没有写如何发送消息,这篇没有如何写生成class,后面会有详细介绍

最新文章

  1. Android开发学习之路-二维码学习
  2. 那些年我们写过的T-SQL(下篇)
  3. .Net简单图片系统-使用说明
  4. Daily Scrum 11.3
  5. WBS练习
  6. Linux I2C工具查看配置I2C设备【转】
  7. erlang实现ssh
  8. Ant 脚本打印系统属性变量、ant内置属性
  9. android开发 替换bitmap中的颜色值
  10. jQuery 定位锚点
  11. elasticsearch 索引 类型 id
  12. Linux编程return与exit区别
  13. 关于GNU软件的版本号命名规则
  14. SQLServer 重建索引前后对比
  15. 201521123071《Java程序设计》第五周学习总结
  16. iOS 实现UIImageView 的不停的旋转(更新:2017.7.26)
  17. wireshark抓包,安装及简单使用
  18. 为wordpress博客网站替换鼠标样式
  19. python3csv与xlsx文件操作模块(csv、xlsxwriter)
  20. C#字典Dictionay多线程读是否是安全的

热门文章

  1. Java基本语法.part02
  2. overload和override二者之间的区别
  3. day 60 Django基础七之Ajax
  4. view架构
  5. C# 封装首页、上一页、下一月、尾页处理器
  6. CSS——div内文字的溢出部分用省略号显示
  7. JS流程控制语句 多重判断满足你各种需求 要在多组语句中选择一组来执行,使用if..else嵌套语句。
  8. JavaScript特效源码(5、背景特效)
  9. java 压缩包
  10. Luogu P2079 烛光晚餐(背包)