アノテーションプロセッサ処理時の例外をソースコードに吐く

アノテーションプロセッサ処理中にエラー等をシステム側(Eclipse側)に通知したい場合は、通常の標準出力にプリントしても駄目で、代わりにMessagerクラスを使う。

@Override
public boolean process(Set annotations, RoundEnvironment roundEnv) {
    Messager messager = processingEnv.getMessager();
    try {
       何か処理
    } catch (Exception e)
       messager.printMessage(Kind.ERROR, e.getMessage());
    }

Messagerから出力されたメッセージは標準出力コンソールには表示されず、Eclipseでいうと「エラー・ログ」という(私は)普段はあまり開かないビューにしか表示されない。

もっと強烈にエラーが発生したことをユーザ側に通知するには? と考えたんだけど今ひとつ思いつかなかったので、例外を現在ソースコード生成のために開いているWriterに出力するようにしてみた。

    try {
       何か処理
    } catch (Exception e)
       e.printStackTrace(new PrintWriter(this.writer));
       messager.printMessage(Kind.ERROR, e.getMessage());
    }

アノテーションプロセッサの実行時にエラーが発生すると以下のように生成したソースコード側に出力される。

/*
 * このファイルはアノテーションプロセッサ(net.kazzz.annotation.ActivityAutoDtoAnnotationProcessor)により自動生成されました。
 * file : UserInfo.java;
 * base : net.kazzz.android.UserActivity.java;
 */
package net.kazzz.android.dto;

import net.kazzz.annotation.Element;
import net.kazzz.annotation.XmlAutoBean;

java.lang.NullPointerException
    at net.kazzz.annotation.AbstractBeanAnnotationProcessor.getShortClassName(AbstractBeanAnnotationProcessor.java:188)
    at net.kazzz.annotation.ActivityAutoDtoAnnotationProcessor.needConverters(ActivityAutoDtoAnnotationProcessor.java:322)
    at net.kazzz.annotation.ActivityAutoDtoAnnotationProcessor.writePackageAndImport(ActivityAutoDtoAnnotationProcessor.java:290)
    at net.kazzz.annotation.ActivityAutoDtoAnnotationProcessor.outputBean(ActivityAutoDtoAnnotationProcessor.java:194)
    at net.kazzz.annotation.ActivityAutoDtoAnnotationProcessor.process(ActivityAutoDtoAnnotationProcessor.java:94)
    at org.eclipse.jdt.internal.compiler.apt.dispatch.RoundDispatcher.handleProcessor(RoundDispatcher.java:139)
    at org.eclipse.jdt.internal.compiler.apt.dispatch.RoundDispatcher.round(RoundDispatcher.java:121)
    at org.eclipse.jdt.internal.compiler.apt.dispatch.BaseAnnotationProcessorManager.processAnnotations(BaseAnnotationProcessorManager.java:159)
    at org.eclipse.jdt.internal.apt.pluggable.core.dispatch.IdeAnnotationProcessorManager.processAnnotations(IdeAnnotationProcessorManager.java:134)
    at org.eclipse.jdt.internal.compiler.Compiler.processAnnotations(Compiler.java:809)
    at org.eclipse.jdt.internal.compiler.Compiler.compile(Compiler.java:428)
    at org.eclipse.jdt.internal.core.builder.AbstractImageBuilder.compile(AbstractImageBuilder.java:364)
    at org.eclipse.jdt.internal.core.builder.BatchImageBuilder.compile(BatchImageBuilder.java:178)
    at org.eclipse.jdt.internal.core.builder.AbstractImageBuilder.compile(AbstractImageBuilder.java:301)
    at org.eclipse.jdt.internal.core.builder.BatchImageBuilder.build(BatchImageBuilder.java:60)
    at org.eclipse.jdt.internal.core.builder.JavaBuilder.buildAll(JavaBuilder.java:254)
    at org.eclipse.jdt.internal.core.builder.JavaBuilder.build(JavaBuilder.java:173)
    at org.eclipse.core.internal.events.BuildManager$2.run(BuildManager.java:629)
    at org.eclipse.core.runtime.SafeRunner.run(SafeRunner.java:42)
    at org.eclipse.core.internal.events.BuildManager.basicBuild(BuildManager.java:172)
    at org.eclipse.core.internal.events.BuildManager.basicBuild(BuildManager.java:203)
    at org.eclipse.core.internal.events.BuildManager$1.run(BuildManager.java:255)
    at org.eclipse.core.runtime.SafeRunner.run(SafeRunner.java:42)
    at org.eclipse.core.internal.events.BuildManager.basicBuild(BuildManager.java:258)
    at org.eclipse.core.internal.events.BuildManager.basicBuildLoop(BuildManager.java:311)
    at org.eclipse.core.internal.events.BuildManager.build(BuildManager.java:343)
    at org.eclipse.core.internal.events.AutoBuildJob.doBuild(AutoBuildJob.java:144)
    at org.eclipse.core.internal.events.AutoBuildJob.run(AutoBuildJob.java:242)
    at org.eclipse.core.internal.jobs.Worker.run(Worker.java:54)

わかりやすいんだけど、ちょっと刺激が強すぎるかな。