【问题标题】:how do you debug java annotation processors using intellij?如何使用 intellij 调试 Java 注释处理器?
【发布时间】:2011-12-21 08:47:42
【问题描述】:

如何使用 intellij 调试 Java 注释处理器?

最好使用 IDEA IntelliJ。我尝试在处理器内部设置断点并运行,但没有中断。

【问题讨论】:

  • 我刚刚开始了一个什么都不做的主类。我已经按照here 的描述启用了注释处理。
  • @manu1001,这将不起作用,因为注释处理器在编译器运行之前正在运行。然后启动 JVM 并尝试调试它。您可以调试应用程序代码,但不能调试注释处理器中发生的情况。
  • 但是处理代码本身必须在jvm下运行,所以理论上不应该有调试的方法吗?
  • 你是对的。它在JVM下运行。但它是 JVM 的其他实例。 javac 运行运行处理器的 JVM,然后编译代码。然后您的 IDE 运行另一个运行您的应用程序的 JVM。您想调试 first JVM,即由编译器执行的JVM。

标签: java intellij-idea


【解决方案1】:

如果您确实需要调试注释处理器,最好从命令行运行注释处理器,而不是在启用调试的 IDE 中并使用 IDE 的调试器附加到该处理器。


如果直接运行javac,可以通过指定以下额外参数来调试:

javac -J-Xdebug -J-Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000 ... (usual javac parameters go here)

如果运行 Maven,请使用 mvndebug 而不是标准的 mvn 命令 - Maven 在进程中运行编译器。


如果运行 Ant,在运行前将以下内容添加到 ANT_OPTS 环境变量中:

-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000

通过所有这些执行,javac、Ant 或 Maven 进程将在实际开始执行之前等待您附加调试器。 IntelliJ 指令是here。对于 Eclipse,here。

【讨论】:

  • 另请参阅 AndroidAnnotations 的处理器 here 是如何完成的,文章解释了如何在每个 IDE 中调试注释处理器。
  • -Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000 适用于 IntelliJ
  • 有关如何使用 IDEA 2020.1 调试在运行 javac 的 JVM 中运行的注释处理器的示例,请查看此示例:github.com/nazmulidris/annotation-processing/tree/main/…
【解决方案2】:

本教程是为 Android 项目 编写的。与往常一样,主模块名称为 "app"。该项目包含一个名为 "annotation" 的子模块,它是“app”的子依赖项。 “app” 模块使用 gradle 声明运行注释处理 apt project(':annotation').

简单版 (从终端运行编译并从 IDE 附加)

  1. [REQUIRED] 添加新的项目配置“+”->“远程”。勾选“仅限单一实例”。所有其他设置都是自动生成的。将 <whole project> 保留为类路径。端口应保留为默认 5005。

  1. [REQUIRED] 确保通过调用停止所有 gradle 实例:./gradlew --stop
  2. [必需] 运行命令:./gradlew --no-daemon -Dorg.gradle.debug=true :app:clean :app:compileDebugJavaWithJavac

  1. 尽快在调试模式下运行 APT 项目配置 :)


  1. [HINT] 我们从一个空的 gradle.properties 文件开始
  2. [提示] 不要使用 gradle daemon(--no-daemon / org.gradle.daemon=false 选项)
  3. [HINT] 在 debug 模式下运行 gradle(org.gradle.debug=true 选项)
  4. [HINT] 运行应用的模块编译而不是处理器的模块编译(应用的编译运行注解处理!)
  5. 我们通常不会在 Android Studio 中添加任何 Java 编译器设置(即文件 -> 其他设置 -> 默认设置)

扩展版本(使用 gradle.properties)

  1. 将以下内容添加到您的 gradle.properties 文件中:
org.gradle.daemon=false org.gradle.debug=true
  1. 从终端运行编译:

./gradlew :app:clean :app:compileDebugJavaWithJavac


高级版本(只需在 IDE 中按调试)

  1. 将 bash 脚本添加到您的项目主目录(例如 compile.sh)
#!/bin/bash ./gradlew :app:clean :app:compileDebugJavaWithJavac &

记住用于后台处理的“&”符号。

  1. 转到我们在第 1 步中创建的 APT 配置设置并添加 启动前配置。选择运行外部工具。

  1. 将路径添加到我们之前创建的 compile.sh 脚本。


警告

搞砸 gradle 编译,编译过程中的 NullPointer 异常 等有时会导致 AndroidStudio 卡住(在 gradle 刷新阶段冻结)。如果您无法在 IDE 中停止 gradle,请在终端中使用以下命令:

ps -A | grep gradle | awk '{ print $1; }' | xargs kill -9

