groovy 如何在build.gradle中定义和调用自定义方法?

yhuiod9q  于 2022-12-26  发布在  其他
关注(0)|答案(8)|浏览(206)

作为项目的一部分,我需要从目录读取文件并执行一些操作所有这些操作都在构建脚本中执行。对于每个文件,操作都是相同的(阅读一些SQL查询并执行)。我认为这是一项重复性任务,最好在方法内部编写。由于我是Gradle新手,我不知道应该如何编写。

kdfy810k

kdfy810k1#

一种方法如下:

ext.myMethod = { param1, param2 ->
    // Method body here
}

请注意,这是为项目范围创建的,即项目全局可用,可以使用myMethod(p1, p2)(等效于project.myMethod(p1, p2))在构建脚本中的任何位置调用,如下所示
该方法也可以在不同的作用域下定义,例如在任务中:

task myTask {
    ext.myMethod = { param1, param2 ->
        // Method body here
    }

    doLast {
        myMethod(p1, p2) // This will resolve 'myMethod' defined in task
    }
}
gwo2fgha

gwo2fgha2#

如果您在任何其他文件 *.gradle中定义了任何方法,则ext.method()可使其在整个项目范围内可访问。
versioning.gradle

// ext makes method callable project wide
ext.getVersionName = { ->
    try {
        def branchout = new ByteArrayOutputStream()
        exec {
            commandLine 'git', 'rev-parse', '--abbrev-ref', 'HEAD'
            standardOutput = branchout
        }
        def branch = branchout.toString().trim()

        if (branch.equals("master")) {
            def stdout = new ByteArrayOutputStream()
            exec {
                commandLine 'git', 'describe', '--tags'
                standardOutput = stdout
            }
            return stdout.toString().trim()
        } else {
            return branch;
        }
    }
    catch (ignored) {
        return null;
    }
}

build.gradle

task showVersion << {
    // Use inherited method
    println 'VersionName: ' + getVersionName()
}

如果没有ext.method()格式,该方法将仅在声明它的 *.gradle文件中可用。这与属性相同。

smtd7mpg

smtd7mpg3#

可以按以下方式定义方法:

// Define an extra property
ext.srcDirName = 'src/java'

// Define a method
def getSrcDir(project) {
    return project.file(srcDirName)
}

您可以在gradle文档Chapter 62. Organizing Build Logic中找到更多详细信息

bogh5gae

bogh5gae4#

包含方法的根对象的示例。
hg.gradle文件:

ext.hg = [

    cloneOrPull: { source, dest, branch ->
        if (!dest.isDirectory())
            hg.clone(source, dest, branch)
        else
            hg.pull(dest)
        hg.update(dest, branch)
    },

    clone: { source, dest, branch ->
        dest.mkdirs()
        exec {
            commandLine 'hg', 'clone', '--noupdate', source, dest.absolutePath
        }
    },

    pull: { dest ->
        exec {
            workingDir dest.absolutePath
            commandLine 'hg', 'pull'
        }
    },

]

构建.gradle文件

apply from: 'hg.gradle'

hg.clone('path/to/repo')
798qvoo8

798qvoo85#

不知何故,也许是因为它的五年以来的行动,但没有一个

ext.someMethod = { foo ->
   methodBody
}

相反,一个简单的函数定义似乎就能在我的gradle文件中完成这项工作:

def retrieveEnvvar(String envvar_name) {
    if ( System.getenv(envvar_name) == "" ) {
        throw new InvalidUserDataException("\n\n\nPlease specify environment variable ${envvar_name}\n")
    } else {
        return System.getenv(envvar_name)
    }       
}

我在脚本的其他地方不带前缀地调用它,例如retrieveEnvvar("APP_PASSWORD")
现在是2020年,所以我使用的是Gradle 6.1.1。

vxbzzdmp

vxbzzdmp6#

@ether_joe上面的@InvisibleArrow投票最多的答案 * 确实 * 有效,但是您必须在调用它 * 之前 * 定义您调用的方法-即在build.gradle文件的前面。
您可以看到一个here示例。我在Gradle 6.5中使用过这种方法,效果很好。

ukqbszuj

ukqbszuj7#

通过Kotlin DSL(build.gradle.kts),您可以定义并使用常规函数。
函数是在调用点之前还是之后定义并不重要。

println(generateString())

fun generateString(): String {
    return "Black Forest"
}

tasks.create("MyTask") {
    println(generateString())
}

如果要从其他脚本导入和使用函数,请参见this answerthis answer

kgsdhlau

kgsdhlau8#

在我的react-native in build.gradle中

def func_abc(y){return "abc"+y;}

那么

def x = func_abc("y");

如果要检查:

throw new GradleException("x="+x);

println "x="+x;

相关问题