自定义gradle插件实现不同版本app的听云配置文件

问题由来

在做项目的时候,需要接入听云监测系统,因为我们的app分为 debug->preRelease->release 版本。这样的话,需要再在三个不同的版本平台同时接入。
不过听云的接入有一点比较坑的地方是需要配置tingyun.properties文件再app目录,
每次手动去新建肯定是不合适的,自然而然的就想到了gradle打包脚本,不过一开始是写在gradle.properties文件里的,具体代码如下

File TingyunProperties = new File("${project.projectDir.absolutePath}/tingyun.properties")
            TingyunProperties.createNewFile()
        //gradle build package name
        android.applicationVariants.all { variant ->
        variant.productFlavors.each { flavor ->
            def variantSuffix = variant.name.capitalize()
            def generateResourcesTask = project.tasks.getByName("compile${variantSuffix}Sources")
            def generatePropertiesTask = task("TingyunGenerateProperties${variantSuffix}") {
                doLast {
                    Properties properties = new Properties()
                    properties.load(TingyunProperties.newDataInputStream())
                    properties.setProperty("authKey", "")
                    properties.setProperty("appKey", flavor.manifestPlaceholders.tingyunAppToken)
                    properties.setProperty("mapping_file_auto_upload", "true")
                    properties.store(TingyunProperties.newWriter(), null)
                }
            }
            generateResourcesTask.dependsOn generatePropertiesTask
        }

这就导致了一个问题,日常开发每次打包都会新建TingyunProperties的文件,次次提交都更改,有时候还会冲突,就会很烦,日常开发过程中其实并不需要我们去建立这个文件,只有在需要的时候新建一下就行了,于是就考虑到了自定义gradle插件来解决这个问题

自定义gradle插件流程

这个网上教程很多,我就不细讲了,可以参考 https://www.jianshu.com/p/0b7c141a5b75
这里主要讲一下需要注意的点和遇到的坑

productFlavor的获取

由于我们需要用到 productFlavor 这个属性去获取版本的名字,比如debug,所以在我们gradle插件的build.gradle 需要引入‘com.android.tools.build:gradle:3.6.3’
具体代码如下:

apply plugin: 'groovy'
apply plugin: 'maven'
dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
    implementation 'com.android.tools.build:gradle:3.6.3'
    implementation gradleApi()
}
/**
 * 上传本地marven
 */
apply plugin: 'maven-publish'
publishing{
    publications{
        //这个名字任意取
        tingyun(MavenPublication){
            from  components.java
            groupId 'com.derek'
            artifactId 'tingyun'
            version '1.0.0'
        }
    }
}

plugin代码

package com.example.tingyunplugin
import com.android.build.gradle.AppExtension
import com.android.build.gradle.api.ApplicationVariant
import com.android.builder.model.ProductFlavor
import org.gradle.api.Plugin
import org.gradle.api.Project

class tingyunPlugin implements Plugin<Project> {
    @Override
    void apply(Project project) {
        project.afterEvaluate {
            AppExtension android = project.extensions.android
            android.applicationVariants.all { ApplicationVariant variant  ->
                variant.productFlavors.each { ProductFlavor flavor ->
                    def variantSuffix = variant.name.capitalize()
                    //创建一个Task任务去处理听云
                    TingyunTask tingyunTask = project.tasks.create("createTingyunProperties${variantSuffix}", TingyunTask)
                    tingyunTask.flavor = flavor
                }
            }

        }


    }
}

Task代码

package com.example.tingyunplugin
import com.android.builder.model.ProductFlavor
import org.gradle.api.DefaultTask
import org.gradle.api.tasks.TaskAction

class TingyunTask extends DefaultTask {
    ProductFlavor flavor
    TingyunTask(){
        group = "tingyun"
    }
    @TaskAction
    def run() {
        File TingyunProperties = new File("${project.projectDir.absolutePath}/tingyun.properties")
        TingyunProperties.createNewFile()
        Properties properties = new Properties()
        properties.load(TingyunProperties.newDataInputStream())
        properties.setProperty("authKey", "")
        properties.setProperty("appKey", flavor.manifestPlaceholders.tingyunAppToken)
        properties.setProperty("mapping_file_auto_upload", "true")
        properties.store(TingyunProperties.newWriter(), null)
    }

}

解释一下代码 :

TingyunTask(){
        group = "tingyun"
    }

这个代码是给我们的gradle任务分组,在AS中,我们可以看到很多的task,如图所示
在这里插入图片描述
那么,这个方法的作用就是给任务分组,如上图的tingyun

要想使用这个插件一定要将该插件上传到仓库

当我们写完自定义插件之后,不是直接引用一下就可以直接用了,一定要上传到(本地)仓库。
上传本地仓库(远程仓库一样)的gradle配置在gradle插件 的build.gradle中,代码如下

apply plugin: 'maven-publish'
publishing{
    publications{
        //这个名字任意取
        tingyun(MavenPublication){//tingyun的名字任意
            from  components.java //表示我们要将源代码打进jar包
            groupId 'com.derek'
            artifactId 'tingyun'
            version '1.0.0'
        }
    }

当搞定这个之后,我们就可以在gradle的任务栏中看到这个发布按钮了
在这里插入图片描述
点击publishToMavenLocal就可以发布到我们自己电脑的本地仓库了,Mac的地址在
/用户/用户名/.m2 目录下,如图
在这里插入图片描述
至此,就大功告成了,只需要在我们的工程目录下 repositories 中添加 mavenLocal()
dependencies 中添加 classpath ‘com.derek:tingyun:1.0.0’ 即可
具体代码如下

buildscript {
    repositories {
       .....
        mavenLocal()
        }
    }

    dependencies {
        .......//忽略的代码
        classpath 'com.derek:tingyun:1.0.0}
}

在app的build gradle中引入即可,如图
在这里插入图片描述
至此,我们再gradle任务栏就可以看到我们的任务了,可以根据需要,来创建不同的properties文件了
在这里插入图片描述

Unable to load class 'com.xxxx.plugin

在这里插入图片描述
遇到这个问题一开始也很蒙,以为是网络问题或者是AS问题,但是本地仓库那里有网络问题啊,一度怀疑AS ,重启无效。
进入/用户/用户名/.m2 目录下查看.jar 文件 只有600多字节,解压缩一看,里面没有class文件,怪不得引用不到。
如果你也遇到这个问题,你需要查看一下自己的task任务或者plugin插件,是不是groovy文件,查看方式就是 右击你的groovy文件,选择Refactor->renameFile.看看是不是以groovy结尾的
在这里插入图片描述
在这里插入图片描述
如果是的话就没问题,为什么这么说,我就是因为有一个groovy文件不知道是bug还是什么原因,没有.groovy结尾,同时你要是手动添加的话,还报错,所以如果你有这个问题的话,可以这么排查一下,解决方法就是复制代码,然后删掉源文件,新建新的groovy文件

当处理完这些,你就可以再gradle任务栏执行一下build任务
在这里插入图片描述
如果在build文件夹下看到对应的编译文件,就说明没问题了。打包重新上传即可
在这里插入图片描述
另外还有一点就是要注意的是,groovy不会自动给你写包名,这个也会导致.class文件编译不出来,这个也是要注意的。

记录一下。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值