多模块Android项目自定义Gradle测试任务技术问询
多模块Android项目自定义Gradle测试任务实现方案
需求明确
- 一键执行全模块单元测试,覆盖三类模块:
- Android应用模块(对应任务如
testOrangeDebugUnitTest) - Android库模块(对应任务如
testDebug) - Java/Kotlin库模块(对应任务如
test)
- Android应用模块(对应任务如
- 支持指定单个Product Flavor,避免全量测试耗时
- 仅运行Debug构建类型的Android单元测试
- 自动识别新增模块,无需硬编码模块名称
问题解决与实现代码
1. 非字符串匹配的任务过滤与收集
不用解析任务名字符串,直接通过Gradle Android插件提供的变体API进行类型安全的任务筛选,结合模块插件类型区分不同模块:
- Android应用/库模块:通过
testVariants获取测试变体,直接访问buildType和productFlavors属性过滤 - Java/Kotlin库模块:直接获取默认的
test任务
2. 让自定义任务执行收集到的测试任务
通过Gradle的任务依赖机制,将收集到的所有测试任务设置为自定义任务的依赖,执行自定义任务时会自动触发所有依赖任务。
完整实现代码
在项目根目录的build.gradle中添加以下代码:
// 定义可配置的Product Flavor参数,命令行可覆盖默认值 ext { testFlavor = "" // 示例:命令行传入指定风味 ./gradlew runAllUnitTests -PtestFlavor=orange } // 创建自定义全局测试任务 task runAllUnitTests { group = "Verification" description = "一键执行所有模块的Debug单元测试,支持指定Product Flavor" // 延迟配置,确保所有子模块的任务都已初始化完成 doFirst { def targetTestTasks = [] // 遍历所有子项目 subprojects { subproject -> // 处理Android应用/库模块 if (subproject.plugins.hasPlugin('com.android.application') || subproject.plugins.hasPlugin('com.android.library')) { subproject.android.testVariants.all { variant -> // 仅保留Debug构建类型的测试变体 if (variant.buildType.name == 'debug') { // 根据配置的风味过滤任务 def isFlavorMatch = project.ext.testFlavor.isEmpty() ? variant.productFlavors.isEmpty() // 未指定风味时,仅选无风味的变体 : variant.productFlavors.any { it.name == project.ext.testFlavor } // 指定风味时匹配对应变体 if (isFlavorMatch) { targetTestTasks.add(variant.testTask) } } } } // 处理Java/Kotlin库模块 else if (subproject.plugins.hasPlugin('java') || subproject.plugins.hasPlugin('java-library') || subproject.plugins.hasPlugin('org.jetbrains.kotlin.jvm')) { def javaTestTask = subproject.tasks.findByName('test') if (javaTestTask) { targetTestTasks.add(javaTestTask) } } } // 将筛选后的测试任务设置为当前任务的依赖 dependsOn targetTestTasks } }
使用方式
- 执行无指定风味的Debug单元测试:
./gradlew runAllUnitTests - 执行指定风味(如
orange)的Debug单元测试:./gradlew runAllUnitTests -PtestFlavor=orange
内容的提问来源于stack exchange,提问作者JJD
相关产品推荐
相关产品推荐

