多次运行Gradle任务

3

我有一个gradle项目,其中包含两个子目录中的模块。目录结构如下。

root
    module1
        build.gradle
    module2
        build.gradle
    build.gradle
    settings.gradle

顶层的settings.gradle包含了这两个模块。顶层的build.gradle文件包含以下内容。
task runScript(type: Exec) {
    workingDir 'scripts'
    commandLine 'python3', 'myscript.py'
}

project(':module1') {
    evaluationDependsOn(':module1')

    final test = tasks.findByName('test')
    test.dependsOn(runScript)
}

project(':module2') {
    evaluationDependsOn(':module2')

    final test = tasks.findByName('test')
    test.dependsOn(runScript)
}

任务runScript将数据库设置为已知状态,在每个模块测试任务之前必须运行

当我运行测试任务时,我的脚本只执行一次。如何确保它可以多次执行?

$ ./gradlew test 
... some output

:runScript
RUNNING MY SCRIPT

:module1:test
RUNNING MODULE1 TESTS

... some output

:module2:test
RUNNING MODULE2 TESTS

我尝试过的方法

我尝试在任务runScript中添加outputs.upToDateWhen {false},以便Gradle永远不认为它是最新的。但这没有任何区别;我猜测是因为该任务仍只出现一次在任务图中?

我尝试将每个模块包含dependsOn的行替换为test.doFirst {runScript.execute()}。这会改变任务执行的时间,但不会导致多次执行。

$ ./gradlew test 
... some output

:module1:test
RUNNING MY SCRIPT
RUNNING MODULE1 TESTS

... some output

:module2:test
RUNNING MODULE2 TESTS

我尝试为每个模块创建一个新的任务。虽然这样可行,但是会重复代码。

project(':module1') {
    evaluationDependsOn(':module1')

    final test = tasks.findByName('test')

    task runScript(type: Exec) {
        workingDir '../scripts'
        commandLine 'python3', 'myscript.py'
    }

    test.dependsOn(runScript)
}

project(':module2') {
    evaluationDependsOn(':module2')

    final test = tasks.findByName('test')

    task runScript(type: Exec) {
        workingDir '../scripts'
        commandLine 'python3', 'myscript.py'
    }

    test.dependsOn(runScript)
}

这不会起作用。Gradle任务在构建中只能运行一次。如果您需要设置,则应使用doFirst方法进行任务特定的设置,或者使用beforeTest方法进行测试特定的设置。 - Lukas Körfer
1个回答

2
如果您的脚本对于每个测试任务的每次运行都是必需的,那么只需确保在每个测试任务之前执行它即可。那么为什么还要使用一个任务呢?
subprojects {
    tasks.withType(Test) {
        doFirst {
            exec {
                workingDir 'scripts'
                commandLine 'python3', 'myscript.py'
            }
        }
    }
}

1
我原本想定义一个任务来避免代码重复。在我发布的示例中,所有测试都需要运行脚本。在我的实际项目中,只有一个子集运行脚本,因为它很昂贵并且不总是必要的。我需要添加一个任务或单独添加执行任务。 - user1190707
1
感谢您的帮助 :-) - user1190707
你可以使用 tasks.withType(Test).matching { /* 任何条件 */ } 来配置任务的子集。 - Lukas Körfer

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接