跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客我的书AI学习GitHub 精选镜像AI 生图工具UI配色美学关于
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
Javajava

Gradle 学习系列:如何自定义 Plugin

Gradle 插件开发支持三种常见实现方式,分别适用于不同场景。第一种是在 build.gradle 文件中直接定义类,适合快速验证但难以复用;第二种是将插件代码放入 buildSrc 目录,由 Gradle 自动编译构建,便于工程内共享;第三种是独立项目发布为 Maven 依赖,通过 buildscript 引入,适合跨项目分发。插件核心需实现 Plugin 接口并配置 Extension 属性,Task 创建与配置逻辑保持一致。掌握这些模式有助于灵活扩展 Gradle 构建能力。

人间失格发布于 2025/1/20更新于 2026/10/880 浏览
Gradle 学习系列:如何自定义 Plugin

上篇文章我们探讨了如何自定义 Task 类型,本文将深入讲解如何自定义 Plugin。

方式一:在 build.gradle 中直接定义

类似于在脚本中定义 Task,我们可以直接将 Plugin 的实现类写在 build.gradle 里。这种方式适合临时测试或简单场景,但不利于维护。

apply plugin: DateAndTimePlugin

dateAndTime {
    timeFormat = 'HH:mm:ss.SSS'
    dateFormat = 'MM/dd/yyyy'
}

class DateAndTimePlugin implements Plugin<Project> {
    void apply(Project project) {
        project.extensions.create("dateAndTime", DateAndTimePluginExtension)
        project.task('showTime') << {
            println "Current time is " + new Date().format(project.dateAndTime.timeFormat)
        }
        project.tasks.create('showDate') << {
            println "Current date is " + new Date().format(project.dateAndTime.dateFormat)
        }
    }
}

class DateAndTimePluginExtension {
    String timeFormat = "MM/dd/yyyyHH:mm:ss.SSS"
    String dateFormat = "yyyy-MM-dd"
}

每个自定义 Plugin 都需要实现 Plugin<T> 接口。除了针对 Project,我们也可以为其他 Gradle 对象编写插件。接口中的 apply() 方法是核心入口,在这里我们可以操作 Project,比如添加 Task 或定义扩展属性。

上面的例子向 Project 添加了两个 Task:showTime 和 showDate。注意这里使用了不同的 Task 创建方式,具体细节可参考相关文档。

每个 Gradle Project 都维护了一个 ExtensionContainer,通过 project.extensions 访问。我们在插件中定义了名为 dateAndTime 的扩展,包含 timeFormat 和 dateFormat 两个属性。使用时只需在配置块中覆盖默认值即可。

方式二:在当前工程中定义(buildSrc)

为了提升复用性,建议将插件代码提取到 buildSrc/src/main/groovy 目录下。这样 Gradle 会在执行任务前自动构建该目录。

首先创建 DateAndTimePlugin.groovy:

package davenkin

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

class DateAndTimePlugin implements Plugin<Project> {
    void apply(Project project) {
        project.extensions.create("dateAndTime", DateAndTimePluginExtension)
        project.task('showTime') << {
            println "Current time is " + new Date().format(project.dateAndTime.timeFormat)
        }
        project.tasks.create('showDate') << {
            println "Current date is " + new Date().format(project.dateAndTime.dateFormat)
        }
    }
}

再单独定义扩展类 DateAndTimePluginExtension.groovy:

package davenkin

class DateAndTimePluginExtension {
    String timeFormat = "MM/dd/yyyyHH:mm:ss.SSS"
    String dateFormat = "yyyy-MM-dd"
}

由于这两个类都在 davenkin 包下,应用插件时需要指定全限定名:

apply plugin: davenkin.DateAndTimePlugin dateAndTime { timeFormat = 'HH:mm:ss.SSS' dateFormat = 'MM/dd/yyyy' }

执行 gradle showTime 时,你会看到 Gradle 先构建 buildSrc,然后才执行任务。这种模式非常适合团队内部统一构建规范。

方式三:在独立项目中创建并发布

如果需要跨多个项目甚至跨公司使用插件,最好将其打包成独立的 Maven 仓库依赖。

新建一个项目,将上述 buildSrc 的内容拷贝过来,配置 build.gradle:

apply plugin: 'groovy'
apply plugin: 'maven'

version = '1.0'
group = 'davenkin'
archivesBaseName = 'datetimeplugin'

repositories.mavenCentral()

dependencies {
    compile gradleApi()
    compile localGroovy()
}

uploadArchives {
    repositories.mavenDeployer {
        repository(url: 'file:../lib')
    }
}

如果希望插件名称更简洁,可以在 src/main/resources/META-INF/gradle-plugins 下创建 time.properties,指定实现类:

implementation-class=davenkin.DateAndTimePlugin

执行上传后,插件会被打包成 jar 并推送到指定目录。在客户端项目中,通过 buildscript 引入依赖并应用插件:

buildscript {
    repositories {
        maven { url 'file:../lib' }
    }
    dependencies {
        classpath group: 'davenkin', name: 'datetimeplugin', version: '1.0'
    }
}

apply plugin: 'time'

dateAndTime {
    timeFormat = 'HH:mm:ss.SSS'
    dateFormat = 'MM/dd/yyyy'
}

这里的关键是先配置仓库路径,声明依赖,最后使用别名 time 来应用插件。至此,Gradle 插件开发的几种核心模式便介绍完毕。

目录

  1. 方式一:在 build.gradle 中直接定义
  2. 方式二:在当前工程中定义(buildSrc)
  3. 方式三:在独立项目中创建并发布

更多推荐文章

查看全部
  • AI 时代重读《人人都是产品经理》:核心内核与当代价值
  • Spring Cloud Gateway 核心机制与高性能原理实战
  • 基于 ArkUI 的鸿蒙五子棋游戏开发实战
  • Python Django 音乐推荐系统:协同过滤算法与 Echarts 可视化
  • C++ STL 容器适配器详解:Stack、Queue、Priority Queue 原理与实战
  • 中国人工智能大模型技术白皮书核心内容解读
  • Vheer:免费免登录 AI 绘画视频生成与智能编辑工具
  • AR 健身教练“形随心动”:基于 Rokid CXR-M SDK 的实践落地
  • 数据结构核心:栈
  • AIGC 浪潮下:R 语言在数据科学中的应用与实践
  • C++ 基于哈希表封装 unordered_map 与 unordered_set 模拟实现
  • Stable Diffusion 提示词编写指南:结构、权重与反向提示词
  • 基于 Chroma 和 Ollama 搭建本地 RAG 应用
  • OpenClaw 多端交互实战指南:Web 控制台、TUI 终端与钉钉集成
  • FastapiAdmin V2.0.0 现代开源全栈中后台快速开发平台
  • Python 爬虫入门指南:从基础到进阶的三个阶段
  • Python + AI 自动化生成每日工作汇报工具
  • 腾讯 RecSys'24:基于行为微调 LLM 初始化物品 Embedding 的高效推荐方法
  • 从零构建 gRPC 跨语言通信:C++ 服务端与 C# 客户端实战
  • 大厂面试流程解析与核心技术考点汇总

相关免费在线工具

  • Keycode 信息

    查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online

  • Escape 与 Native 编解码

    JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online

  • JavaScript / HTML 格式化

    使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online

  • JavaScript 压缩与混淆

    Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online

  • Base64 字符串编码/解码

    将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online

  • Base64 文件转换器

    将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online