如何创建基于Gradle扩展值动态添加依赖或插件的自定义插件?
解决Gradle插件扩展属性读取报错问题
问题原因
你在插件的apply方法中直接调用basePluginExtension.useSpock.get()时,用户的basePluginConfig配置块还未执行。Gradle的执行顺序是先应用插件,再执行构建脚本里的配置代码,导致此时属性没有可用值,触发报错。
解决方案
核心是延迟读取扩展属性的时机,等到用户配置完成后再处理。最直接的方式是使用afterEvaluate回调:
修改插件代码如下:
interface BasePluginExtension { Property<Boolean> getUseSpock() } class BasePlugin implements Plugin<Project> { @Override void apply(Project project) { BasePluginExtension basePluginExtension = project.extensions.create('basePluginConfig', BasePluginExtension) // 延迟到所有项目配置完成后执行逻辑 project.afterEvaluate { // 读取属性,未配置时使用默认值true boolean useSpock = basePluginExtension.useSpock.getOrElse(true) if (useSpock) { println "I'm using spock! ${useSpock}" project.plugins.apply("test-config") } } } }
关键说明
afterEvaluate会在所有构建脚本的配置代码(包括你的basePluginConfig块)执行完成后触发,此时可以安全读取扩展属性的值。getOrElse(true)替代了原来的Elvis运算符,更符合Gradle属性API的使用规范,优雅处理用户未配置属性的场景。
扩展支持多参数
你使用接口定义扩展的方式完全可行,Gradle会自动生成实现类,后续可以轻松添加更多配置参数:
interface BasePluginExtension { Property<Boolean> getUseSpock() Property<String> getSpockVersion() Property<Boolean> getUseMockito() }
对应的用户配置块:
basePluginConfig { useSpock = true spockVersion = "2.3-groovy-4.0" useMockito = false }
Gradle完全支持基于扩展值动态添加依赖或插件,只要确保读取属性的时机在用户配置完成之后即可。
内容的提问来源于stack exchange,提问作者Rob Schwartz
相关产品推荐
相关产品推荐

