Android Gradle 开发与应用 (五) : 基于Gradle 8.2,创建Gradle插件
1. 前言
本文介绍在Android中,如何基于Gradle 8.2,创建Gradle插件。
1.1 本文环境
Android Studio版本 :Android Studio Hedgehog | 2023.1.1Gralde版本 :gradle 8.2
使用 Android Gradle 插件升级助理
Android Gradle 插件版本说明
1.2 为什么要写插件
可以将相关代码抽取出来,而不是耦合在build.gradle中,成为通用性的插件,可以在多个项目中复用。
比如com.android.application就是我们最为熟悉的Android插件。
plugins {id 'com.android.application'
}
2. 创建插件
2.1 新建项目
新建MyGradlePluginTest项目,这里选择Groovy DSL。

2.2 新建Gradle插件Module
这里选择Java or Kotlin Library,也可以选择Android Library

2.3 修改build.gradle
plugins {id 'java-gradle-plugin'
}gradlePlugin {plugins {//MyTestPlugin { //这种方式也行create("MyTestPlugin") {//插件idid = 'com.heiko.myplugin'//插件的包名+类名implementationClass = 'com.heiko.myplugin.MyPlugin'}}
}
2.4 新建插件类
对应implementationClass中的路径,新建插件类 MyPlugin
package com.heiko.myplugin;import org.gradle.api.Plugin;
import org.gradle.api.Project;class MyPlugin implements Plugin<Project> {@Overridepublic void apply(Project project) {System.out.println("这是我的第一个插件!");}
}
3. 发布插件
3.1 依赖maven-publish
在build.gradle中,添加maven-publish插件,然后配置发布插件的信息和仓库信息。
这里的maven仓库配置的是本地的,仅用作演示。实际项目中,应该使用真实的maven仓库服务器更合理些。
关于maven仓库更多的操作,详见我的另一篇文章 : Android Module上传到Maven仓库 及 实现同时上传到多个Maven仓库
plugins {//...省略了代码...id 'maven-publish'
}//...省略了代码...println("原本的version:" + version)
println("原本的group:" + group)//设置group
group = 'com.heiko.group'
//设置版本号
version = "1.0.0"println("设置后的group:" + group)
println("设置后的version:" + version)afterEvaluate {/*这部分代码不需要配置,会根据gradlePlugin中的进行生成除非使用老版本的插件依赖方式(classpath):需要指定artifactId的情况下,才需要使用publications {maven(MavenPublication) {groupId = groupartifactId = 'MyPlugin'version = versionfrom components.java}}*/publishing {// 配置仓库地址repositories {maven {url = uri('../repo')}}}
}
build.gradle的完整代码如下
plugins {id 'java-gradle-plugin'id 'maven-publish'
}gradlePlugin {plugins {//MyTestPlugin { //这种方式也行create("MyTestPlugin") {//插件idid = 'com.heiko.plugin.myplugin'//插件的包名+类名implementationClass = 'com.heiko.myplugin.MyPlugin'}}
}println("原本的version:" + version)
println("原本的group:" + group)//设置group
group = 'com.heiko.group'
//设置版本号
version = "1.0.0"println("设置后的group:" + group)
println("设置后的version:" + version)afterEvaluate {/*这部分代码不需要配置,会根据gradlePlugin中的进行生成除非使用老版本的插件依赖方式(classpath):需要指定artifactId的情况下,才需要使用publications {maven(MavenPublication) {groupId = groupartifactId = 'MyPlugin'version = versionfrom components.java}}*/publishing {// 配置仓库地址repositories {maven {url = uri('../repo')}}}
}
发布插件
这个时候,点击下Sync同步下代码,然后可以在右侧Gradle的Tab中,找到publishing,里面有publish选项,我们双击它,就开始执行发布插件的操作了。

上传插件成功后,可以看到如下信息

4. 使用插件
4.1 添加Maven仓库
pluginManagement {repositories {//省略了其他仓库...maven {url 'repo'}}
}
4.2 依赖插件
在更目录下的build.gradle中,依赖插件
plugins {id 'com.android.application' version '8.2.0' apply false//省略了其他插件代码id 'com.heiko.plugin.myplugin' version '1.0.0' apply false
}
通常默认配置会 立马 解析(resolve) 并 应用(apply) 插件。
而 apply 设为 false, 表示 不应用插件到 根项目。目的是 提前解析 插件,保持一样的版本。
4.3 应用插件
在app目录下的build.gradle中,应用插件
plugins {id 'com.android.application'id 'org.jetbrains.kotlin.android'//应用插件id 'com.heiko.plugin.myplugin'
}
4.4 同步项目
点击Sync同步下项目,可以看到我们的插件打印的日志了

5. 使用Groovy编写插件
上文中我们是使用java语言来编写的插件,那么如果使用Groovy语言来编写插件,需要怎么操作呢 ?
5.1 添加groovy插件
为了识别groovy语言,我们需要在MyPlugin目录下的build.gradle中添加groovy插件
plugins {id 'java-gradle-plugin'//添加groovy插件id 'groovy'id 'maven-publish'
}
5.2 新建groovy目录
在和java同级别的目录下,新建groovy目录,groovy目录下需要和原java目录一样

5.3 新建MyPluginGroovy.groovy
在groovy目录下,要把MyPlugin.java改为MyPlugin.groovy ,这里我为了方便区分,把名称改为了MyPluginGroovy.groovy 。
package com.heiko.myplugin;import org.gradle.api.Plugin;
import org.gradle.api.Project;class MyPluginGroovy implements Plugin<Project> {@Overridepublic void apply(Project project) {println "这是我的第一个Groovy插件!"}
}
5.4 修改implementationClass
修改MyPlugin目录下的build.gradle文件中的implementationClass ,修改为groovy目录下对应的插件类的包名+类名,注意没有文件后缀。
implementationClass = 'com.heiko.myplugin.MyPluginGroovy'
完整的build.gradle文件
plugins {id 'java-gradle-plugin'id 'groovy'id 'maven-publish'
}gradlePlugin {plugins {create("MyTestPlugin") {//插件idid = 'com.heiko.plugin.myplugin'//插件的包名+类名implementationClass = 'com.heiko.myplugin.MyPluginGroovy'}}
}//设置group
group = 'com.heiko.group'
//设置版本号
version = "1.0.1"afterEvaluate {publishing {// 配置仓库地址repositories {maven {url = uri('../repo')}}}
}
5.5 重新发布插件
将版本号version改为1.0.1,双击publish,重新发布插件
5.6 依赖插件
修改项目根目录下的build.gradle,将我们的com.heiko.plugin.myplugin插件版本号修改为1.0.1。
重新运行项目,可以看到打印的插件日志变成了
这是我的第一个Groovy插件!
6. 使用Kotlin编写插件
除了使用Java或Groovy编写插件,我们还可以使用Kotlin来编写插件,使用kotlin对于Android开发者来说会更友好。
6.1 添加java插件
为了识别kotlin语言,我们需要在MyPlugin目录下的build.gradle中添加kotlin插件
plugins {id 'java-gradle-plugin'//添加Kotlin插件id "org.jetbrains.kotlin.jvm"id 'maven-publish'
}
6.2 新建kotlin目录
在和java同级别的目录下,新建kotlin目录,kotlin目录下需要和原java目录一样

6.3 新建MyPluginKotlin.kt
在kotlin目录下,要把MyPlugin.java改为MyPlugin.kt ,这里我为了方便区分,把名称改为了MyPluginKotlin.groovy 。
package com.heiko.mypluginimport org.gradle.api.Plugin
import org.gradle.api.Projectclass MyPluginKotlin : Plugin<Project> {override fun apply(project: Project) {println("这是我的第一个Kotlin插件!")}
}
6.4 修改implementationClass
修改MyPlugin目录下的build.gradle文件中的implementationClass ,修改为groovy目录下对应的插件类的包名+类名,注意没有文件后缀。
implementationClass = 'com.heiko.myplugin.MyPluginKotlin'
完整的build.gradle文件
plugins {id 'java-gradle-plugin'id "org.jetbrains.kotlin.jvm"id 'maven-publish'
}gradlePlugin {plugins {create("MyTestPlugin") {//插件idid = 'com.heiko.plugin.myplugin'//插件的包名+类名implementationClass = 'com.heiko.myplugin.MyPluginKotlin'}}
}//设置group
group = 'com.heiko.group'
//设置版本号
version = "1.0.2"afterEvaluate {publishing {// 配置仓库地址repositories {maven {url = uri('../repo')}}}
}
6.5 重新发布插件
将版本号version改为1.0.2,双击publish,重新发布插件
6.6 依赖插件
修改项目根目录下的build.gradle,将我们的com.heiko.plugin.myplugin插件版本号修改为1.0.2。
重新运行项目,可以看到打印的插件日志变成了
这是我的第一个Kotlin插件!
7. Android Gradle系列文章
Android Gradle 开发与应用 (一) : Gradle基础-氦客-CSDN博客
Android Gradle开发与应用 (二) : Groovy基础语法-CSDN博客
Android Gradle开发与应用 (三) : Groovy语法概念与闭包-CSDN博客
Android Gradle开发与应用 (四) : Gradle构建与生命周期-CSDN博客
Android Gradle开发与应用 (五): 基于Gradle 8.2,创建Gradle插件-CSDN博客
Android Gradle 开发与应用 (六) : 创建buildSrc插件和使用命令行创建Gradle插件-CSDN博客
8. 参考文章
Using Plugins (gradle.org)
Gradle用户手册 - Gradle8.1.1中文文档 - API参考文档 - 全栈行动派 (qzxdp.cn)
编写 Gradle 插件 | Android Studio | Android Developers (google.cn)
Android Gradle8.0版本新建Gradle插件 - 掘金 (juejin.cn)
Gradle基础到进阶 - yechaoa的专栏 - 掘金 (juejin.cn)
【Gradle-8】Gradle插件开发指南 - 掘金 (juejin.cn)
【Gradle-9】Gradle插件发布指南 - 掘金 (juejin.cn)
Gradle自定义插件实践与总结 - 掘金 (juejin.cn)
创建Gradle插件记录 - 掘金 (juejin.cn)
相关文章:
Android Gradle 开发与应用 (五) : 基于Gradle 8.2,创建Gradle插件
1. 前言 本文介绍在Android中,如何基于Gradle 8.2,创建Gradle插件。 1.1 本文环境 Android Studio 版本 : Android Studio Hedgehog | 2023.1.1Gralde版本 : gradle 8.2 使用 Android Gradle 插件升级助理 Android Gradle 插件版本说明 1.2 为什么要写…...
中文在职博士|中国社科院-新加坡社科大学(公立大学)工商管理博士
中文在职博士|中国社科院-新加坡社科大学(公立大学)工商管理博士 中国社科大-新加坡社科大学合作举办全球战略领导力博士项目 【条件】:硕士学位+三年管理经验 【证书】:颁发新加坡社科大学博士学位证书 【招生】&…...
前端性能优化终极指南
前端性能优化一直是很多同学非常关注的问题,在日常的面试中也是经常会被用到的点。今天就来了解一下前端性能优化方案。 一:页面渲染相关 01:减少页面重绘和回流 回流(reflow):是指由于DOM结构或样式发生…...
基于Logstash由SQLServer向Elasticsearch同步数据: logstash配置文件
文章目录 I Logstash1.1 Logstash 安装1.2 logstash配置文件参数含义1.3 启动LogstashII 增量数据同步方案2.1 思路2.2 使用LastModifyTime来追踪DB的变更数据2.3 将最大ID 设置为查询条件,获取增量数据2.4 把时间戳设置为记录产生的时间III 单表同步IV 多表同步V 使用 Logsta…...
sqllab第八关通关笔记
知识点: 这里感觉是一个单纯的单引号绕过bp爆破配置的条件和第七关一样 首先判断注入类型 构造id1/0 回显成功 构造id1 错误回显,感觉又是一个单引号绕过 构造id1 正常回显了,说明不错,就是一个单引号绕过 构造payload:id1 a…...
unity text 文本符号显示问题与打字机效果的结合
问题1:unity text显示文本时,符号可能显示在某行的开头的位置 问题2:打字机效果没有适配问题1的脚本 解决方法: 问题1:通过遍历text组件每一行数据(第二行开始),如果是符号,就在它之前的字符前…...
Netty架构详解
文章目录 概述整体结构Netty的核心组件逻辑架构BootStrap & ServerBootStrapChannelPipelineFuture、回调和 ChannelHandler选择器、事件和 EventLoopChannelHandler的各种ChannelInitializer类图 Protocol Support 协议支持层Transport Service 传输服务层Core 核心层模块…...
Unity自带的WebSocket使用说明
Unity中的WebSocket是一种用于实时性强、低延迟的双向通信的技术。它可以在客户端和服务器之间建立一个持久的连接,允许双方随时互相发送数据。这种实时性使得WebSocket在游戏中非常有用,特别是对于多人在线游戏和实时竞技游戏。 在Unity中,…...
【Web】浅聊XStream反序列化之SortedSetTreeMap利用链
前文:【Web】浅聊XStream反序列化本源之恶意动态代理注入-CSDN博客 前言 在上一篇文章我们聊到可以用XStream反序列化来进行恶意动态代理的注入,但其有一个很大的限制就是必须要知道目标靶机会调用哪个接口的方法,才能去相应地精心构造对应…...
HTML CSS学习
# html css 日常学习记录---学习途径--渡一教育-袁老师# 元素包含关系 以前:块级元素可以包含行级元素,行级元素不可以包含块级元素,a元素除外 元素的包含关系由元素的内容类别决定。 例如,查看h1元素中是否可以包含p元素 总…...
MySQL的事务隔离是如何实现的?
目录 从一个例子说起 快照读和当前读 事务的启动时机和读视图生成的时刻 MVCC 隐藏字段 Undo Log回滚日志 Read View - 读视图 可重复读(RC)隔离级别下的MVCC 读提交(RR)隔离级别下的MCC 关于MVCC的一些疑问 1.为什么需要 MVCC ?如果没有 MVCC 会怎样&am…...
STM32电源及时钟介绍
一、STM32最小系统 二、电源电路 2.1供电电压VDD,VSS F103VET6 的引角图 在 F103VET6 的引角图中可找到 49\50 角, 74\75 角, 99\100 角, 27\28角,10 \11角一共 5 对的VDD,VSS,也就是给我们芯片…...
使用公式在Excel中指定列值的变化实现自动间隔着色(不是按照固定的行数)
如果你的文件很小,可以手工着色;但如果很大,就要借助公式来着色; 目的是什么,其中之一是:提升可读性。 一起往下看吧!! 如果你想要根据Excel某列中值的变化来间隔着色,…...
蚓链给传统供应链的数字化解决方案会带来什么价值呢?
传统供应链在蚓链数字化的加持下,通过互相融合、结合将为数字经济带来多方面的影响和变革,包括但不限于以下几点: 1. 提高效率和降低成本:数字化可以优化供应链中的各个环节,例如采购、生产、物流和销售等࿰…...
有来团队后台项目-解析8
UnoCss 介绍 UnoCss 官网UnoCss 官网 安装 pnpm add -D unocss引入 vite.config.ts import UnoCSS from unocss/vite // plugins 中引入 UnoCSS({/* options */ }),创建uno.config.ts // uno.config.ts import {defineConfig,presetAttributify,presetIcons,presetTyp…...
vs2022的下载及安装教程(Visual Studio 2022)
vs简介 Visual Studio在团队项目开发中使用非常多且功能强大,支持开发人员编写跨平台的应用程序;Microsoft Visual C 2022正式版(VC2022运行库),具有程序框架自动生成,灵活方便的类管理,强大的代码编写等功能,可提供编…...
BFS(宽度优先搜索)C++(Acwing)
代码: #include <cstring> #include <iostream> #include <algorithm>using namespace std;typedef pair<int, int> PII;const int N 110;int n, m; int g[N][N]; int d[N][N]; PII q[N * N];int bfs() {int hh 0, tt 0;q[0] {0, 0};m…...
信息收集:端口扫描原理,端口扫描分类,端口扫描工具,手动判断操作系统,操作系统识别工具
「作者主页」:士别三日wyx 「作者简介」:CSDN top100、阿里云博客专家、华为云享专家、网络安全领域优质创作者 「专栏简介」:此文章已录入专栏《网络安全自学教程》 端口&系统版本 一、端口扫描1、telnet2、Nmap3、Masscan4、端口扫描原…...
【Tauri】(5):本地运行candle和 qwen 大模型,并测试速度
1,本地运行candle 关于candle项目 https://github.com/huggingface/candle Hugging Face 使用rust开发的高性能推理框架。 语法简单, 风格与 PyTorch 相似。 CPU 和 Cuda Backend:m1、f16、bf16。 支持 Serverless(CPUÿ…...
基于udp协议的cs网络通信代码(echo版+命令行输入版+执行指令版),netstat指令
目录 引入 基础版 服务端 思路 头文件log类 套接字的初始化 思路 代码 服务器开始运行 思路 代码 注意点 -- ip地址和端口号的来源 ip地址的选择 本地环回地址 端口号 编辑 运行情况 netstat -nlup 客户端 思路 初始化 思路 代码 客户端的运行 思…...
系统设计 --- MongoDB亿级数据查询优化策略
系统设计 --- MongoDB亿级数据查询分表策略 背景Solution --- 分表 背景 使用audit log实现Audi Trail功能 Audit Trail范围: 六个月数据量: 每秒5-7条audi log,共计7千万 – 1亿条数据需要实现全文检索按照时间倒序因为license问题,不能使用ELK只能使用…...
spring:实例工厂方法获取bean
spring处理使用静态工厂方法获取bean实例,也可以通过实例工厂方法获取bean实例。 实例工厂方法步骤如下: 定义实例工厂类(Java代码),定义实例工厂(xml),定义调用实例工厂ÿ…...
MySQL账号权限管理指南:安全创建账户与精细授权技巧
在MySQL数据库管理中,合理创建用户账号并分配精确权限是保障数据安全的核心环节。直接使用root账号进行所有操作不仅危险且难以审计操作行为。今天我们来全面解析MySQL账号创建与权限分配的专业方法。 一、为何需要创建独立账号? 最小权限原则…...
A2A JS SDK 完整教程:快速入门指南
目录 什么是 A2A JS SDK?A2A JS 安装与设置A2A JS 核心概念创建你的第一个 A2A JS 代理A2A JS 服务端开发A2A JS 客户端使用A2A JS 高级特性A2A JS 最佳实践A2A JS 故障排除 什么是 A2A JS SDK? A2A JS SDK 是一个专为 JavaScript/TypeScript 开发者设计的强大库ÿ…...
人工智能(大型语言模型 LLMs)对不同学科的影响以及由此产生的新学习方式
今天是关于AI如何在教学中增强学生的学习体验,我把重要信息标红了。人文学科的价值被低估了 ⬇️ 转型与必要性 人工智能正在深刻地改变教育,这并非炒作,而是已经发生的巨大变革。教育机构和教育者不能忽视它,试图简单地禁止学生使…...
STM32HAL库USART源代码解析及应用
STM32HAL库USART源代码解析 前言STM32CubeIDE配置串口USART和UART的选择使用模式参数设置GPIO配置DMA配置中断配置硬件流控制使能生成代码解析和使用方法串口初始化__UART_HandleTypeDef结构体浅析HAL库代码实际使用方法使用轮询方式发送使用轮询方式接收使用中断方式发送使用中…...
NPOI操作EXCEL文件 ——CAD C# 二次开发
缺点:dll.版本容易加载错误。CAD加载插件时,没有加载所有类库。插件运行过程中用到某个类库,会从CAD的安装目录找,找不到就报错了。 【方案2】让CAD在加载过程中把类库加载到内存 【方案3】是发现缺少了哪个库,就用插件程序加载进…...
python爬虫——气象数据爬取
一、导入库与全局配置 python 运行 import json import datetime import time import requests from sqlalchemy import create_engine import csv import pandas as pd作用: 引入数据解析、网络请求、时间处理、数据库操作等所需库。requests:发送 …...
【前端异常】JavaScript错误处理:分析 Uncaught (in promise) error
在前端开发中,JavaScript 异常是不可避免的。随着现代前端应用越来越多地使用异步操作(如 Promise、async/await 等),开发者常常会遇到 Uncaught (in promise) error 错误。这个错误是由于未正确处理 Promise 的拒绝(r…...
Unity VR/MR开发-VR开发与传统3D开发的差异
视频讲解链接:【XR马斯维】VR/MR开发与传统3D开发的差异【UnityVR/MR开发教程--入门】_哔哩哔哩_bilibili...
