从自定义 gradle 插件获取 java 项目的资源路径
Getting the resource path of the java project from a custom gradle plugin
尝试在 java 中创建自定义 gradle 插件,我如何从任务 class 中获取资源路径?
public class MyCustomPlugin implements Plugin<Project> {
@Override
public void apply(Project project) {
project.getTasks().register("doStuff", CustomTask.class);
}
}
public class CustomTask extends DefaultTask {
// How do I get java project resources dir from here?
@Inject
public CustomTask(ProjectLayout projectLayout) {
directoryProperty = projectLayout.getBuildDirectory();
}
@TaskAction
public void execute() {
...
}
}
我建议不要获取任务中的目录,因为提供它的插件可能无法应用。相反,我会在注册任务的插件中执行此操作,这样您还可以确保实际应用了必要的插件。 Gradle 如果在没有为输入分配任何值的情况下使用任务,将显示错误,说明没有分配任何内容。
与kotlin-dsl
:
@CacheableTask
abstract class CustomTask : DefaultTask() {
@get:InputFiles
abstract val resources: FileCollection
//...
}
我无法回答 @InputFiles
是否适合您的用例,因为我不知道您想对资源做什么。有关可用注释及其作用的更多信息,请参阅 Gradle 文档。
plugins {
java
}
tasks.register<CustomTask>("customTask") {
resources.set(sourceSets.main.map { it.resources })
}
注意 map {}
确保我们的任务依赖于 processResources
任务,这是自动为我们完成的,因为我们坚持使用 [=34] 的提供者 API =] 一切。
请注意,资源默认位于一个目录中,但并非必须如此。这就是资源定义为 SourceDirectorySet
而不是 Provider<Directory>
的原因。对于源自 SourceSetContainer
的任何内容也是如此。用 Java 源代码更容易解释:假设你有 Java 和 Kotlin,那么你将有 src/main/java
和 src/main/kotlin
,因此有 2 个目录。前者将有一个 **/*.java
包含过滤器,而后者有一个 **/*.kt
包含过滤器。如果我们只想获取所有来源,那么我们使用 sourceSets.main.map { it.java.sourceDirectories }
,如果我们想要获取两者之一,那就变得复杂了。
您可以通过 project.sourceSets
访问资源。
@Inject
public CustomTask(Project project) {
directoryProperty = project.projectLayout.getBuildDirectory();
sourceSet = project.sourceSets.main
}
另请参阅此处的参考文档:https://docs.gradle.org/current/userguide/java_plugin.html#sec:java_project_layout
首先,您必须确保这是一个 Java 项目:从您的插件 (project.getPluginManager().apply("java")
) 应用 "java"
插件,或者仅在"java"
插件已被用户应用 (project.getPluginManager().withPlugin("java", ignored -> { project.getTasks().register(…); });
)。
然后您可以从主源集中获取资源:
SourceSetContainer sourceSets = project.getExtensions().getByType(SourceSetContainer.class);
// Use named() instead of get() if you prefer/need to use providers
SourceSet mainSourceSet = sourceSets.get(SourceSet.MAIN_SOURCE_SET_NAME);
SourceDirectorySet resources = mainSourceSet.getResources();
顺便说一句,最好的做法是让任务只声明它们的输入和输出(例如,我需要一组目录或文件作为输入,而我的输出将是一个文件或一个目录)并让 默认 值的实际接线由插件完成。
您可以让插件无条件地注册任务,然后在应用 "java"
插件时有条件地将其输入配置到项目资源;或有条件地注册任务或无条件地应用 "java"
插件,如上所示。
尝试在 java 中创建自定义 gradle 插件,我如何从任务 class 中获取资源路径?
public class MyCustomPlugin implements Plugin<Project> {
@Override
public void apply(Project project) {
project.getTasks().register("doStuff", CustomTask.class);
}
}
public class CustomTask extends DefaultTask {
// How do I get java project resources dir from here?
@Inject
public CustomTask(ProjectLayout projectLayout) {
directoryProperty = projectLayout.getBuildDirectory();
}
@TaskAction
public void execute() {
...
}
}
我建议不要获取任务中的目录,因为提供它的插件可能无法应用。相反,我会在注册任务的插件中执行此操作,这样您还可以确保实际应用了必要的插件。 Gradle 如果在没有为输入分配任何值的情况下使用任务,将显示错误,说明没有分配任何内容。
与kotlin-dsl
:
@CacheableTask
abstract class CustomTask : DefaultTask() {
@get:InputFiles
abstract val resources: FileCollection
//...
}
我无法回答 @InputFiles
是否适合您的用例,因为我不知道您想对资源做什么。有关可用注释及其作用的更多信息,请参阅 Gradle 文档。
plugins {
java
}
tasks.register<CustomTask>("customTask") {
resources.set(sourceSets.main.map { it.resources })
}
注意 map {}
确保我们的任务依赖于 processResources
任务,这是自动为我们完成的,因为我们坚持使用 [=34] 的提供者 API =] 一切。
请注意,资源默认位于一个目录中,但并非必须如此。这就是资源定义为 SourceDirectorySet
而不是 Provider<Directory>
的原因。对于源自 SourceSetContainer
的任何内容也是如此。用 Java 源代码更容易解释:假设你有 Java 和 Kotlin,那么你将有 src/main/java
和 src/main/kotlin
,因此有 2 个目录。前者将有一个 **/*.java
包含过滤器,而后者有一个 **/*.kt
包含过滤器。如果我们只想获取所有来源,那么我们使用 sourceSets.main.map { it.java.sourceDirectories }
,如果我们想要获取两者之一,那就变得复杂了。
您可以通过 project.sourceSets
访问资源。
@Inject
public CustomTask(Project project) {
directoryProperty = project.projectLayout.getBuildDirectory();
sourceSet = project.sourceSets.main
}
另请参阅此处的参考文档:https://docs.gradle.org/current/userguide/java_plugin.html#sec:java_project_layout
首先,您必须确保这是一个 Java 项目:从您的插件 (project.getPluginManager().apply("java")
) 应用 "java"
插件,或者仅在"java"
插件已被用户应用 (project.getPluginManager().withPlugin("java", ignored -> { project.getTasks().register(…); });
)。
然后您可以从主源集中获取资源:
SourceSetContainer sourceSets = project.getExtensions().getByType(SourceSetContainer.class);
// Use named() instead of get() if you prefer/need to use providers
SourceSet mainSourceSet = sourceSets.get(SourceSet.MAIN_SOURCE_SET_NAME);
SourceDirectorySet resources = mainSourceSet.getResources();
顺便说一句,最好的做法是让任务只声明它们的输入和输出(例如,我需要一组目录或文件作为输入,而我的输出将是一个文件或一个目录)并让 默认 值的实际接线由插件完成。
您可以让插件无条件地注册任务,然后在应用 "java"
插件时有条件地将其输入配置到项目资源;或有条件地注册任务或无条件地应用 "java"
插件,如上所示。