Gradle常用技巧


转载请说明出处!
作者:kqw攻城狮
出处:个人站 | CSDN


Gradle

http://google.github.io/android-gradle-dsl/current/index.html

https://docs.gradle.org/current/userguide/java_plugin.html

打包多个版本

开发过程中我们经常需要打包多个版本的apk,最为常见的,一个是release版本,一个是debug版本,他们可能使用的api也有所区别,手动改起来总是很麻烦。
我们可以通过Gradle,配置多个版本,他们有各自的参数来区分不同的版本。如下,在 app/build.gradle 系统默认会给我生成release版本,我们可以手动自己添加一个版本,我这里命名为debug,分别添加了三种类型的参数。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
apply plugin: 'com.android.application'
android {
……
buildTypes {
release {
……
buildConfigField("boolean", "isDebug", "false")
}
debug {
// 添加了boolean类型的参数
buildConfigField("boolean", "isDebug", "true")
// 添加了String类型的参数
buildConfigField("String", "coder", "\"kongqw\"")
// 添加了int类型的参数
buildConfigField("int", "age", "26")
}
}
}
……
dependencies {
……
}

添加完成后Rebuild,会在 BuildConfig 下看到我们添加的参数

P1

因为是静态变量,取值时直接用类名点变量名即可

P2

上述属于在Java代码中添加字段,同样的,Gradle也支持添加xml属性,类似这样

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
apply plugin: 'com.android.application'
android {
……
defaultConfig {
……
}
buildTypes {
release {
……
}
debug {
……
resValue("bool", "is_debug", "true")
resValue("string", "coder", "\"kongqw\"")
resValue("integer", "age", "26")
}
}
}
dependencies {
……
}

添加完以后Rebuild,会在generated.xml 下生产如下字段

P3

但是要避免和string.xml文件里的字段重复

在xml中使用

1
android:text="@string/coder"

或者再Java中使用

1
String coder = getString(R.string.coder);

添加工程build时间

有时候,测试和产品总是会拿着手机跑过来问你,“有没有更新?”、“帮我看一下我装的是不是最新的版本?”,总是很烦,我们可以利用Gradle,获取到工程的Build时间,在测试版本打印出来,可以为工程师节省不少时间。

Gradle支持直接添加方法

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
apply plugin: 'com.android.application'
android {
……
defaultConfig {
……
resValue("string", "build_time", getDate())
// BuildTime
buildConfigField("String", "buildTime", "\"" + getDate() + "\"")
}
buildTypes {
release {
……
}
debug {
……
}
}
}
def getDate() {
return new Date().format("yyyy-MM-dd HH:mm:ss")
}
dependencies {
……
}

判断的时候调用

1
BuildConfig.buildTime

或者

1
getString(R.string.build_time)

P4

不同版本包名不同

我们都知道,相同包名,不同签名,在一台手机上是无法同时安装的。前面我们配置了两个不同的版本,release版本肯定是用正式签名,debug版本我们通常都会使用测试签名。那么问题来了,测试人员如果已经在手机上安装了上线的版本,再装测试版,就会有冲突,必须要卸载一个,那么最好的办法就是修改测试版包名。这样包名不同,两个版本同时安装,也不会有冲突。

同样的,Gradle依然可以轻松的帮我们做到。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
apply plugin: 'com.android.application'
android {
……
defaultConfig {
……
}
buildTypes {
release {
……
}
debug {
……
applicationIdSuffix ".debug"
}
}
}
dependencies {
……
}

可以看到我们在 debug 版本添加了applicationIdSuffix,其值为 .debug,顾名思义,是debug版本在包名后面添加.debug后缀。

多渠道打包

多渠道打包,打包多个市场的apk,用来统计。

首先在AndroidManifest文件添加meta-data

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<?xml version="1.0" encoding="utf-8"?>
<manifest ……>
<application
……>
<meta-data
android:name="PRODUCT"
android:value="${CHANNEL_VALUE}"/>
<activity ……>
……
</activity>
</application>
</manifest>

app/build.gradle添加productFlavors,如下所示,添加 XIAO_MIGOOGLE_PLAY两个渠道

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
apply plugin: 'com.android.application'
android {
……
defaultConfig {
……
}
buildTypes {
release {
……
}
debug {
……
}
}
productFlavors {
xiaomi {
manifestPlaceholders = [CHANNEL_VALUE: "XIAO_MI"]
}
googlePlay {
manifestPlaceholders = [CHANNEL_VALUE: "GOOGLE_PLAY"]
}
}
}
dependencies {
……
}

获取渠道

1
2
3
4
5
6
7
try {
ApplicationInfo applicationInfo = getPackageManager().getApplicationInfo(getPackageName(), PackageManager.GET_META_DATA);
String channel = applicationInfo.metaData.getString("PRODUCT");
Log.i(TAG, "onCreate: 渠道 :" + channel);
} catch (PackageManager.NameNotFoundException e) {
e.printStackTrace();
}
坚持原创技术分享,您的支持将鼓励我继续创作!