第17章 Using Ant from Gradle 從 Gradle 使用 Ant

2018-02-24 15:56 更新

Gradle 提供了對 Ant 的優(yōu)秀集成。可以在你的 Gradle 構(gòu)建中,使用單獨的 Ant 任務或整個 Ant 構(gòu)建。事實上,你會發(fā)現(xiàn)在 Gradle 中使用 Ant 任務比使用 Ant 的 XML 格式更容易也更強大。你甚至可以只把 Gradle 當作一個強大的 Ant 任務腳本的工具。

Ant 可以分為兩層。第一層是 Ant 的語言。它提供了用于 build.xml,處理的目標,特殊的構(gòu)造方法比如宏,還有其他等等的語法。換句話說,除了 Ant 任務和類型之外全部都有。Gradle 理解這種語言,并允許您直接導入你的 Ant build.xml 到 Gradle 項目中。然后你可以使用你的 Ant 構(gòu)建中的 target,就好像它們是 Gradle task 一樣。

Ant 的第二層是其豐富的 Ant 任務和類型,如 javac、copy或jar。這一層 Gradle 只靠 Groovy 和非常棒的 AntBuilder,對其提供了集成。

最后,由于構(gòu)建腳本是 Groovy 腳本,所以您始終可以作為一個外部進程來執(zhí)行 Ant 構(gòu)建。你的構(gòu)建腳本可能包含有類似這樣的語句:"ant clean compile".execute()?(在 Groovy 中,你可以執(zhí)行字符串。了解更多關于執(zhí)行外部進程,請查看 9.3.2 的'Groovy in Action'或者 Groovy wiki)

你可以把 Gradle 的 Ant 集成當成一個路徑,將你的構(gòu)建從 Ant 遷移至 Gradle 。例如,你可以通過導入您現(xiàn)有的 Ant 構(gòu)建來開始。然后,可以將您的依賴聲明從 Ant 腳本移到您的構(gòu)建文件。最后,您可以將整個任務移動到您的構(gòu)建文件,或者把它們替換為一些 Gradle 插件。這個過程可以隨著時間一點點完成,并且在這整個過程當中你的 Gradle 構(gòu)建都可以使用用。

17.1. Using Ant tasks and types in your build 在你的構(gòu)建中使用 Ant 的任務和類型

在構(gòu)建腳本中,Gradle 提供了一個名為 ant 的屬性。它指向一個?AntBuilder?實例。AntBuilder 用于從你的構(gòu)建腳本中訪問 Ant 任務、 類型和屬性。從 Ant 的 build.xml 格式到 Groovy 之間有一個非常簡單的映射,下面解釋。

通過調(diào)用 AntBuilder 實例上的一個方法,可以執(zhí)行一個 Ant 任務。你可以把任務名稱當作方法名稱使用。例如,你可以通過調(diào)用 ant.echo() 方法執(zhí)行 Ant 的 echo 任務。Ant 任務的屬性會作為 Map 參數(shù)傳給該方法。下面是執(zhí)行 echo 任務的例子。請注意我們還可以混合使用 Groovy 代碼和 Ant 任務標記。這將會非常強大。

Example 17.1. Using an Ant task

build.gradle

task hello << {
    String greeting = 'hello from Ant'
    ant.echo(message: greeting)
}

執(zhí)行 gradle hello

> gradle hello
:hello
[ant:echo] hello from Ant

BUILD SUCCESSFUL

Total time: 1 secs

你可以把一個嵌套文本,通過作為任務方法調(diào)用的參數(shù),把它傳給一個 Ant 任務。在此示例中,我們將把作為嵌套文本的消息傳給 echo 任務:

Example 17.2. Passing nested text to an Ant task

build.gradle

task hello << {
    ant.echo('hello from Ant')
}

執(zhí)行 gradle hello

> gradle hello
:hello
[ant:echo] hello from Ant

BUILD SUCCESSFUL

Total time: 1 secs

你可以在一個閉包里把嵌套的元素傳給一個 Ant 任務。嵌套元素的定義方式與任務相同,通過調(diào)用與我們要定義的元素一樣的名字的方法

Example 17.3. Passing nested elements to an Ant task

build.gradle

task zip << {
    ant.zip(destfile: 'archive.zip') {
        fileset(dir: 'src') {
            include(name: '**.xml')
            exclude(name: '**.java')
        }
    }
}

您可以用訪問任務同樣的方法,把類型名字作為方法名稱,訪問 Ant 類型。方法調(diào)用返回 Ant 數(shù)據(jù)類型,然后可以在構(gòu)建腳本中直接使用。在以下示例中,我們創(chuàng)建一個 Ant 的 path 對象,然后循環(huán)訪問它的內(nèi)容。

Example 17.4. Using an Ant type

build.gradle

task list << {
    def path = ant.path {
        fileset(dir: 'libs', includes: '*.jar')
    }
    path.list().each {
        println it
    }
}

更多有關 AntBuilder 見 8.4 的'Groovy in Action' 或者?Groovy Wiki

17.1.1. Using custom Ant tasks in your build 在構(gòu)建中使用自定義的 Ant 任務

要使自定義任務在您的構(gòu)建中可用,你可以使用 Ant 任務 taskdef(通常更容易) 或 typedef,就像在 build.xml 文件中一樣。然后,您可以像引用內(nèi)置的 Ant 任務一樣引用自定義 Ant 任務。

Example 17.5. Using a custom Ant task

build.gradle

task check << {
    ant.taskdef(resource: 'checkstyletask.properties') {
        classpath {
            fileset(dir: 'libs', includes: '*.jar')
        }
    }
    ant.checkstyle(config: 'checkstyle.xml') {
        fileset(dir: 'src')
    }
}

