早期写过一些 gradle task,了解过插件开发,现在项目中有需要一个复用的 task 原本在项目的 gradle 文件中,最近由于配置变化,需要修改,考虑处理成一个插件,方便各项目使用。
本文包含一下两部分,内容主要来自官方文档
一定要阅读官方文档,以下内容仅仅是个人使用中的一个记录,仅作参考。
1. 插件开发
对于 gradle 插件开发基本会涉及到三个步骤: Build script -> buildSrc project -> Standalone project,本文主要介绍最后一项。
1.1 插件开发背景
原有项目 apk 生成之后,需要在远程签名,然后拷贝回来,之前这一部分业务打包成一个 jar,然后在 build.gradle 中定义了一个 task,调用 jar 中对应方法,jar 中需要的配置项和 task 中获取和校验参数的逻辑最近发生了变化,需要修改代码,于是考虑直接做成 gradle plugin。
1.2 插件开发
gradle 插件开发个人理解是有三部分内容,
- 入口
- 配置
- 业务逻辑
这个三部分在插件开发中对应了 Plugin,Extension,Task 三部分。
Plugin 入口
插件类:
public class DPlugin implements Plugin<Project> {
@Override
public void apply(final Project project) {
project.getExtensions().create("dconfig", DExtension.class);
project.getTasks().create("dcustom", DTask.class, new Action<DTask>() {
@Override
public void execute(DTask d) {
d.mProject = project;
}
});
}
}
Extension 配置类
配置类:
public class DExtension {
String username;
String password;
String filepath;
}
Task 业务类
Task 类:
public class DTask extends DefaultTask {
String username;
String password;
String filepath;
public Project mProject;
@TaskAction
public void action() throws IOException, DException {
copyValueFromExtension();
// 业务处理
}
private void copyValueFromExtension() {
DExtension dconfig = (DExtension) mProject.getExtensions().getByName("dconfig");
// copy porperties from DExtension to DTask
}
}
2. 插件发布
插件开发之后,需要发布到远程,项目中使用的时候就可以方便的配置使用了,以下是 artifactory 发布示例:
2.1 配置 maven
lib_java.gradle
apply plugin: 'maven-publish'
publishing {
publications {
// 此处定义的 archive 在之后会用到
archive(MavenPublication) {
// 配置 groupId,版本,artifactId,和生成的 jar 路径
groupId "${artifactory_group_id}"
version = "${verName}"
artifactId project.getName()
artifact "build/libs/${project.name}.jar"
// 生成 pom 文件
pom.withXml {
def dependenciesNode = asNode().appendNode('dependencies')
configurations.compile.allDependencies.each {
def dependencyNode = dependenciesNode.appendNode('dependency')
dependencyNode.appendNode('groupId', it.group)
dependencyNode.appendNode('artifactId', it.name)
dependencyNode.appendNode('version', it.version)
}
configurations.implementation.allDependencies.each {
if (it.name != "unspecified") {
def dependencyNode = dependenciesNode.appendNode('dependency')
dependencyNode.appendNode('groupId', it.group)
dependencyNode.appendNode('artifactId', it.name)
dependencyNode.appendNode('version', it.version)
}
}
}
}
}
}
2.2 配置 artifactory
artifactory.gradle
buildscript {
repositories {
jcenter()
}
dependencies {
classpath "org.jfrog.buildinfo:build-info-extractor-gradle:latest.release"
}
}
apply plugin: 'com.jfrog.artifactory'
artifactory {
// 配置 artifactory 地址
contextUrl = "${artifactory_contextUrl}"
publish {
repository {
// 配置 artifactory 参数
repoKey = "${artifactory_repoKey}"
username = "${artifactory_user}"
password = "${artifactory_password}"
maven = true
}
defaults {
// 配置发布信息
publishArtifacts = true
publications('archive') // lib_java.gradle 中定义的 archive
publishPom = true
publishIvy = false
}
}
resolve {
repository {
repoKey = "${artifactory_repoKey}"
username = "${artifactory_user}"
password = "${artifactory_password}"
}
}
}
2.3 插件发布
./gradlew :d:assemble
./gradlew :d:artifactPublish
2.4 插件引用
在项目中新建 d.gradle
文件:
buildscript {
repositories {
maven {
url "${artifactory_contextUrl}"
credentials {
username artifactory_user
password artifactory_password
}
}
maven {
url 'https://dl.google.com/dl/android/maven2/'
}
google()
jcenter()
}
dependencies {
classpath 'your.plugin.groupid:artifactId:version'
}
}
apply plugin: pkg.DPlugin
dconfig {
user = project.user
password = project.password
}
在项目的 build.gradle 中增加以下代码:
apply from:"d.gradle"
将插件的配置和信息写在独立文件中是为了保证项目的 build.gradle
文件内容更简单
注意事项:
d.gradle
中不能使用插件的 id(稍后介绍)buildscript.repositories
中需要添加插件中依赖库的地址。
2.5 使用 id 引用插件
使用第三方插件时不需要使用 Plugin
完整名称,原因在于 gradle 会去查找 jar 文件中 META-INF/gradle-plugins
目录下和 id 对应的插件。
关于 id 的官方文档 Creating a plugin id