mirror of
https://github.com/tadfisher/gradle2nix.git
synced 2026-01-11 23:40:37 -05:00
Support downloading additional artifacts (sources, javadoc, etc.)
This commit is contained in:
@@ -1,20 +1,61 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
import org.gradle.api.Project
|
||||
import org.gradle.api.tasks.TaskAction
|
||||
import org.gradle.api.tasks.TaskProvider
|
||||
import org.nixos.gradle2nix.model.RESOLVE_PROJECT_TASK
|
||||
import org.gradle.api.artifacts.Configuration
|
||||
import org.gradle.api.artifacts.component.ModuleComponentIdentifier
|
||||
import org.gradle.api.attributes.Bundling
|
||||
import org.gradle.api.attributes.Category
|
||||
import org.gradle.api.attributes.DocsType
|
||||
import org.gradle.api.attributes.Usage
|
||||
import org.gradle.api.file.FileCollection
|
||||
import org.nixos.gradle2nix.model.ArtifactType
|
||||
|
||||
private fun Configuration.artifactConfigurationName(artifactType: ArtifactType): String =
|
||||
"$name-${artifactType.name.toLowerCase()}-artifacts"
|
||||
|
||||
object ResolveAllArtifactsApplierBase : AbstractResolveAllArtifactsApplier() {
|
||||
override fun Project.registerProjectTask(): TaskProvider<*> =
|
||||
tasks.register(RESOLVE_PROJECT_TASK, ResolveProjectDependenciesTaskBase::class.java)
|
||||
}
|
||||
@Suppress("UnstableApiUsage")
|
||||
override fun Project.addConfigurationArtifactResolver(
|
||||
configuration: Configuration,
|
||||
artifactType: ArtifactType,
|
||||
): FileCollection {
|
||||
val artifactConfiguration =
|
||||
configurations.register(configuration.artifactConfigurationName(artifactType)) { artifactConfig ->
|
||||
val usage = configuration.attributes.getAttribute(Usage.USAGE_ATTRIBUTE)
|
||||
artifactConfig.extendsFrom(configuration)
|
||||
artifactConfig.isCanBeConsumed = false
|
||||
artifactConfig.attributes { attrs ->
|
||||
with(attrs) {
|
||||
if (usage != null) {
|
||||
attribute(Usage.USAGE_ATTRIBUTE, usage)
|
||||
}
|
||||
attribute(Category.CATEGORY_ATTRIBUTE, objects.named(Category::class.java, Category.DOCUMENTATION))
|
||||
attribute(Bundling.BUNDLING_ATTRIBUTE, objects.named(Bundling::class.java, Bundling.EXTERNAL))
|
||||
attribute(
|
||||
DocsType.DOCS_TYPE_ATTRIBUTE,
|
||||
objects.named(
|
||||
DocsType::class.java,
|
||||
when (artifactType) {
|
||||
ArtifactType.DOXYGEN -> DocsType.DOXYGEN
|
||||
ArtifactType.JAVADOC -> DocsType.JAVADOC
|
||||
ArtifactType.SAMPLES -> DocsType.SAMPLES
|
||||
ArtifactType.SOURCES -> DocsType.SOURCES
|
||||
ArtifactType.USERMANUAL -> DocsType.USER_MANUAL
|
||||
},
|
||||
),
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
abstract class ResolveProjectDependenciesTaskBase : ResolveProjectDependenciesTask() {
|
||||
@TaskAction
|
||||
fun action() {
|
||||
for (configuration in getReportableConfigurations()) {
|
||||
configuration.artifactFiles().count()
|
||||
}
|
||||
return objects.fileCollection().from(
|
||||
artifactConfiguration.map { config ->
|
||||
config.incoming
|
||||
.artifactView { view ->
|
||||
view.isLenient = true
|
||||
view.componentFilter { it is ModuleComponentIdentifier }
|
||||
}.files
|
||||
},
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,27 +3,56 @@ package org.nixos.gradle2nix
|
||||
import org.gradle.api.DefaultTask
|
||||
import org.gradle.api.Project
|
||||
import org.gradle.api.artifacts.Configuration
|
||||
import org.gradle.api.artifacts.component.ModuleComponentIdentifier
|
||||
import org.gradle.api.file.FileCollection
|
||||
import org.gradle.api.invocation.Gradle
|
||||
import org.gradle.api.logging.Logging
|
||||
import org.gradle.api.model.ObjectFactory
|
||||
import org.gradle.api.tasks.InputFiles
|
||||
import org.gradle.api.tasks.Internal
|
||||
import org.gradle.api.tasks.TaskProvider
|
||||
import org.gradle.api.tasks.TaskAction
|
||||
import org.gradle.internal.deprecation.DeprecatableConfiguration
|
||||
import org.nixos.gradle2nix.model.ARTIFACTS_PROPERTY
|
||||
import org.nixos.gradle2nix.model.ArtifactType
|
||||
import org.nixos.gradle2nix.model.RESOLVE_ALL_TASK
|
||||
import org.nixos.gradle2nix.model.RESOLVE_PROJECT_TASK
|
||||
import javax.inject.Inject
|
||||
|
||||
fun interface ResolveAllArtifactsApplier {
|
||||
fun apply(gradle: Gradle)
|
||||
}
|
||||
|
||||
val Project.reportableConfigurations: List<Configuration>
|
||||
get() = configurations.filter { (it as? DeprecatableConfiguration)?.canSafelyBeResolved() ?: it.isCanBeResolved }
|
||||
|
||||
abstract class AbstractResolveAllArtifactsApplier : ResolveAllArtifactsApplier {
|
||||
abstract fun Project.registerProjectTask(): TaskProvider<*>
|
||||
abstract fun Project.addConfigurationArtifactResolver(
|
||||
configuration: Configuration,
|
||||
artifactType: ArtifactType,
|
||||
): FileCollection
|
||||
|
||||
final override fun apply(gradle: Gradle) {
|
||||
val resolveAll = gradle.rootProject.tasks.register(RESOLVE_ALL_TASK)
|
||||
|
||||
val artifacts =
|
||||
System
|
||||
.getProperty(ARTIFACTS_PROPERTY, "")
|
||||
.split(",")
|
||||
.filter { it.isNotBlank() }
|
||||
.mapTo(mutableSetOf()) { ArtifactType.valueOf(it.toUpperCase()) }
|
||||
|
||||
// Depend on "dependencies" task in all projects
|
||||
gradle.allprojects { project ->
|
||||
val resolveProject = project.registerProjectTask()
|
||||
val resolveProject =
|
||||
project.tasks.register(RESOLVE_PROJECT_TASK, ResolveProjectDependenciesTask::class.java) { task ->
|
||||
task.projectName.set(project.path)
|
||||
for (configuration in project.reportableConfigurations) {
|
||||
task.configurations.from(configuration)
|
||||
for (artifactType in artifacts) {
|
||||
task.configurations.from(project.addConfigurationArtifactResolver(configuration, artifactType))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
resolveAll.configure { it.dependsOn(resolveProject) }
|
||||
}
|
||||
|
||||
@@ -36,17 +65,25 @@ abstract class AbstractResolveAllArtifactsApplier : ResolveAllArtifactsApplier {
|
||||
}
|
||||
}
|
||||
|
||||
abstract class ResolveProjectDependenciesTask : DefaultTask() {
|
||||
@Internal
|
||||
protected fun getReportableConfigurations(): List<Configuration> =
|
||||
project.configurations.filter {
|
||||
(it as? DeprecatableConfiguration)?.canSafelyBeResolved() ?: true
|
||||
@Suppress("UnstableApiUsage")
|
||||
abstract class ResolveProjectDependenciesTask
|
||||
@Inject
|
||||
constructor(
|
||||
objects: ObjectFactory,
|
||||
) : DefaultTask() {
|
||||
@get:Internal
|
||||
val projectName = objects.property(String::class.java)
|
||||
|
||||
@get:InputFiles
|
||||
val configurations = objects.fileCollection()
|
||||
|
||||
@TaskAction
|
||||
fun resolve() {
|
||||
val count = configurations.count()
|
||||
LOGGER.info("${projectName.get()}: resolved $count artifacts")
|
||||
}
|
||||
|
||||
protected fun Configuration.artifactFiles(): FileCollection =
|
||||
incoming
|
||||
.artifactView { viewConfiguration ->
|
||||
viewConfiguration.isLenient = true
|
||||
viewConfiguration.componentFilter { it is ModuleComponentIdentifier }
|
||||
}.files
|
||||
}
|
||||
companion object {
|
||||
private val LOGGER = Logging.getLogger(ResolveProjectDependenciesTask::class.java)
|
||||
}
|
||||
}
|
||||
|
||||
12
plugin/gradle75/build.gradle.kts
Normal file
12
plugin/gradle75/build.gradle.kts
Normal file
@@ -0,0 +1,12 @@
|
||||
plugins {
|
||||
`plugin-conventions`
|
||||
}
|
||||
|
||||
dependencies {
|
||||
compileOnly(libs.gradle.api.get75())
|
||||
implementation(project(":plugin:common"))
|
||||
}
|
||||
|
||||
tasks.shadowJar {
|
||||
archiveFileName = "plugin-gradle75.jar"
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
import org.gradle.api.invocation.Gradle
|
||||
import org.gradle.api.services.BuildService
|
||||
import org.gradle.api.services.BuildServiceParameters
|
||||
import org.gradle.internal.build.event.BuildEventListenerRegistryInternal
|
||||
import org.gradle.internal.operations.BuildOperationDescriptor
|
||||
import org.gradle.internal.operations.BuildOperationListener
|
||||
import org.gradle.internal.operations.OperationFinishEvent
|
||||
import org.gradle.internal.operations.OperationIdentifier
|
||||
import org.gradle.internal.operations.OperationProgressEvent
|
||||
import org.gradle.internal.operations.OperationStartEvent
|
||||
|
||||
object DependencyExtractorApplierG75 : DependencyExtractorApplier {
|
||||
@Suppress("UnstableApiUsage")
|
||||
override fun apply(
|
||||
gradle: Gradle,
|
||||
extractor: DependencyExtractor,
|
||||
) {
|
||||
val serviceProvider =
|
||||
gradle.sharedServices
|
||||
.registerIfAbsent(
|
||||
"nixDependencyExtractor",
|
||||
DependencyExtractorService::class.java,
|
||||
) {}
|
||||
.map { service ->
|
||||
service.apply { this.extractor = extractor }
|
||||
}
|
||||
|
||||
gradle.service<BuildEventListenerRegistryInternal>().onOperationCompletion(serviceProvider)
|
||||
}
|
||||
}
|
||||
|
||||
@Suppress("UnstableApiUsage")
|
||||
internal abstract class DependencyExtractorService :
|
||||
BuildService<BuildServiceParameters.None>,
|
||||
BuildOperationListener,
|
||||
AutoCloseable {
|
||||
var extractor: DependencyExtractor? = null
|
||||
|
||||
override fun started(
|
||||
buildOperation: BuildOperationDescriptor,
|
||||
startEvent: OperationStartEvent,
|
||||
) {}
|
||||
|
||||
override fun progress(
|
||||
operationIdentifier: OperationIdentifier,
|
||||
progressEvent: OperationProgressEvent,
|
||||
) {}
|
||||
|
||||
override fun finished(
|
||||
buildOperation: BuildOperationDescriptor,
|
||||
finishEvent: OperationFinishEvent,
|
||||
) {
|
||||
extractor?.finished(buildOperation, finishEvent)
|
||||
}
|
||||
|
||||
override fun close() {
|
||||
extractor = null
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
abstract class Gradle2NixPlugin :
|
||||
AbstractGradle2NixPlugin(
|
||||
GradleCacheAccessFactoryG75,
|
||||
DependencyExtractorApplierG75,
|
||||
ResolveAllArtifactsApplierG75,
|
||||
)
|
||||
@@ -0,0 +1,18 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
import org.gradle.api.internal.artifacts.ivyservice.ArtifactCachesProvider
|
||||
import org.gradle.api.invocation.Gradle
|
||||
|
||||
object GradleCacheAccessFactoryG75 : GradleCacheAccessFactory {
|
||||
override fun create(gradle: Gradle): GradleCacheAccess = GradleCacheAccessG75(gradle)
|
||||
}
|
||||
|
||||
class GradleCacheAccessG75(
|
||||
gradle: Gradle,
|
||||
) : GradleCacheAccess {
|
||||
private val artifactCachesProvider = gradle.service<ArtifactCachesProvider>()
|
||||
|
||||
override fun useCache(block: () -> Unit) {
|
||||
artifactCachesProvider.writableCacheLockingManager.useCache(block)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
import org.gradle.api.Project
|
||||
import org.gradle.api.artifacts.Configuration
|
||||
import org.gradle.api.artifacts.component.ModuleComponentIdentifier
|
||||
import org.gradle.api.attributes.Bundling
|
||||
import org.gradle.api.attributes.DocsType
|
||||
import org.gradle.api.file.FileCollection
|
||||
import org.nixos.gradle2nix.model.ArtifactType
|
||||
|
||||
object ResolveAllArtifactsApplierG75 : AbstractResolveAllArtifactsApplier() {
|
||||
@Suppress("UnstableApiUsage")
|
||||
override fun Project.addConfigurationArtifactResolver(
|
||||
configuration: Configuration,
|
||||
artifactType: ArtifactType,
|
||||
): FileCollection {
|
||||
val result =
|
||||
configuration.incoming
|
||||
.artifactView { view ->
|
||||
view.isLenient = true
|
||||
view.withVariantReselection()
|
||||
view.componentFilter { it is ModuleComponentIdentifier }
|
||||
view.attributes { attrs ->
|
||||
with(attrs) {
|
||||
attribute(Bundling.BUNDLING_ATTRIBUTE, objects.named(Bundling::class.java, Bundling.EXTERNAL))
|
||||
attribute(
|
||||
DocsType.DOCS_TYPE_ATTRIBUTE,
|
||||
objects.named(
|
||||
DocsType::class.java,
|
||||
when (artifactType) {
|
||||
ArtifactType.DOXYGEN -> DocsType.DOXYGEN
|
||||
ArtifactType.JAVADOC -> DocsType.JAVADOC
|
||||
ArtifactType.SAMPLES -> DocsType.SAMPLES
|
||||
ArtifactType.SOURCES -> DocsType.SOURCES
|
||||
ArtifactType.USERMANUAL -> DocsType.USER_MANUAL
|
||||
},
|
||||
),
|
||||
)
|
||||
}
|
||||
}
|
||||
}.files
|
||||
|
||||
configuration.incoming.afterResolve { result.files.count() }
|
||||
|
||||
return result
|
||||
}
|
||||
}
|
||||
@@ -1,37 +1,49 @@
|
||||
package org.nixos.gradle2nix
|
||||
|
||||
import org.gradle.api.Project
|
||||
import org.gradle.api.artifacts.Configuration
|
||||
import org.gradle.api.artifacts.component.ModuleComponentIdentifier
|
||||
import org.gradle.api.attributes.Bundling
|
||||
import org.gradle.api.attributes.DocsType
|
||||
import org.gradle.api.file.FileCollection
|
||||
import org.gradle.api.model.ObjectFactory
|
||||
import org.gradle.api.tasks.TaskAction
|
||||
import org.gradle.api.tasks.TaskProvider
|
||||
import org.gradle.internal.serialization.Cached
|
||||
import org.gradle.work.DisableCachingByDefault
|
||||
import org.nixos.gradle2nix.model.RESOLVE_PROJECT_TASK
|
||||
import javax.inject.Inject
|
||||
import org.nixos.gradle2nix.model.ArtifactType
|
||||
|
||||
object ResolveAllArtifactsApplierG8 : AbstractResolveAllArtifactsApplier() {
|
||||
override fun Project.registerProjectTask(): TaskProvider<*> =
|
||||
tasks.register(RESOLVE_PROJECT_TASK, ResolveProjectDependenciesTaskG8::class.java)
|
||||
}
|
||||
@Suppress("UnstableApiUsage")
|
||||
override fun Project.addConfigurationArtifactResolver(
|
||||
configuration: Configuration,
|
||||
artifactType: ArtifactType,
|
||||
): FileCollection {
|
||||
val result =
|
||||
configuration.incoming
|
||||
.artifactView { view ->
|
||||
view.isLenient = true
|
||||
view.withVariantReselection()
|
||||
view.componentFilter { it is ModuleComponentIdentifier }
|
||||
view.attributes { attrs ->
|
||||
with(attrs) {
|
||||
attribute(Bundling.BUNDLING_ATTRIBUTE, objects.named(Bundling::class.java, Bundling.EXTERNAL))
|
||||
attribute(
|
||||
DocsType.DOCS_TYPE_ATTRIBUTE,
|
||||
objects.named(
|
||||
DocsType::class.java,
|
||||
when (artifactType) {
|
||||
ArtifactType.DOXYGEN -> DocsType.DOXYGEN
|
||||
ArtifactType.JAVADOC -> DocsType.JAVADOC
|
||||
ArtifactType.SAMPLES -> DocsType.SAMPLES
|
||||
ArtifactType.SOURCES -> DocsType.SOURCES
|
||||
ArtifactType.USERMANUAL -> DocsType.USER_MANUAL
|
||||
},
|
||||
),
|
||||
)
|
||||
}
|
||||
}
|
||||
}.files
|
||||
|
||||
@DisableCachingByDefault(because = "Not worth caching")
|
||||
abstract class ResolveProjectDependenciesTaskG8
|
||||
@Inject
|
||||
constructor(
|
||||
private val objects: ObjectFactory,
|
||||
) : ResolveProjectDependenciesTask() {
|
||||
private val artifactFiles = Cached.of { artifactFiles() }
|
||||
|
||||
private fun artifactFiles(): FileCollection =
|
||||
objects.fileCollection().from(
|
||||
getReportableConfigurations().map { configuration ->
|
||||
configuration.artifactFiles()
|
||||
},
|
||||
)
|
||||
|
||||
@TaskAction
|
||||
fun action() {
|
||||
artifactFiles.get().count()
|
||||
configuration.incoming.afterResolve {
|
||||
result.files.count()
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,8 +3,8 @@ plugins {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation(project(":plugin:gradle8"))
|
||||
compileOnly(libs.gradle.api.get80())
|
||||
implementation(project(":plugin:gradle8"))
|
||||
}
|
||||
|
||||
tasks.shadowJar {
|
||||
|
||||
@@ -3,8 +3,8 @@ plugins {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation(project(":plugin:gradle8"))
|
||||
compileOnly(libs.gradle.api.get81())
|
||||
implementation(project(":plugin:gradle8"))
|
||||
}
|
||||
|
||||
tasks.shadowJar {
|
||||
|
||||
Reference in New Issue
Block a user