在项目刷新期间关闭调试选项有时有助于 Android Studio 回到正确的轨道。

【讨论】:

    【解决方案3】:

    按照这些步骤操作,这些对我在 android studio for gradle 项目中有用:-

    1).在 gradle.properties 中添加以下行

    org.gradle.daemon=true
    org.gradle.jvmargs=-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=5005
    

    2).编辑构建配置并添加远程配置

    3).运行最近创建的运行配置APT。

    4).注解处理代码中添加断点,构建整体工程

    【讨论】:

    • 创建配置后,出现“无法找到或加载主类agentlib:jdwp[...]”错误,我不知道为什么。
    • 遗漏的步骤是从 cmd ./gradlew.bat app:compileDebugJavaWithJavac --debug 运行 javac 任务,然后立即从 IDE 启动创建的配置任务。
    【解决方案4】:

    可以运行javac 并对其进行调试,如上所示。但是在我的情况下,编写完整的类路径很乏味,所以我想把它留给 IDEA。所以在我想应用注释处理器的模块中,只需创建一个带有 main 方法的类。

    public static void main(String[] args) {
        com.sun.tools.javac.Main.main("-proc:only",
            "-processor", "my.pkgs.MyAnnotationProcessor",
            "my/pkgs/any/ClassIWantProcess.java");
    }
    

    为此,您需要将 $JAVA_HOME/lib/tools.jar 添加到您的 SDK 的 JAR(默认情况下不存在)。这与编译 JSP 的应用服务器在其类路径中需要此 JAR 的原因相同——它们需要编译器。

    然后只需为您的运行配置设置正确的工作目录(因此 java 文件的相对路径是正确的),在处理器中设置断点并随意调试!

    好处 - 类路径已经由 IDEA 设置并由“内部”javac 使用,因为这里它不是一个单独的进程。我相信也可以将其翻译到其他 IDE。

    【讨论】:

    • 我刚刚经历了这个过程,我更喜欢这个解决方案,因为它使用 -processor 标志,它比 --processorpath 或 -cp javac 调试路由抛出更详细的错误。我的问题原来是我生成的类文件与我运行它们的位置不兼容。
    • 虽然我知道这些 cmets 没有太多价值,但这确实是我最终要做的(将JDK\libs\tools.jar 作为依赖项添加到项目中并为文件"c:/Development/HomeProjects/funky-apt/src/main/java/com/zhuinden/App.java" 执行javac(绝对路径)),我确实可以调试我的注释处理器。很好的答案。
    【解决方案5】:

    对于一个 Maven 项目,this post,它更详细地解释了以下步骤,对我有用:

    1. 添加“远程”运行配置并将“端口”设置为 8000。

    2. 从项目目录(在命令行上)发出命令mvnDebug clean install。

    3. 运行运行配置。要在进程退出后开始新会话,请从 (2) 开始重复。

    记得在项目的依赖项发生变化时对它们运行mvn install(例如,如果注释处理器与您正在从中调试它的项目位于不同的工件中)。

    【讨论】:

      【解决方案6】:

      我找到了以下可以帮助您的资源:@​​987654321@

      这家伙逐步解释了如何使用 Eclipse 调试注释处理器。

      【讨论】:

        【解决方案7】:

        注解处理在编译过程中进行,因此无法正常调试。如果你想在你的项目上下文中调试它,你可以使用 IntelliJ 远程调试,同时让 Gradle 或 Maven 处于调试模式。然后你可以在注释处理器的文件中放置断点。

        见Debugging an Annotation Processor in any project。

        免责声明:我写了这篇文章。

        【讨论】:

          【解决方案8】:

          使用 IntelliJ IDEA 和 Gradle 调试注释处理器

          1. 设置自定义 VM 选项 -Dcompiler.process.debug.port=5005:按 Ctrl + Shift + A 并在操作列表中选择 Edit Custom VM Options... 以添加自定义VM 选项,然后重新启动 IDE。
          2. 使用默认参数创建远程调试配置:运行 -> 编辑配置... -> 添加新配置(Alt + 插入)-> 远程。
          3. 设置断点。
          4. 从终端使用 Gradle 构建:$ ./gradlew --no-daemon -Dorg.gradle.debug=true clean build(如果命令执行被冻结也没关系,不要终止进程)。
          5. 在 IDE 中调试远程调试配置(参见步骤 3):选择合适的远程调试配置并按 Shift + F9。

          希望它可以帮助某人:)

          【讨论】:

            猜你喜欢
            • 2015-09-29
            • 1970-01-01
            • 1970-01-01
            • 2014-02-21
            • 2021-01-10
            • 2017-07-15
            • 2017-05-22
            • 1970-01-01
            相关资源
            最近更新 更多