注目の記事

Gradle入門

この記事は公開されてから1年以上経過しています。情報が古い可能性がありますので、ご注意ください。

2013-10-22_1158

よく訓練されたアップル信者、都元です。Gradle(グレードル)つかってますか? 筆者は、プロダクトコードを書くのも好きなのですが、その周辺にある「プロジェクトのライフサイクル管理」の自動化にも非常に興味を持っています。つい半年前くらいまではMaven信者だったのですが、今は宗旨替えをし、Gradleにどっぷりハマっております。

Gradleは、進化系のビルド自動化ツールです。Gradleは、ソフトウェアパッケージもちろん、その他様々な形式のプロジェクト(例えば自動生成された静的Webサイトやドキュメント等)のビルド・テスト・(ライブラリ等の)公開・デプロイ・その他を自動化します。

プロジェクトライフサイクルマネジメントツール?

このようなビルド自動化は、古くはGNU Makeやシェルスクリプトが利用されており、その後Javaの世界ではAnt, Mavenと進化を遂げて来ました。Gradleはその進化の最先端、かどうかは分かりませんが、これらの流れを汲むプロダクトの一つです。

これらのツールは一言で「ビルドツール」と呼ぶ事もあります。しかしそもそも「ビルド」という言葉は、多くの場合、複数の要素(ファイル等?)を集約して1つの成果物を生成するプロセス、または何らかのファイル変換をするプロセス、として捉えられているようです *1。従って、これらのツールは「アプリケーション」の「ビルド」を行うだけではなく、「プロジェクト」の「ライフサイクルに関わる処理を管理」している、と捉えるのが多分正解なんだろうと思っています。この仕事にぱっとした名前が無いので、さらっと「ビルドツール」と呼ばれてしまうのでしょう。「プロジェクトライフサイクルマネジメントツール」というのがジャストな表現かもしれませんが、抽象的ですし何よりも長い…。

話が横に逸れてしまいましたが。要するに「ビルドツール」と呼ばれてしまいがちですが、アプリケーションのビルド以外にも多くの使い方がある、ということです。また、Javaと縁が深いが故、Javaプロジェクト用のツールとして見られてしまうことも多いのですが、そんなことはありません。本エントリーでは、Javaプロジェクトではない例を紹介しています。

Gradleのインストール

MacOS環境でしかご案内できませんが。一番簡単なのはbrew install gradleです。

ただ、Gradleを真面目に使い出すと、複数バージョンのGradleを切り替えて使うシーンが予想できますので、筆者はGVM (※)を経由したインストールをしています。先のリンクからまずGVMを導入し、その上でgvm install gradleでインストール可能です。下記のコマンドで、バージョン情報が出ればインストールが成功しています。

※ GVM は現在 skdman に名称変更しています。

$ gradle -v

------------------------------------------------------------
Gradle 1.8
------------------------------------------------------------

Build time:   2013-09-24 07:32:33 UTC
Build number: none
Revision:     7970ec3503b4f5767ee1c1c69f8b4186c4763e3d

Groovy:       1.8.6
Ant:          Apache Ant(TM) version 1.9.2 compiled on July 8 2013
Ivy:          2.2.0
JVM:          1.7.0_25 (Oracle Corporation 23.25-b01)
OS:           Mac OS X 10.8.5 x86_64

本エントリー投下後、そのスジの方からのご指摘がございましたのでここに引用させていただきやす。

Groovyベースのビルドスクリプト

一般的に、タスクはある意味手続きですので、手続き的な記述がなされることが多いでしょう。シェルスクリプトによる実装はまさに手続き的です。一方で、それを全てXMLで宣言的に記述しようとしたのがMavenでしょう。

Gradleは、GroovyベースのDSLを用いて、そのプロジェクトのビルドライフサイクルに関わるタスクを記述します。GroovyはJavaVM (JVM)上で動作する、Javaに非常に良く似た文法を持ち、さらに独自の拡張を行った言語です。Javaを読み書き出来る方であれば、少ない学習コストでGroovyを読み書きできるようになるでしょう。Groovyはそのような言語ですので、一面としては「手続き的」記述がなされます。一方、前述のGroovy独自の拡張によって、プログラミング言語特有の手続き的な匂いを抑えた、宣言的な記述も可能になっています。

さて、能書きはこのくらいにして、ハロワいってみますか。まず、あるプロジェクトgradle1があると考え、そのディレクトリを作成してください。その中に、以下の内容でbuild.gradleというファイルを作ってください。これがGradleのビルドスクリプトを記述するファイルです。

task hello << {
    println "Hello, ${System.properties['user.name']}"
}

以上で、helloというタスクを定義しました。その内容は手続き的に書かれていますが、まぁ普通にハローワールドです。実行は、gradleコマンドの引数に、実行対象となるタスク名を記述します。

$ gradle hello
:hello
Hello, daisuke

BUILD SUCCESSFUL

Total time: 1.679 secs

あなたのユーザ名が表示されたでしょうか?

ちょっと実用的に見える小さなスクリプト

さて、入門編だとこのようにハロワを書いて終わってしまうことが多いのですが。もう少し実用性を感じられるプロジェクトを作ってみましょう。 先ほどのプロジェクトにsrc/index.htmlというファイルを追加します。

$ tree
.
├── build.gradle
└── src
    └── index.html

1 directory, 2 files

中身は以下の通り。この時点で、何が起こるかだいたい分かったのではないでしょうか。

<html><body>Hello, @username@!</body></html>

続いてbuild.gradleに以下のように変更します。

import org.apache.tools.ant.filters.*

task build(type: Copy) {
	from 'src'
	into buildDir
	include '**/*.html'
	filter(ReplaceTokens, tokens: [username: System.properties['user.name']])
}

そしてbuildタスクを実行して、その後の状況をtreeで表示してみます。

$ gradle build
:build

BUILD SUCCESSFUL

Total time: 1.646 secs
$ tree
.
├── build
│   └── index.html
├── build.gradle
└── src
    └── index.html

2 directories, 3 files

buildというディレクトリが増えていて、その中にもindex.htmlがあります。中身を確認してみましょう。

$ cat build/index.html
<html><body>Hello, daisuke!</body></html>

と、いう感じです。文字列の置換、という「ビルド」が記述できました。

まとめ

さて、いかがでしたか。早足でしたがGradleによるプロジェクトライフサイクルマネジメントを見てみました。

今回はご紹介できなかったので、いずれまた、と思っているのですが、このWebサイトをサーバにデプロイする、という作業もtask deploy ...という形で記述することにより、プロジェクトの周辺作業がどんどん自動化されていきます。

脚注

  1. コンパイルというフェーズの無い、PHPやRubyのプロジェクトにおいては、あまりビルドという言葉は使わないようです。