【问题标题】:gradle: change default port from 5005gradle:从 5005 更改默认端口
【发布时间】:2019-04-20 00:16:29
【问题描述】:

我想调试一些同时运行的 JVM 实例。我知道我可以使用--debug-jvm 运行 gradle,这样 JVM 会等到我启动 IDE 调试器,以便它连接到 JVM,但它默认使用端口 5005。这对于调试一个 JVM 实例来说很好......但是如果我想调试多个实例,我需要定义一个与 5005 不同的端口。如何使用 gradle 实现这一点?

【问题讨论】:

  • 你不能只使用集成工具在 Gradle 的调试模式下启动吗?我知道 IntelliJ 只是让我启动一个 gradle 进程,我仍然可以调试代码。
  • 简短回答:。长答案:不,因为我使用的脚本正在运行许多不同的东西,最终以 gradle 调用结束。

标签: java debugging gradle jvm


【解决方案1】:

您可以修改 GRADLE_OPTS 环境变量并添加标准 Java 调试器语法,例如使用端口 8888:

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

【讨论】:

  • 这看起来很有希望......但是调试器无法在我在项目上设置的断点处停止。如果我使用 --debug-jvm 并使用端口 5005 连接,它会按预期停止。我猜是少了点什么。
  • @eftshift0 也许 Gradle 守护进程正在后台运行。你可以试试--no-daemon吗?
  • 这将是gladle call的一个选项还是GRADLE_OPTS的一个附加选项?
  • @eftshift0 是,根据docs
  • 很遗憾,没有变化。
【解决方案2】:

就我而言,我想调试一个特定的文件,所以我在build.gradle 中包含了以下代码:

task execFile(type: JavaExec) {
    main = mainClass

    classpath = sourceSets.main.runtimeClasspath
    
    if (System.getProperty('debug', 'false') == 'true') {
        jvmArgs "-Xdebug", "-agentlib:jdwp=transport=dt_socket,address=8787,server=y,suspend=y"
    }

    systemProperties System.getProperties()
}

我可以运行:

gradle execFile -PmainClass=com.MyClass -Dmyprop=somevalue -Ddebug=true

自定义execFile 任务接收:

  • -PmainClass=com.MyClass:我要执行的main方法所在的类(在脚本中,main = mainClass
  • -Dmyprop=somevalue:在调用System.getProperty("myprop") 的应用程序中检索其值的属性(在脚本中,需要systemProperties System.getProperties()
  • -Ddebug=true:在端口 8787 上启用调试的标志(在脚本中,请参见 if 条件,以及 address=8787,但端口可以更改,并且此标志名称也可以更改)。使用suspend=y 会暂停执行,直到将调试器附加到端口(如果您不希望这种行为,可以使用suspend=n

对于您的用例,您可以尝试将jvmArgs ... 行后面的逻辑应用于您的特定任务(或使用tasks.withType(JavaExec) { ... } 应用于此类型的所有任务)。

使用此解决方案时,请勿使用 --debug-jvm 选项,因为您可能会收到关于属性 jdwp 被定义两次的错误消息。

更新(2020-08-10)

为了确保代码仅在我显式执行任务execFile 时运行(例如,在我刚刚构建 gradle 时不运行),我将代码更改为:

task execFile {
    dependsOn 'build'

    doLast {
        tasks.create('execFileJavaExec', JavaExec) {
            main = mainClass
            classpath = sourceSets.main.runtimeClasspath

            if (System.getProperty('debug', 'false') == 'true') {
                jvmArgs "-Xdebug", "-agentlib:jdwp=transport=dt_socket,address=*:8787,server=y,suspend=y"
            }

            systemProperties System.getProperties()
        }.exec()
    }
}

查看更多信息:Run gradle task only when called specifically

【讨论】:

  • 使用 Java11,我使用 Spring Boot 和 Vagrant 创建了这种任务以启用远程调试: task debug(type: JavaExec) { main = mainClass classpath = sourceSets.main.runtimeClasspath jvmArgs "-agentlib:jdwp =transport=dt_socket,address=192.168.133.10:5005,server=y,suspend=y" systemProperties System.getProperties() }
  • @PHZ.fi-Pharazon 如果您想确保代码仅在您显式调用execFile 时运行,您可以使用我包含的新代码,其中JavaExec 任务是在doLast 中创建。
【解决方案3】:

选项 1 - 直接传递启动调试器的 JVM 参数

task exampleProgram(type: JavaExec) {
  classpath = sourceSets.main.runtimeClasspath
  description = "Your Description"
  main = 'Example.java'  // <package>.<path>.<to>.<YourMainClass>.java

  // Change `1805` to whatever port you want.
  jvmArgs=["-agentlib:jdwp=transport=dt_socket,server=y,suspend=y,address=1805"]  
}

如果不能立即工作,请尝试使用 gradle --stop 停止所有现有守护进程,这样 Gradle 在构建/运行项目时不会受到任何过去设置的影响。

选项 2 - 使用 Gradle 的 debugOptions 对象

或者,根据Gradle's documentation,以下也应该可以解决问题;但是,it didn't work for me。为了完整起见,我将其包括在内,并希望它在未来能够正常工作。

task runApp(type: JavaExec) {
    ...

    debugOptions {
        enabled = true
        port = 5566
        server = true
        suspend = false
    }
 }

参考文献:

【讨论】:

    猜你喜欢
    • 2011-10-31
    • 2013-11-30
    • 1970-01-01
    • 1970-01-01
    • 2014-08-29
    • 2014-08-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多