gradle - 将编译器参数设置为新语言插件中的字符串列表

标签 gradle groovy gradle-plugin

我正在为一种新语言开发一个插件,我试图向编译器添加对编译选项的支持。我使用 org.gradle.api.tasks.compile.CompileOptions 类作为起点,并实现了我自己的类,如下所示:

class SvCompileOptions extends AbstractOptions {
    private List<String> compilerArgs = Lists.newArrayList();

    @Input
    public List<String> getCompilerArgs() {
        return compilerArgs;
    }

    public void setCompilerArgs(List<String> compilerArgs) {
        this.compilerArgs = compilerArgs;
    }
}

在我的 build.gradle 文件中,我尝试执行以下操作:

compileSv {
    options.compilerArgs += [ "-foo" ]
}

(compileSv 是一个具有 SvCompileOptions 类型的 options 属性的任务。)

我收到以下错误:

A problem occurred evaluating project ':uvc2'.
> java.lang.AbstractMethodError (no error message)

如果我将该行替换为:

compileSv {
    options.compilerArgs.add("-foo")
}

然后一切正常,但不是很渐变。

有人可以指出我做错了什么吗?


根据 @tim_yates 的建议,我添加了一个函数来附加到 compilerArgs:

class SvCompileOptions extends AbstractOptions {

    void compilerArgs(String... args) {
        this.compilerArgs.addAll(args as List)
    }
}

根据@Opal的建议,我创建了一个准系统示例:

// File 'build.gradle'

buildscript {
    dependencies {
        classpath 'com.google.guava:guava:16+'
    }
    repositories {
        mavenCentral()
    }
}

import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Lists;


class SvCompileOptions extends AbstractOptions {

    private List<String> compilerArgs = Lists.newArrayList();

    @Input
    public List<String> getCompilerArgs() {
        return compilerArgs;
    }

    public void setCompilerArgs(List<String> compilerArgs) {
        this.compilerArgs = compilerArgs;
    }

    void compilerArgs(String... args) {
        this.compilerArgs.addAll(args as List)
    }

}


class SvCompile extends DefaultTask {

    @TaskAction
    protected void compile() {
        println options.compilerArgs
    }

    @Nested
    SvCompileOptions options = new SvCompileOptions()

}


task compileSv(type: SvCompile)


compileSv {
    options.compilerArgs 'foo', 'bar'
}

代码将参数附加到空列表并按预期打印[foo, bar]。如果我们尝试使用以下内容覆盖参数:

compileSv {
    options.compilerArgs = ['one', 'two']
}

打印错误消息:

* What went wrong:
A problem occurred evaluating root project 'so_compile_options2'.
> SvCompileOptions.setProperty(Ljava/lang/String;Ljava/lang/Object;)V

我不确定为什么当类内联到 build.gradle 中时错误消息会有所不同,但我认为这就是导致 AbstractMethodError 的原因看到了。

正如 @Opal 指出的,这个问题是由 AbstractOptions 类中的一些魔法引起的。我尝试将以下方法添加到编译选项类中,但错误消息仍然存在:

class SvCompileOptions extends AbstractOptions {

    private static final ImmutableSet<String> EXCLUDE_FROM_ANT_PROPERTIES =
            ImmutableSet.of("compilerArgs");

    @Override
    protected boolean excludeFromAntProperties(String fieldName) {
        return EXCLUDE_FROM_ANT_PROPERTIES.contains(fieldName);
    }

    // ...
}

排除函数似乎根本没有被调用,就好像我在其中添加了一个虚拟打印一样,它永远不会被发出。

最佳答案

这应该有效

options.compilerArgs << "-foo"

如果您想添加多个值(您可能会在某些时候这样做),执行此操作的惯用方法是将您的类更改为:

class SvCompileOptions extends AbstractOptions {
    @Input
    List<String> compilerArgs = Lists.newArrayList();

    def args(String... args) {
        this.compilerArgs += args.toList()
    }
}

然后,你可以这样做:

compileSv {
    options.args "-foo", "-bar"
}

关于gradle - 将编译器参数设置为新语言插件中的字符串列表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49252911/

相关文章:

java - Groovy String 将引号添加到字符串的开头而不是末尾

java - 在 Intellij : unable to resolve class GroovyTestCase 下使用 Groovy 测试 Java 代码

java - 如何使用私有(private) Gitlab 存储库中的 Maven 组件?

Android gradle 将文件拉取到 Assets

android - Android同步失败-找不到com.google.android.gms:play-services-auth:15.1.0

java - 基于自定义 Gradle Java 的插件不起作用

gradle - 在自定义插件中评估了gradle.projects

android - Gradle 依赖项.. Kaltura Player 和 Google 分析不兼容 [Android]

maven - Groovy Maven 编译失败,错误为 : Unable to determine Groovy version. Groovy 是否声明为依赖项?

gradle - Gradle属性在扩展容器封闭中不可见