つかえるGradleプロジェクトの作り方
2015/4/25 DroidKaigi
山 誠 (@zaki50)
自己紹介
• YAMAZAKI Makoto (@zaki50)
• 株式会社 uPhyca 所属
Gradleとは
• Antのようなあらゆる目的に使用できる汎用ビルドツール
• Mavenのような規約によるビルドフレームワーク
• マルチプロジェクトをサポート
• Ivyベースの強力な依存管理
• Maven/Ivyリポジトリのサポート
• Antタスクが使用可能
• Groovyベースのビルドスクリプト
http://gradle.monochromeroad.com/docs/userguide/introduction.html
プロジェクト構成
モジュールを追加
build.grade
buildscript {

repositories {

jcenter()

}

dependencies {

classpath 'com.android.tools.build:gradle:1.1.0'

}

}



allprojects {

repositories {

jcenter()

}

}
app/build.gradle
apply plugin: 'com.android.application'



android {

compileSdkVersion 22

buildToolsVersion "22.0.1"

defaultConfig {

applicationId "com.example.myapplication"

minSdkVersion 9

targetSdkVersion 22

versionCode 1

versionName "1.0"

}

buildTypes {

release {

minifyEnabled false

proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'

}

}

}



dependencies {

compile fileTree(dir: 'libs', include: ['*.jar'])

compile 'com.android.support:appcompat-v7:22.1.0'

}

ポイント
• build.gradleのあるディレクトリがプロジェクト
• build.grade は Groovyスクリプト
• {} はクロージャー
• 項目の設定はメソッド呼び出し
最初からできること
• デバッグビルド
• リリースビルド(署名なし)
設定するとできること
• buildToolsVersion等の一元管理
• デバッグビルド用の証明書をプロジェクトに含めて共有
• リリース用apkへの署名
• リリース署名設定の外出し
• バージョンコード設定の自動化
• git hashをプログラムに埋め込む
• アプリプロジェクトとライブラリプロジェクトのdebug連動
• ビルドサーバーでのビルドの高速化
プロジェクト作成
∼プロジェクトの作成とモジュールの追加∼
buildToolsVersion等の一元管理
buildscript {
…

}



allprojects {
…

}

project.ext {

compileSdkVersion = 22

buildToolsVersion = '22.0.1'

}
/build.gradle /app/build.gradle
apply plugin: 'com.android.application'



android {

compileSdkVersion rootProject.ext.compileSdkVersion

buildToolsVersion rootProject.ext.buildToolsVersion

defaultConfig {
…

}

buildTypes {
…

}

}

デバッグビルド用の証明書を共有
apply plugin: 'com.android.application'



android {
…

signingConfigs {

debug {

storeFile rootProject.file(‘./debug.keystore’)

}

}

buildTypes {
…

}
…

}
/app/build.gradle
リリースapkへの署名
apply plugin: 'com.android.application'



android {
…

signingConfigs {

release {

storeFile file('/Users/zaki/DroidKaigi/release.jks')

storePassword 'android'

keyAlias 'release'

keyPassword 'android'

}
debug {
…
}

}

buildTypes {

release {
…

signingConfig signingConfigs.release

}

}

}
/app/build.gradle
リリース署名設定の外出し(1)
buildscript {
…

}



allprojects {
…



File propertiesFile = rootProject.file("ext.properties")

if (propertiesFile.exists()) {

Properties properties = new Properties()

propertiesFile.withInputStream {

properties.load(it)

}

properties.entrySet().each {

project.ext.set(it.key, it.value)

}

}

}

…
/build.gradle
リリース署名設定の外出し(2)
/app/build.gradle
apply plugin: 'com.android.application'



android {
…

signingConfigs {

if (project.hasProperty('signingStoreFile')) {

release {

storeFile file(signingStoreFile)

storePassword signingStorePassword

keyAlias signingKeyAlias

keyPassword signingKeyPassword

}

}
…

}

buildTypes {

release {

minifyEnabled false

proguardFiles getDefaultProguardFile(‘proguard-android.txt'),

if (project.hasProperty('signingStoreFile')) {

signingConfig signingConfigs.release

}

}

}
…

}
バージョンコード設定の自動化
apply plugin: 'com.android.application'



def versionMajor = 1

def versionMinor = 0

def versionPatch = 0

def versionBuild = 0



android {

compileSdkVersion rootProject.ext.compileSdkVersion

buildToolsVersion rootProject.ext.buildToolsVersion

defaultConfig {

applicationId "com.example.myapplication"

minSdkVersion 9

targetSdkVersion 22

versionCode versionMajor * 10000 + versionMinor * 1000 + versionPatch * 100 + versionBuild

versionName "${versionMajor}.${versionMinor}.${versionPatch}"

}
…

}
/app/build.gradle
git hashをプログラムに埋め込む
apply plugin: 'com.android.application'



def versionMajor = 1

def versionMinor = 0

def versionPatch = 0

def versionBuild = 0



android {

compileSdkVersion rootProject.ext.compileSdkVersion

buildToolsVersion rootProject.ext.buildToolsVersion

defaultConfig {

applicationId "com.example.myapplication"

minSdkVersion 9

targetSdkVersion 22

versionCode versionMajor * 10000 + versionMinor * 1000 + versionPatch * 100 + versionBuild

versionName "${versionMajor}.${versionMinor}.${versionPatch}"



buildConfigField "String", "GIT_HASH", """ +

'git rev-parse --short HEAD'.execute([], project.rootDir).text.trim() + """

}

…
}
/app/build.gradle
プロジェクトのdebug連動(1)
apply plugin: 'com.android.library'



android {
…



defaultPublishConfig 'libRelease'

publishNonDefault true

…

productFlavors {

lib

}

}



…
/mylibrary/build.gradle
プロジェクトのdebug連動(2)
apply plugin: 'com.android.application'



…
android {

…

}

dependencies {

compile fileTree(dir: 'libs', include: ['*.jar'])

compile 'com.android.support:appcompat-v7:22.1.0'

debugCompile project(path: ':mylibrary', configuration: 'libDebug')

releaseCompile project(path: ':mylibrary', configuration: 'libRelease')

}

/app/build.gradle
ビルドサーバーでの高速化
buildscript {

…
}



allprojects {

…


project.plugins.whenPluginAdded { plugin ->

if ("com.android.build.gradle.AppPlugin".equals(plugin.class.name)) {

project.android.dexOptions.preDexLibraries = rootProject.ext.preDexLibs

} else if ("com.android.build.gradle.LibraryPlugin".equals(plugin.class.name)) {

project.android.dexOptions.preDexLibraries = rootProject.ext.preDexLibs

}

}

}



project.ext {

// CIサーバなどでは -PdisablePreDex をつける。 preDexが省略されてビルドが速くなる

preDexLibs = !project.hasProperty('disablePreDex')

…

}
/build.gradle
まとめ
• build.grade はスクリプトなので可能性
は無限大
• 楽をするための苦労を惜しまない
• let’s hack!
参考
http://tools.android.com/tech-docs/new-build-system/user-guide
https://github.com/zaki50/android_gradle_template
https://techbooster.booth.pm/items/75014
Android実践プログラミング 第五章
android_gradle_template
Gradle Plugin User Guide

20150425 DroidKaigi つかえるGradleプロジェクトの作り方