From 7a5b4ccb9a69f47e2755fdf8555c8123bc504152 Mon Sep 17 00:00:00 2001 From: Dmitry Savvinov Date: Wed, 13 Jan 2021 12:37:11 +0300 Subject: [PATCH] Refactoring: collect all logic regarding detecting sourceSet platform in one function Note that previously addSourceSetsToCompilation had logic regarding platforms. The reason for that is that it was the last place where default soruce sets of compilations could be distinguished from all participated source sets. So, to move that logic, we have to preserve default source sets. Therefore, this commit introduces 'KotlinCompilation.defaultSourceSets', and 'ImportingContext.isDefaultSourceSet' method. The rest is trivial code moving/methods introduction The resulting code isn't really pretty and likely has non-orthogonal predicates, this will be cleaned-up in the next commits --- .../src/KotlinMPPGradleModel.kt | 15 ++++++++ .../src/KotlinMPPGradleModelBuilder.kt | 34 +++++++++++-------- .../src/KotlinMPPGradleModelImpl.kt | 21 +++++++++--- .../src/MultiplatformModelImportingContext.kt | 13 +++++++ 4 files changed, 64 insertions(+), 19 deletions(-) diff --git a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModel.kt b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModel.kt index 8ae2ccc41d3..e6aa26a7fcc 100644 --- a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModel.kt +++ b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModel.kt @@ -98,7 +98,22 @@ interface KotlinNativeCompilationExtensions : Serializable { } interface KotlinCompilation : KotlinModule { + /** + * All source sets participated in this compilation, including those available + * via dependsOn. + */ val sourceSets: Collection + + /** + * Only default source sets of this compilation, i.e. those which are included + * into compilations directly. + * + * Usually, those are automatically created source sets for automatically created + * compilations (like jvmMain for JVM compilations) or manually included source sets + * (like 'jvm().compilations["main"].source(mySourceSet)' ) + */ + val defaultSourceSets: Collection + val output: KotlinCompilationOutput val arguments: KotlinCompilationArguments val dependencyClasspath: Array diff --git a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelBuilder.kt b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelBuilder.kt index f606ade930e..f045f701d7a 100644 --- a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelBuilder.kt +++ b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelBuilder.kt @@ -363,16 +363,10 @@ class KotlinMPPGradleModelBuilder : ModelBuilderService { ): KotlinCompilationImpl { val dependsOnSourceSets = this.sourceSets.flatMap { it.dependsOnSourceSets }.mapNotNull { importingContext.sourceSetByName(it) } - if (!importingContext.getProperty(IS_HMPP_ENABLED)) { - // intermediate source sets should be common if HMPP is disabled - dependsOnSourceSets.subtract(this.sourceSets).forEach { - it.actualPlatforms.addSimplePlatforms(listOf(KotlinPlatform.COMMON)) - } - } - return KotlinCompilationImpl( this.name, this.sourceSets.union(dependsOnSourceSets), + this.sourceSets, this.dependencies, this.output, this.arguments, @@ -520,6 +514,7 @@ class KotlinMPPGradleModelBuilder : ModelBuilderService { return KotlinCompilationImpl( gradleCompilation.name, + kotlinSourceSets, // In fact, it's only default source-sets. It will be corrected later, see [addDependsOnSourceSetsToCompilation] kotlinSourceSets, dependencies.map { dependencyMapper.getId(it) }.distinct().toTypedArray(), output, @@ -740,14 +735,25 @@ class KotlinMPPGradleModelBuilder : ModelBuilderService { sourceSet.isTestModule = importingContext.compilationsBySourceSet(sourceSet)?.all { it.isTestModule } ?: false - importingContext.compilationsBySourceSet(sourceSet)?.let { compilations -> - val platforms = compilations.map { it.platform } - sourceSet.actualPlatforms.addSimplePlatforms(platforms) - } + importingContext.computeSourceSetPlatforms(sourceSet) + } + } - if (importingContext.shouldCoerceToCommon(sourceSet)) { - sourceSet.actualPlatforms.addSimplePlatforms(listOf(KotlinPlatform.COMMON)) - } + private fun MultiplatformModelImportingContext.computeSourceSetPlatforms(sourceSet: KotlinSourceSetImpl) { + if (shouldCoerceToCommon(sourceSet)) { + sourceSet.actualPlatforms.addSimplePlatforms(listOf(KotlinPlatform.COMMON)) + return + } + + if (!getProperty(IS_HMPP_ENABLED) && !isDefaultSourceSet(sourceSet)) { + // intermediate source sets should be common if HMPP is disabled + sourceSet.actualPlatforms.addSimplePlatforms(listOf(KotlinPlatform.COMMON)) + return + } + + compilationsBySourceSet(sourceSet)?.let { compilations -> + val platforms = compilations.map { it.platform } + sourceSet.actualPlatforms.addSimplePlatforms(platforms) } } diff --git a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelImpl.kt b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelImpl.kt index 1791edf052f..965fcfb4158 100644 --- a/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelImpl.kt +++ b/idea/kotlin-gradle-tooling/src/KotlinMPPGradleModelImpl.kt @@ -128,6 +128,7 @@ data class KotlinNativeCompilationExtensionsImpl( data class KotlinCompilationImpl( override val name: String, override val sourceSets: Collection, + override val defaultSourceSets: Collection, override val dependencies: Array, override val output: KotlinCompilationOutput, override val arguments: KotlinCompilationArguments, @@ -139,11 +140,8 @@ data class KotlinCompilationImpl( // create deep copy constructor(kotlinCompilation: KotlinCompilation, cloningCache: MutableMap) : this( kotlinCompilation.name, - kotlinCompilation.sourceSets.map { initialSourceSet -> - (cloningCache[initialSourceSet] as? KotlinSourceSet) ?: KotlinSourceSetImpl(initialSourceSet, cloningCache).also { - cloningCache[initialSourceSet] = it - } - }.toList(), + cloneSourceSetsWithCaching(kotlinCompilation.sourceSets, cloningCache), + cloneSourceSetsWithCaching(kotlinCompilation.defaultSourceSets, cloningCache), kotlinCompilation.dependencies, KotlinCompilationOutputImpl(kotlinCompilation.output), KotlinCompilationArgumentsImpl(kotlinCompilation.arguments), @@ -166,6 +164,19 @@ data class KotlinCompilationImpl( || platform == KotlinPlatform.ANDROID && name.contains("Test") override fun toString() = name + + companion object { + private fun cloneSourceSetsWithCaching( + sourceSets: Collection, + cloningCache: MutableMap + ): List = + sourceSets.map { initialSourceSet -> + (cloningCache[initialSourceSet] as? KotlinSourceSet) ?: KotlinSourceSetImpl(initialSourceSet, cloningCache).also { + cloningCache[initialSourceSet] = it + } + } + + } } data class KotlinTargetJarImpl( diff --git a/idea/kotlin-gradle-tooling/src/MultiplatformModelImportingContext.kt b/idea/kotlin-gradle-tooling/src/MultiplatformModelImportingContext.kt index 1d760b09508..003236a7a14 100644 --- a/idea/kotlin-gradle-tooling/src/MultiplatformModelImportingContext.kt +++ b/idea/kotlin-gradle-tooling/src/MultiplatformModelImportingContext.kt @@ -34,6 +34,14 @@ internal interface MultiplatformModelImportingContext { * it anywhere (essentially this is a misconfiguration) */ fun isOrphanSourceSet(sourceSet: KotlinSourceSet): Boolean = compilationsBySourceSet(sourceSet) == null + + /** + * "Default" source-set is a source-set which is included into compilation directly, rather + * through closure over dependsOn-relation. + * + * See also KDoc for [KotlinCompilation.defaultSourceSets] + */ + fun isDefaultSourceSet(sourceSet: KotlinSourceSet): Boolean } internal fun MultiplatformModelImportingContext.getProperty(property: GradleImportProperties): Boolean = project.getProperty(property) @@ -71,6 +79,7 @@ internal class MultiplatformModelImportingContextImpl(override val project: Proj override lateinit var compilations: Collection private set private lateinit var sourceSetToParticipatedCompilations: Map> + private lateinit var allDefaultSourceSets: Set /** see [initializeTargets] */ @@ -102,6 +111,8 @@ internal class MultiplatformModelImportingContextImpl(override val project: Proj } this.sourceSetToParticipatedCompilations = sourceSetToCompilations + + this.allDefaultSourceSets = compilations.flatMapTo(mutableSetOf()) { it.defaultSourceSets } } internal fun initializeTargets(targets: Collection) { @@ -112,6 +123,8 @@ internal class MultiplatformModelImportingContextImpl(override val project: Proj // overload for small optimization override fun isOrphanSourceSet(sourceSet: KotlinSourceSet): Boolean = sourceSet !in sourceSetToParticipatedCompilations.keys + override fun isDefaultSourceSet(sourceSet: KotlinSourceSet): Boolean = sourceSet in allDefaultSourceSets + override fun compilationsBySourceSet(sourceSet: KotlinSourceSet): Collection? = sourceSetToParticipatedCompilations[sourceSet]