java自定义注解配合编译期注解处理器生成代码的核心是:定义@retention(source)和@target的注解,编写继承abstractprocessor的处理器,通过meta-inf/services注册,并在javac编译阶段用filer生成新源文件。

Java 自定义注解配合编译期注解处理器生成代码,核心在于:定义注解 + 编写 Processor + 注册处理器 + 触发编译。整个过程不运行时生效,而是在 javac 编译阶段扫描、解析、生成新源文件或资源。
定义可被处理器识别的自定义注解
注解需声明 @Retention(RetentionPolicy.SOURCE)(仅保留到源码阶段)和 @Target(明确作用位置),并建议加上 @Documented 和 @SupportedSourceVersion 提升规范性:
- 必须用
SOURCE级别,否则编译器不会将其传递给 Processor -
@Target({ElementType.TYPE, ElementType.FIELD})表示该注解可用在类或字段上 - 避免使用
CLASS或RUNTIME,否则无法在编译期被 Processor 拦截处理
编写 AnnotationProcessor 子类处理逻辑
继承 AbstractProcessor,重写 process() 方法,在其中遍历被注解的元素,提取信息,并调用 Filer 生成 Java 源文件:
Java JDK 25 来自 OpenJDK 官方归档,版本为 JDK 25,本条下载地址已指向官方 Windows x64 zip 安装包直链,适合调试旧项目或兼容旧版 Java 运行环境。
-
RoundEnvironment提供getElementsAnnotatedWith(YourAnnotation.class)获取所有匹配元素 - 用
Filer.createSourceFile()创建 .java 文件,返回Writer写入内容(推荐用JavaFileObject+Writer,或更安全地用javapoet库生成结构化代码) - 注意:不能修改已有源文件,只能生成新文件;生成路径自动匹配包名(如包名
com.example→ 输出到com/example/目录)
注册处理器并确保编译时启用
有两种主流方式让 javac 发现你的 Processor:
-
通过 META-INF/services/javax.annotation.processing.Processor:在
src/main/resources/META-INF/services/下建该文件,内容为处理器全限定类名(如com.example.MyProcessor) -
Maven 中显式配置 annotationProcessorPath:在
maven-compiler-plugin中添加<annotationprocessorpaths></annotationprocessorpaths>,指定包含 Processor 的 jar(尤其多模块项目中 Processor 在独立 module 时必需) - 若用 JDK 9+,还需在
module-info.java中声明uses javax.annotation.processing.Processor
常见陷阱与注意事项
实际开发中容易卡在几个关键点:
- Processor 类必须有无参构造函数(由编译器反射调用)
- 不要在
process()中抛出未捕获异常,会导致编译中断;应记录Messager错误信息(processingEnv.getMessager().printMessage(Diagnostic.Kind.ERROR, "...")) - 生成的类名不能与已有类冲突,否则编译报错“duplicate class”
- 首次编译可能看不到生成文件——因为 Maven 默认 clean 后才触发 Processor;建议执行
mvn compile并检查target/generated-sources/annotations/目录
不复杂但容易忽略细节。只要注解声明正确、Processor 注册到位、生成逻辑清晰,就能稳定在编译期产出所需代码。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










