基于gradle的jacoco offline模式

2024-01-02 15:04
文章标签 模式 offline gradle jacoco

本文主要是介绍基于gradle的jacoco offline模式,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

jacoco的官网:EclEmma - JaCoCo Java Code Coverage Library

gradle语法:任务依赖 - Gradle 用户指南官方文档中文版 - UDN开源文档

在使用jacoco的时候,有时候需要将当前待测试的java类,添加到@PrepareForTest() 中,这会导致生成的行覆盖html中,当前类的覆盖率是为0,网上说比较好的解决办法是,使用jacoco offline模式,但是网上给的参考大部分都是maven文件,或者给的gradle文件使用不了。

github上提供了两个比较好的示例:

示例一:GitHub - MohammadAlavi1986/gradle-jacoo-offline-instrumentation

该示例是基于java程序的gradle配置,不使用android程序

示例二:https://github.com/h8MyJob/PowerMockJacocoDemo

该示例比较老了,运行起来有很多问题。

下面是我运行成功的配置(摸索了好久。。。)

其中,gradle版本是:gradle-7.5-bin.zip

顶层的build.gradle文件:

// Top-level build file where you can add configuration options common to all sub-projects/modules.
plugins {id 'com.android.application' version '7.4.1' apply falseid 'com.android.library' version '7.4.1' apply false
}

module的build.gradle文件:

    //单元测试相关依赖testImplementation("org.powermock:powermock-module-junit4:2.0.7")testImplementation("org.powermock:powermock-module-junit4-rule:1.7.4")testImplementation("org.powermock:powermock-api-mockito2:2.0.7")testImplementation("org.powermock:powermock-core:2.0.7")testImplementation("org.mockito:mockito-core:3.11.2")testImplementation("junit:junit:4.13.2")testImplementation("android.arch.core:core-testing:1.1.1")testImplementation("org.mockito:mockito-inline:3.11.2")

最后 jacoco_offline.gradle 文件如下:

