初见gradle plugin

gradle plugin的使用,分为三步:创建、注册、依赖

gradle官方文档:https://docs.gradle.org/current/javadoc/org/gradle/api/Project.html

本文案例:build项目时,下载指定文件保存到项目中

gralde官方文档:

自定义 Gradle 任务官方文档:https://docs.gradle.org/current/userguide/custom_tasks.html#custom_tasks

构建脚本基础:https://docs.gradle.org/current/userguide/tutorial_using_tasks.html#sec:using_ant_tasks_tutorial

1. 创建plugin

plugin的开发方式有三种
本文采取buildSrc module的方式
package com.test.plugin

import org.codehaus.groovy.runtime.IOGroovyMethods
import org.codehaus.groovy.runtime.ResourceGroovyMethods
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.kotlin.dsl.closureOf
import java.io.BufferedWriter
import java.io.File
import java.io.InputStream
import java.io.OutputStream
import java.net.URL

/**
 * 1. 创建Plugin
 * 2. 注册Plugin
 * 3. 依赖Plugin
 */
class MyPlugin : Plugin<Project> {

    override fun apply(project: Project) {
        project.logger.quiet("-------------------------------------")
        project.logger.quiet("---------- MyPlugin 执行 ------------${Thread.currentThread().name}")//子线程
        project.logger.quiet("-------------------------------------")

        val appFilePath = File(project.projectDir, "test.json")
        println("appFilePath = ${appFilePath.absolutePath}")//输出为工程的app目录
        if (appFilePath.exists()) {
            appFilePath.delete()
        }
        appFilePath.createNewFile()

        //downloadJson(appFilePath)
        fileDownload(appFilePath)
    }

    private fun downloadJson(filePath: File) {
        val url = "https://www.wanandroid.com/article/list/0/json"
        val json = ResourceGroovyMethods.getText(URL(url))
        println("url下载的字符长度 = ${json.length}")

        //将字符串写进文件中
        ResourceGroovyMethods.withWriter(filePath, closureOf<BufferedWriter> {
            this.write(json)
        })
    }


    /**
     * 下载数据 保存到 指定位置
     */
    private fun fileDownload(file: File) {
        val url = "https://www.wanandroid.com/article/list/0/json"
        ResourceGroovyMethods.withInputStream(URL(url), closureOf<InputStream> {
            val inputStream = this
            ResourceGroovyMethods.withOutputStream(file, closureOf<OutputStream> {
                val outputStream = this
                IOGroovyMethods.leftShift(outputStream, inputStream)
            })
        })
    }

}

2. 注册plugin

plugins {
    `kotlin-dsl`
}

//注册plugin
gradlePlugin {
    plugins {
        create("MyPluginName") {
            id = "com.plugin.MyPlugin" //apply饮用的id
            implementationClass = "com.test.plugin.MyPlugin"
        }
    }
}


repositories {
    google()
    mavenCentral()
}

dependencies {
    implementation(gradleApi())
    implementation(localGroovy())

}

3. 依赖plugin

在app的build.gradle文件中依赖:  apply plugin: 'com.plugin.MyPlugin'

4. 结果:

注意,别使用离线模式!当build项目后,就会自动下载文件到项目

 

5. 在gradle窗口中创建task的形式来完成下载

5.1 添加下载路径的配置,使得插件更加的完善

apply plugin: 'com.plugin.MyPlugin'

//app 的build.gradle文件中配置下载路径
downloadInfo {
    url "https://www.wanandroid.com/article/list/0/json"
}

5.2 解析配置数据,创建task

package com.test.plugin

/**
 * 解析配置数据的bean
 */
open class DownloadInfo{
    var url: String? = null
}
package com.test.plugin

import org.gradle.api.Plugin
import org.gradle.api.Project

class MyPlugin : Plugin<Project> {

    override fun apply(project: Project) {
        project.logger.quiet("-------------------------------------")
        project.logger.quiet("---------- MyPlugin 执行 ------------${Thread.currentThread().name}")
        project.logger.quiet("-------------------------------------")

        //准备获取这个配置信息
        val downloadInfo = project.extensions.create("downloadInfo", DownloadInfo::class.java)
        //在gradle分析完build.gradle文件后回调
        project.afterEvaluate {
            println("gradle解析完毕,url = ${downloadInfo.url}")
            //创建一个自己的任务名称
            project.tasks.create("MyDownload", MyDownloadTask::class.java, downloadInfo)
        }

    }
}

5.3 执行task

package com.test.plugin

import org.codehaus.groovy.runtime.ResourceGroovyMethods
import org.gradle.api.DefaultTask
import org.gradle.api.tasks.TaskAction
import org.gradle.kotlin.dsl.closureOf
import java.io.BufferedWriter
import java.io.File
import java.net.URL
import javax.inject.Inject

/**
 * created tangsheng
 * 2022/9/9
 */
open class MyDownloadTask : DefaultTask {

    private var downloadInfo: DownloadInfo

    /**
     * 注意需要在构造方法中加入Inject
     * 与创建Task相对应:
     * project.tasks.create("MyDownload", MyDownloadTask::class.java, downloadInfo)
     * 第三个参数开始为MyDownloadTask的构造方法参数,可匹配多个
     */
    @Inject
    constructor(downloadInfo: DownloadInfo) : super() {
        this.downloadInfo = downloadInfo
        group = "my download" //设置gradle窗口中所在的任务组
    }

    @TaskAction
    fun task() {
        println("执行 -- task() 方法了")
        val appFilePath = File(project.projectDir, "test.json")
        println("appFilePath = ${appFilePath.absolutePath}")//输出为工程的app目录
        if (appFilePath.exists()) {
            appFilePath.delete()
        }
        appFilePath.createNewFile()
        downloadJson(appFilePath)
    }

    private fun downloadJson(filePath: File) {
        val startTime = System.currentTimeMillis()
        val url = downloadInfo.url
        val json = ResourceGroovyMethods.getText(URL(url))
        println("url下载的字符长度 = ${json.length}, 耗时:${System.currentTimeMillis() - startTime}")

        //将字符串写进文件中
        ResourceGroovyMethods.withWriter(filePath, closureOf<BufferedWriter> {
            this.write(json)
        })
        println("下载结束, 耗时:${System.currentTimeMillis() - startTime}")
    }

}

创建完MyDawnload与点击后的效果如下: 

 

 

 

其他第三方插件:

使用插件自动完成360加固

https://www.bilibili.com/video/BV1yz4y1C73H?p=6&vd_source=295fc5f0dd7291f2ada701ab20185ff6 

 
posted @ 2022-09-09 16:44  ts-android  阅读(344)  评论(0)    收藏  举报