你可以使用 Gradle 的依賴管理組合類路徑,以用于自定義任務。要做到這一點,你需要定義一個自定義配置的類路徑中,然后將一些依賴項添加到配置中。這在 50.4章節(jié),“如何聲明你的依賴”有更詳細的描述。

Example 17.6. Declaring the classpath for a custom Ant task

build.gradle

configurations {
    pmd
}

dependencies {
    pmd group: 'pmd', name: 'pmd', version: '4.2.5'
}

若要使用類路徑配置,請使用自定義配置里的 asPath 屬性。

Example 17.7. Using a custom Ant task and dependency management together

build.gradle

task check << { ant.taskdef(name: 'pmd', classname: 'net.sourceforge.pmd.ant.PMDTask', classpath: configurations.pmd.asPath) ant.pmd(shortFilenames: 'true', failonruleviolation: 'true', rulesetfiles: file('pmd-rules.xml').toURI().toString()) { formatter(type: 'text', toConsole: 'true') fileset(dir: 'src') } }

17.2. Importing an Ant build 導入 Ant 的構(gòu)建

你可以使用 ant.importBuild() 方法來向 Gradle 項目導入一個 Ant 構(gòu)建。當您導入一個 Ant 構(gòu)建時,每個 Ant 目標被視為一個 Gradle 任務。這意味著你可以用與 Gradle 任務完全相機的方式操縱和執(zhí)行 Ant 目標。

Example 17.8. Importing an Ant build

build.gradle

ant.importBuild 'build.xml'

build.xml

<project>
    <target name="hello">
        <echo>Hello, from Ant</echo>
    </target>
</project>

執(zhí)行 gradle hello

> gradle hello
:hello
[ant:echo] Hello, from Ant

BUILD SUCCESSFUL

Total time: 1 secs

您可以添加一個依賴于 Ant 目標的任務:

build.gradle

ant.importBuild 'build.xml'

task intro(dependsOn: hello) << {
    println 'Hello, from Gradle'
}

執(zhí)行 gradle intro

> gradle intro
:hello
[ant:echo] Hello, from Ant
:intro
Hello, from Gradle

BUILD SUCCESSFUL

Total time: 1 secs

或者,您可以將行為添加到 Ant 目標中:

Example 17.10. Adding behaviour to an Ant target

build.gradle

ant.importBuild 'build.xml'

hello << {
    println 'Hello, from Gradle'
}

執(zhí)行 gradle hello

> gradle hello
:hello
[ant:echo] Hello, from Ant
Hello, from Gradle

BUILD SUCCESSFUL

Total time: 1 secs

它也可以用于一個依賴于 Gradle 任務的 Ant 目標:

Example 17.11. Ant target that depends on Gradle task

build.gradle

ant.importBuild 'build.xml'

task intro << {
    println 'Hello, from Gradle'
}

build.xml

<project>
    <target name="hello" depends="intro">
        <echo>Hello, from Ant</echo>
    </target>
</project>

執(zhí)行 gradle hello

> gradle hello
:intro
Hello, from Gradle
:hello
[ant:echo] Hello, from Ant

BUILD SUCCESSFUL

Total time: 1 secs‘

有時可能需要“改名”來避免 Ant target 生成的 task 與現(xiàn)有的 Gradle task 在命名上沖突。使用?AntBuilder.importBuild()?方法

Example 17.12. Renaming imported Ant targets

build.gradle

ant.importBuild('build.xml') { antTargetName ->
    'a-' + antTargetName
}

build.xml

<project>
    <target name="hello">
        <echo>Hello, from Ant</echo>
    </target>
</project>

執(zhí)行 gradle a-hello

> gradle a-hello
:a-hello
[ant:echo] Hello, from Ant

BUILD SUCCESSFUL

Total time: 1 secs

請注意,雖然這個方法的第二個參數(shù)應該是一個?Transformer,在 Groovy 編程時可以使用簡單的閉包而不是一個匿名內(nèi)部類(或類似的),因為?Groovy 的支持自動強制關閉 single-abstract-method(單一的抽象方法)的類型。

17.3. Ant properties and references 關于 Ant 的屬性和引用

有幾種方法來設置 Ant 屬性,以便使該屬性被 Ant 任務使用。你可以直接在 AntBuilder 實例上設置屬性。Ant 屬性也可以從一個你可以修改的 Map 中獲得。您還可以使用 Ant property 任務。下面是一些如何做到這一點的例子。

Example 17.13. Setting an Ant property

build.gradle

ant.buildDir = buildDir
ant.properties.buildDir = buildDir
ant.properties['buildDir'] = buildDir
ant.property(name: 'buildDir', location: buildDir)

build.xml

<echo>buildDir = ${buildDir}</echo>

有幾種方法可以設置 Ant 引用:

Example 17.14. Getting an Ant property

build.xml

<property name="antProp" value="a property defined in an Ant build"/>

build.gradle

println ant.antProp
println ant.properties.antProp
println ant.properties['antProp']

有幾種方法可以獲取 Ant 引用:

Example 17.15. Setting an Ant reference

build.gradle

ant.path(id: 'classpath', location: 'libs')
ant.references.classpath = ant.path(location: 'libs')
ant.references['classpath'] = ant.path(location: 'libs')

build.xml

<path refid="classpath"/>

有幾種方法可以獲取 Ant 引用:

Example 17.16. Getting an Ant reference

build.xml

<path id="antPath" location="libs"/>

``
build.gradle

println ant.references.antPath
println ant.references['antPath']

17.4. API

AntBuilder?提供 Ant 的集成

以上內(nèi)容是否對您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號
微信公眾號

編程獅公眾號