Gradle- выполнить более одной команды в задаче, не прерывая инкрементную сборку

Итак, мы используем инкрементные сборки Gradle и хотим запустить две команды (в идеале из одной задачи). Одно из решений здесь сработало, запустив две команды... однако оно нарушает инкрементную сборку.. Это выглядит примерно так:

task myTask() {
inputs.files(inputFiles)

  project.exec {
     workingDir web
     commandLine('mycmd')
  }
  project.exec {
    workingDir web
    commandLine('mysecond-cmd')
  }
}

если запускать одну команду и работать с инкрементной сборкой, задача выглядела примерно так, что, по-видимому, имеет значение workingDir:

task myTask(type: Exec)  {
     workingDir  myDir // this seems to trigger/enable continuos compilation
    commandLine ('myCmd')
 }

лучшая альтернатива на данный момент - создать 3 задачи, по одной для каждой задачи cmdline, которую я хочу выполнить, и третью для их группировки, что выглядит грязно.

Таким образом, вопрос заключается в следующем: есть ли способ запустить две или более команд в одной задаче с работающими инкрементными сборками?

1 ответ

Я постараюсь ответить на вопрос из комментариев: как я могу дать сигнал от задачи, у которой нет выходных файлов, что сборка должна смотреть определенные файлы. К сожалению, трудно ответить, не зная точного варианта использования.

Для начала, Gradle требует некоторой формы объявленного вывода, которую он может проверить, чтобы увидеть, была ли запущена задача или она должна быть запущена. Учтите, что во время предыдущего запуска задача могла быть неудачной, но входные файлы с тех пор не изменились. Должен ли Gradle выполнить задачу?

Если у вас есть задача, у которой нет выходных данных, это означает, что вам нужно подумать о том, почему эта задача должна выполняться или нет при любом выполнении сборки. Что он делает, если не создает или не изменяет файлы и не взаимодействует с другой частью системы?

Предполагая, что инкрементная сборка является правильным решением, а может и не быть, Gradle позволяет вам обрабатывать необычные сценарии с помощью TaskOutputs.upToDateWhen(Action), Вот пример с простой задачей (gen), который генерирует файл, который действует как ввод для задачи (runIt) без выходов:

task gen {
    ext.outputDir = "$buildDir/stuff"
    outputs.dir outputDir

    doLast {
        new File(outputDir, "test.txt").text = "Hurray!\n"
    }
}

task runIt {
    inputs.dir gen
    outputs.upToDateWhen { !gen.didWork }
    doLast {
        println "Running it"
    }
}

Это указывает на то, что runIt будет работать только в том случае, если изменились входные файлы или задание gen на самом деле что-то сделал. В этом примере эти два сценария соответствуют одному и тому же. Если gen работает, то входные файлы для runIt были изменены.

Ключевым моментом для понимания является то, что условие, которое вы предоставляете upToDateWhen() оценивается на этапе выполнения сборки, а не на этапе конфигурации.

Надеюсь, это поможет, и если вам нужны какие-либо разъяснения, дайте мне знать.

Другие вопросы по тегам