[Gradle] GranularMetadataTransformation: ProjectData: Use Future instead of lambda
^KT-34662 Verification Pending
This commit is contained in:
committed by
Space Team
parent
7c65d00f29
commit
ea48b52d43
+3
-2
@@ -387,6 +387,8 @@ private class KotlinPluginLifecycleImpl(override val project: Project) : KotlinP
|
||||
"${KotlinPluginLifecycle::class.java.name} cannot be started in ProjectState '${project.state}'"
|
||||
}
|
||||
|
||||
loopIfNecessary()
|
||||
|
||||
project.whenEvaluated {
|
||||
assert(enqueuedActions.getValue(stage).isEmpty()) { "Expected empty queue from '$stage'" }
|
||||
stage = stage.nextOrThrow
|
||||
@@ -445,14 +447,13 @@ private class KotlinPluginLifecycleImpl(override val project: Project) : KotlinP
|
||||
|
||||
enqueuedActions.getValue(stage).addLast(action)
|
||||
|
||||
if (stage == Stage.Configure) {
|
||||
if (stage == Stage.Configure && isStarted.get()) {
|
||||
loopIfNecessary()
|
||||
}
|
||||
}
|
||||
|
||||
override fun launch(block: suspend KotlinPluginLifecycle.() -> Unit) {
|
||||
val lifecycle = this
|
||||
check(isStarted.get()) { "Cannot launch when ${KotlinPluginLifecycle::class.simpleName} is not started" }
|
||||
|
||||
val coroutine = block.createCoroutine(this, object : Continuation<Unit> {
|
||||
override val context: CoroutineContext = EmptyCoroutineContext +
|
||||
|
||||
+2
-2
@@ -77,8 +77,6 @@ abstract class DefaultKotlinBasePlugin : KotlinBasePlugin {
|
||||
|
||||
checkGradleCompatibility()
|
||||
|
||||
project.startKotlinPluginLifecycle()
|
||||
|
||||
project.gradle.projectsEvaluated {
|
||||
whenBuildEvaluated(project)
|
||||
}
|
||||
@@ -233,6 +231,8 @@ abstract class KotlinBasePluginWrapper : DefaultKotlinBasePlugin() {
|
||||
project.addNpmDependencyExtension()
|
||||
|
||||
project.registerBuildKotlinToolingMetadataTask()
|
||||
|
||||
project.startKotlinPluginLifecycle()
|
||||
}
|
||||
|
||||
internal open fun createTestRegistry(project: Project) = KotlinTestsRegistry(project)
|
||||
|
||||
+13
-15
@@ -14,12 +14,10 @@ import org.gradle.api.file.FileCollection
|
||||
import org.gradle.api.logging.Logging
|
||||
import org.jetbrains.kotlin.gradle.dsl.KotlinMultiplatformExtension
|
||||
import org.jetbrains.kotlin.gradle.dsl.multiplatformExtension
|
||||
import org.jetbrains.kotlin.gradle.dsl.multiplatformExtensionOrNull
|
||||
import org.jetbrains.kotlin.gradle.plugin.KotlinPlatformType
|
||||
import org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet
|
||||
import org.jetbrains.kotlin.gradle.plugin.extraProperties
|
||||
import org.jetbrains.kotlin.gradle.plugin.*
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.MetadataDependencyResolution.ChooseVisibleSourceSets.MetadataProvider.ArtifactMetadataProvider
|
||||
import org.jetbrains.kotlin.gradle.plugin.sources.internal
|
||||
import org.jetbrains.kotlin.gradle.utils.Future
|
||||
import org.jetbrains.kotlin.gradle.utils.LazyResolvedConfiguration
|
||||
import org.jetbrains.kotlin.gradle.utils.future
|
||||
import org.jetbrains.kotlin.gradle.utils.getOrPut
|
||||
@@ -118,12 +116,9 @@ internal class GranularMetadataTransformation(
|
||||
|
||||
class ProjectData(
|
||||
val path: String,
|
||||
sourceSetMetadataOutputsProvider: () -> Map<String, SourceSetMetadataOutputs>,
|
||||
moduleIdProvider: () -> ModuleDependencyIdentifier
|
||||
val sourceSetMetadataOutputs: Future<Map<String, SourceSetMetadataOutputs>>,
|
||||
val moduleId: Future<ModuleDependencyIdentifier>
|
||||
) {
|
||||
val sourceSetMetadataOutputs by lazy(sourceSetMetadataOutputsProvider)
|
||||
val moduleId by lazy(moduleIdProvider)
|
||||
|
||||
override fun toString(): String = "ProjectData[path='$path']"
|
||||
}
|
||||
|
||||
@@ -275,7 +270,7 @@ internal class GranularMetadataTransformation(
|
||||
val metadataProvider = when (mppDependencyMetadataExtractor) {
|
||||
is ProjectMppDependencyProjectStructureMetadataExtractor -> ProjectMetadataProvider(
|
||||
sourceSetMetadataOutputs = params.projectData[mppDependencyMetadataExtractor.projectPath]?.sourceSetMetadataOutputs
|
||||
?: error("Unexpected project path '${mppDependencyMetadataExtractor.projectPath}'")
|
||||
?.getOrThrow() ?: error("Unexpected project path '${mppDependencyMetadataExtractor.projectPath}'")
|
||||
)
|
||||
|
||||
is JarMppDependencyProjectStructureMetadataExtractor -> ArtifactMetadataProvider(
|
||||
@@ -308,7 +303,7 @@ internal class GranularMetadataTransformation(
|
||||
is ModuleComponentIdentifier -> ModuleDependencyIdentifier(componentId.group, componentId.module)
|
||||
is ProjectComponentIdentifier -> {
|
||||
if (componentId.build.isCurrentBuild) {
|
||||
params.projectData[componentId.projectPath]?.moduleId
|
||||
params.projectData[componentId.projectPath]?.moduleId?.getOrThrow()
|
||||
?: error("Cant find project Module ID by ${componentId.projectPath}")
|
||||
} else {
|
||||
ModuleDependencyIdentifier(
|
||||
@@ -337,15 +332,18 @@ private val Project.allProjectsData: Map<String, GranularMetadataTransformation.
|
||||
get() = rootProject
|
||||
.extraProperties
|
||||
.getOrPut("all${GranularMetadataTransformation.ProjectData::class.java.simpleName}") {
|
||||
future { collectAllProjectsData() }.getOrThrow()
|
||||
collectAllProjectsData()
|
||||
}
|
||||
|
||||
private fun Project.collectAllProjectsData(): Map<String, GranularMetadataTransformation.ProjectData> {
|
||||
return rootProject.allprojects.associateBy { it.path }.mapValues { (path, subProject) ->
|
||||
return rootProject.allprojects.associateBy { it.path }.mapValues { (path, currentProject) ->
|
||||
GranularMetadataTransformation.ProjectData(
|
||||
path = path,
|
||||
sourceSetMetadataOutputsProvider = future { subProject.collectSourceSetMetadataOutputs() }::getOrThrow,
|
||||
moduleIdProvider = { ModuleIds.idOfRootModule(subProject) }
|
||||
sourceSetMetadataOutputs = currentProject.future { currentProject.collectSourceSetMetadataOutputs() },
|
||||
moduleId = currentProject.future {
|
||||
await(KotlinPluginLifecycle.Stage.AfterFinaliseDsl)
|
||||
ModuleIds.idOfRootModule(currentProject)
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
+7
-9
@@ -9,8 +9,11 @@ import org.gradle.api.Project
|
||||
import org.gradle.api.file.FileCollection
|
||||
import org.jetbrains.kotlin.gradle.dsl.KotlinMultiplatformExtension
|
||||
import org.jetbrains.kotlin.gradle.dsl.multiplatformExtensionOrNull
|
||||
import org.jetbrains.kotlin.gradle.plugin.KotlinPluginLifecycle
|
||||
import org.jetbrains.kotlin.gradle.plugin.KotlinSourceSet
|
||||
import org.jetbrains.kotlin.gradle.plugin.await
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.MetadataDependencyResolution.ChooseVisibleSourceSets.MetadataProvider.ProjectMetadataProvider
|
||||
import org.jetbrains.kotlin.gradle.targets.metadata.findMetadataCompilation
|
||||
import org.jetbrains.kotlin.gradle.targets.native.internal.*
|
||||
|
||||
private typealias SourceSetName = String
|
||||
@@ -33,7 +36,7 @@ internal class SourceSetMetadataOutputs(
|
||||
|
||||
private class ProjectMetadataProviderImpl(
|
||||
private val sourceSetMetadataOutputs: Map<SourceSetName, SourceSetMetadataOutputs>
|
||||
): ProjectMetadataProvider() {
|
||||
) : ProjectMetadataProvider() {
|
||||
|
||||
override fun getSourceSetCompiledMetadata(sourceSetName: String): FileCollection =
|
||||
sourceSetMetadataOutputs[sourceSetName]?.metadata ?: error("Unexpected source set '$sourceSetName'")
|
||||
@@ -63,16 +66,11 @@ internal suspend fun Project.collectSourceSetMetadataOutputs(): Map<SourceSetNam
|
||||
}.mapKeys { it.key.name }
|
||||
}
|
||||
|
||||
private fun KotlinMultiplatformExtension.sourceSetsMetadataOutputs(): Map<KotlinSourceSet, FileCollection> {
|
||||
val commonTarget = metadata()
|
||||
|
||||
val compilations = commonTarget.compilations
|
||||
private suspend fun KotlinMultiplatformExtension.sourceSetsMetadataOutputs(): Map<KotlinSourceSet, FileCollection> {
|
||||
await(KotlinPluginLifecycle.Stage.AfterFinaliseDsl)
|
||||
|
||||
return sourceSets.mapNotNull { sourceSet ->
|
||||
val compilation = compilations.findByName(sourceSet.name)
|
||||
?: return@mapNotNull null // given source set is not shared
|
||||
|
||||
val destination = when (compilation) {
|
||||
val destination = when (val compilation = project.findMetadataCompilation(sourceSet) ?: return@mapNotNull null) {
|
||||
is KotlinCommonCompilation -> compilation.output.classesDirs
|
||||
is KotlinSharedNativeCompilation -> compilation.output.classesDirs
|
||||
else -> error("Unexpected compilation type: $compilation")
|
||||
|
||||
-4
@@ -9,10 +9,6 @@ import org.gradle.api.Project
|
||||
import org.gradle.api.artifacts.Configuration
|
||||
import org.jetbrains.kotlin.gradle.dsl.multiplatformExtensionOrNull
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.*
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.GranularMetadataTransformation
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.MetadataDependencyResolution
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.ModuleIds
|
||||
import org.jetbrains.kotlin.gradle.plugin.mpp.projectDependency
|
||||
import org.jetbrains.kotlin.gradle.targets.metadata.dependsOnClosureWithInterCompilationDependencies
|
||||
import org.jetbrains.kotlin.tooling.core.extrasNullableLazyProperty
|
||||
|
||||
|
||||
+6
-3
@@ -80,7 +80,7 @@ internal fun <T> Project.future(block: suspend Project.() -> T): Future<T> = kot
|
||||
internal fun <T> Project.lazyFuture(block: suspend Project.() -> T): Lazy<Future<T>> = lazy { future(block) }
|
||||
|
||||
internal fun <T> KotlinPluginLifecycle.future(block: suspend () -> T): Future<T> {
|
||||
return FutureImpl<T>(CompletableDeferred()).also { future ->
|
||||
return FutureImpl<T>(lifecycle = this).also { future ->
|
||||
launch { future.completeWith(runCatching { block() }) }
|
||||
}
|
||||
}
|
||||
@@ -90,7 +90,10 @@ internal fun <T> CompletableFuture(): CompletableFuture<T> {
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalCoroutinesApi::class)
|
||||
private class FutureImpl<T>(private val deferred: CompletableDeferred<T> = CompletableDeferred()) : CompletableFuture<T>, Serializable {
|
||||
private class FutureImpl<T>(
|
||||
private val deferred: CompletableDeferred<T> = CompletableDeferred(),
|
||||
private val lifecycle: KotlinPluginLifecycle? = null
|
||||
) : CompletableFuture<T>, Serializable {
|
||||
fun completeWith(result: Result<T>) = deferred.completeWith(result)
|
||||
|
||||
override fun complete(value: T) {
|
||||
@@ -103,7 +106,7 @@ private class FutureImpl<T>(private val deferred: CompletableDeferred<T> = Compl
|
||||
|
||||
override fun getOrThrow(): T {
|
||||
return if (deferred.isCompleted) deferred.getCompleted() else throw IllegalLifecycleException(
|
||||
"Future was not completed yet"
|
||||
"Future was not completed yet" + if (lifecycle != null) " (stage '${lifecycle.stage}')" else ""
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user