apply plugin: 'jacoco'configurations {jacocoAntjacocoRuntime
}// 设置 jacoco offline 模式的Report目录
def jacocoOfflineDir = layout.buildDirectory.dir('jacocoOfflineReport')jacoco {toolVersion = "0.8.11"  // 升级最新的版本reportsDirectory = jacocoOfflineDir
}def offline_instrumented_outputDir = "$buildDir.path/intermediates/classes-instrumented/debugCoverage"tasks.withType(Test) {jacoco.includeNoLocationClasses = truejacoco.excludes = ['jdk.internal.*']
}// 设置原java文件的目录
def coverageSourceDirs = ['src/main/java'
]// 设置生成覆盖率报告时,需要排除的文件
def excludeFiles = ['**/R.class','**/R$*.class','**/Manifest*.*','**/*Test*.*','android/**/*.*','**/BuildConfig.*','**/**Bean.class','**/inputmethod/*','**/config/*.*','**/flex/*.*','**/AssetsUtils.class'
]// 设置生成覆盖率报告时,仅仅支持的文件
def includeFiles = ['**/BuildConfig.*','**/HCInfoUtil.*'
]def classFileDir = fileTree(dir: 'build/intermediates/javac/debug/classes',excludes: excludeFiles
//        includes: includeFiles
)// (1)生成jacoco动态覆盖率报告(jacoco属于动态检查)
task jacocoTestReport(type: JacocoReport, dependsOn: "test") {group = "Reporting"description = "Generate Jacoco coverage reports"classDirectories.from = classFileDirgetSourceDirectories().setFrom(files(coverageSourceDirs))getExecutionData().setFrom(files('./build/jacoco/testDebugUnitTest.exec'))}jacocoTestReport {reports {xml.enabled  falsehtml.enabled  truehtml.destination file("build/test-results/jacocoHtml")}
}/*** jacoco offline instrumentation jacoco离线检查* 先生成原始的预检测的*.class,然后在此基础上生成.exec文件,而不是在运行中生成检测的class文件*/
task createOfflineTestCoverageReport(dependsOn: ['clean', 'instrument', 'testDebugUnitTest']) {group = "Reporting"doLast {ant.taskdef(name: 'report',classname: 'org.jacoco.ant.ReportTask',classpath: configurations.jacocoAnt.asPath)ant.report() {executiondata {ant.file(file: "$buildDir.path/jacoco/testDebugUnitTest.exec")}structure(name: 'Example') {classfiles {fileset(dir: "$project.buildDir/intermediates/javac/debug/classes")}sourcefiles {fileset(dir: 'src/main/java')}}// offline模式生成的报告路径,此报告不能排除文件,一般不用,而是在之后的task中生成 html 报告
//            html(destdir: "$buildDir.path/reports/jacocoHtml")}}
}gradle.taskGraph.whenReady { graph ->if (graph.hasTask(instrument)) {tasks.withType(Test) {doFirst {systemProperty 'jacoco-agent.destfile', buildDir.path + '/jacoco/testDebugUnitTest.exec'classpath = files(offline_instrumented_outputDir) + classpath + configurations.jacocoRuntime}}}
}/**  Instruments the classes per se*/
task instrument(dependsOn:'compileDebugUnitTestSources') {doLast {println 'Instrumenting classes'ant.taskdef(name: 'instrument',classname: 'org.jacoco.ant.InstrumentTask',classpath: configurations.jacocoAnt.asPath)ant.instrument(destdir: offline_instrumented_outputDir) {fileset(dir: "$buildDir.path/intermediates/javac/debug/classes")}}
}// 将 offline 模式生成的exec文件拷贝到另一个目录,与jacoco动态生成区分
task copyTask(dependsOn:['createOfflineTestCoverageReport']) {doLast{copy {from './build/jacoco/testDebugUnitTest.exec'into './build/jacoco/offline'}}
}// 删除 offline 生成的html报告,防止执行当前生成报告未更新
task deleteReportTask(type: Delete) {doLast {delete jacocoOfflineDir.get().toString()+'/jacocoTestReportOffline'}
}// 使用 offline 模式下的 exec 文件,生成html报告
task jacocoTestReportOffline(type: JacocoReport, dependsOn:['copyTask', 'deleteReportTask']) {group = "Reporting"description = "Generate Jacoco coverage reports"classDirectories.from = classFileDirgetSourceDirectories().setFrom(files(coverageSourceDirs))getExecutionData().setFrom(files('./build/jacoco/offline/testDebugUnitTest.exec'))
}// (2)生成 jacoco offline 模式的覆盖率报告
task GenerateJacocoOfflineCoverageReports(dependsOn:'jacocoTestReportOffline') {group = "Reporting"doLast {println '生成 jacoco offline 报告的路径:'println jacocoOfflineDir.get().toString() + '/jacocoTestReportOffline'}
}

这篇关于基于gradle的jacoco offline模式的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/562809

相关文章

Java设计模式---迭代器模式(Iterator)解读

《Java设计模式---迭代器模式(Iterator)解读》:本文主要介绍Java设计模式---迭代器模式(Iterator),具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,... 目录1、迭代器(Iterator)1.1、结构1.2、常用方法1.3、本质1、解耦集合与遍历逻辑2、统一

Java 线程安全与 volatile与单例模式问题及解决方案

《Java线程安全与volatile与单例模式问题及解决方案》文章主要讲解线程安全问题的五个成因(调度随机、变量修改、非原子操作、内存可见性、指令重排序)及解决方案,强调使用volatile关键字... 目录什么是线程安全线程安全问题的产生与解决方案线程的调度是随机的多个线程对同一个变量进行修改线程的修改操

Redis Cluster模式配置

《RedisCluster模式配置》:本文主要介绍RedisCluster模式配置,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧... 目录分片 一、分片的本质与核心价值二、分片实现方案对比 ‌三、分片算法详解1. ‌范围分片(顺序分片)‌2. ‌哈希分片3. ‌虚

Linux系统中的firewall-offline-cmd详解(收藏版)

《Linux系统中的firewall-offline-cmd详解(收藏版)》firewall-offline-cmd是firewalld的一个命令行工具,专门设计用于在没有运行firewalld服务的... 目录主要用途基本语法选项1. 状态管理2. 区域管理3. 服务管理4. 端口管理5. ICMP 阻断

RabbitMQ工作模式中的RPC通信模式详解

《RabbitMQ工作模式中的RPC通信模式详解》在RabbitMQ中,RPC模式通过消息队列实现远程调用功能,这篇文章给大家介绍RabbitMQ工作模式之RPC通信模式,感兴趣的朋友一起看看吧... 目录RPC通信模式概述工作流程代码案例引入依赖常量类编写客户端代码编写服务端代码RPC通信模式概述在R

SQL Server身份验证模式步骤和示例代码

《SQLServer身份验证模式步骤和示例代码》SQLServer是一个广泛使用的关系数据库管理系统,通常使用两种身份验证模式:Windows身份验证和SQLServer身份验证,本文将详细介绍身份... 目录身份验证方式的概念更改身份验证方式的步骤方法一:使用SQL Server Management S

Redis高可用-主从复制、哨兵模式与集群模式详解

《Redis高可用-主从复制、哨兵模式与集群模式详解》:本文主要介绍Redis高可用-主从复制、哨兵模式与集群模式的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝... 目录Redis高可用-主从复制、哨兵模式与集群模式概要一、主从复制(Master-Slave Repli

Gradle在国内配置镜像加速的实现步骤

《Gradle在国内配置镜像加速的实现步骤》在国内使用Gradle构建项目时,最大的痛点就是依赖下载贼慢,甚至卡死,下面教你如何配置国内镜像加速Gradle下载依赖,主要是通过改写repositori... 目录引言一、修改 build.gradle 或 settings.gradle 的 reposito

Gradle下如何搭建SpringCloud分布式环境

《Gradle下如何搭建SpringCloud分布式环境》:本文主要介绍Gradle下如何搭建SpringCloud分布式环境问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地... 目录Gradle下搭建SpringCloud分布式环境1.idea配置好gradle2.创建一个空的gr

一文带你搞懂Redis Stream的6种消息处理模式

《一文带你搞懂RedisStream的6种消息处理模式》Redis5.0版本引入的Stream数据类型,为Redis生态带来了强大而灵活的消息队列功能,本文将为大家详细介绍RedisStream的6... 目录1. 简单消费模式(Simple Consumption)基本概念核心命令实现示例使用场景优缺点2