Avoid duplication between similar Gradle tasks?

2020-05-19 05:15发布

问题:

It there any way to avoid duplication in configuration between two similar tasks of the same type?

For example, I'd like to create a debugSomething task, with the same configuration as runSomething below but with the addition of a remote debugger argument to the jvmArgs:

task runSomething(dependsOn: jar, type: JavaExec, group: "Run") {
    jvmArgs "-Xmx1024m", "-XX:MaxPermSize=128m"
    main = "com.some.Main"
    classpath = sourceSets.main.runtimeClasspath
}

回答1:

I've found that using the Task.configure method is very helpful for centralizing logic like this.

I haven't tested it, but in your case this might look like this:

def commonSomething = {
    main = "com.some.Main"
    classpath = sourceSets.main.runtimeClasspath
    jvmArgs "-Xmx1024m", "-XX:MaxPermSize=128m"
}

task runSomething(dependsOn: jar, type: JavaExec, group: "Run") {
    configure commonSomething
}

task debugSomething(dependsOn: jar, type: JavaExec, group: "Run") {
    configure commonSomething
    jvmArgs ...add debug arguments...
}


回答2:

This can be solved using plain Groovy:

task runSomething(dependsOn: jar, type: JavaExec, group: "Run") {
}

task debugSomething(dependsOn: jar, type: JavaExec, group: "Run") {
    jvmArgs "-agentlib:jdwp=transport=dt_socket,server=y,address=8000,suspend=y"
}

[runSomething, debugSomething].each { task ->
    task.main = "com.some.Main"
    task.classpath = sourceSets.main.runtimeClasspath
    task.jvmArgs "-Xmx1024m", "-XX:MaxPermSize=128m"
}

Even though debugSomething.jvmArgs is invoked twice, all three arguments are supplied to the JVM.

Single arguments can be set using Groovy's Spread operator:

[runSomething, debugSomething]*.main = "com.some.Main"


回答3:

Refer to section 51.2 of the manual. AFAICT, it shows exactly what you want.



回答4:

I've been searching for something similar with a difference that I don't want to share the config among all the tasks of the same type, but only for some of them.

I've tried something like stated in the accepted answer, it wasn't working well though. I'll try again then.

As I've got here, I don't mind to share, there is (at least now) a better, Gradle's built-in way to achieve the thing which was asked here. It goes like:

tasks.withType(JavaExec) {
    jvmArgs "-Xmx1024m", "-XX:MaxPermSize=128m"
    main = "com.some.Main"
    classpath = sourceSets.main.runtimeClasspath
}

This way all the tasks of JavaExec type will receive the default config which can obviously be altered by any specific task of the same type.



标签: gradle