diff --git a/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt index 65b0e66922f..8a8289bda15 100644 --- a/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt +++ b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt @@ -12,6 +12,7 @@ import com.intellij.openapi.externalSystem.model.project.ModuleData import com.intellij.openapi.externalSystem.model.project.ProjectData import com.intellij.openapi.externalSystem.model.task.TaskData import com.intellij.openapi.externalSystem.util.Order +import com.intellij.openapi.util.io.StreamUtil import com.intellij.openapi.util.registry.Registry import com.intellij.util.Consumer import org.gradle.tooling.model.idea.IdeaModule @@ -19,6 +20,11 @@ import org.jetbrains.kotlin.gradle.KotlinMPPGradleModel import org.jetbrains.kotlin.gradle.KotlinMPPGradleModelBuilder import org.jetbrains.kotlin.idea.configuration.getMppModel import org.jetbrains.plugins.gradle.service.project.AbstractProjectResolverExtension +import org.jetbrains.plugins.gradle.service.project.GradleProjectResolverExtension +import org.jetbrains.plugins.gradle.service.project.JavaGradleProjectResolver +import java.io.IOException +import java.lang.Boolean +import java.nio.charset.StandardCharsets @Order(Int.MIN_VALUE) open class KotlinTestTasksResolver : AbstractProjectResolverExtension() { @@ -82,6 +88,32 @@ open class KotlinTestTasksResolver : AbstractProjectResolverExtension() { return originalTaskData.mapTo(arrayListOf()) { replacementMap[it] ?: it } } + override fun enhanceTaskProcessing( + taskNames: MutableList, + initScriptConsumer: Consumer, + parameters: MutableMap + ) { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return + + val testExecutionExpected = parameters[GradleProjectResolverExtension.TEST_EXECUTION_EXPECTED_KEY] + + if (Boolean.valueOf(testExecutionExpected)) { + try { + val addTestListenerScript = javaClass + .getResourceAsStream("/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy") + .bufferedReader() + .readText() + initScriptConsumer.consume(addTestListenerScript) + } catch (e: Exception) { + LOG.error(e) + } + } + + val jvmParametersSetup = parameters[GradleProjectResolverExtension.JVM_PARAMETERS_SETUP_KEY] + enhanceTaskProcessing(taskNames, jvmParametersSetup, initScriptConsumer) + } + override fun enhanceTaskProcessing(taskNames: MutableList, jvmAgentSetup: String?, initScriptConsumer: Consumer) { if (!Registry.`is`(ENABLED_REGISTRY_KEY)) return diff --git a/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.191 b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.191 new file mode 100644 index 00000000000..8ddc3a2d687 --- /dev/null +++ b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.191 @@ -0,0 +1,109 @@ +/* + * Copyright 2010-2019 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.gradle.testing + +import com.intellij.openapi.diagnostic.Logger +import com.intellij.openapi.externalSystem.model.DataNode +import com.intellij.openapi.externalSystem.model.ProjectKeys +import com.intellij.openapi.externalSystem.model.project.ModuleData +import com.intellij.openapi.externalSystem.model.project.ProjectData +import com.intellij.openapi.externalSystem.model.task.TaskData +import com.intellij.openapi.externalSystem.util.Order +import com.intellij.openapi.util.registry.Registry +import com.intellij.util.Consumer +import org.gradle.tooling.model.idea.IdeaModule +import org.jetbrains.kotlin.gradle.KotlinMPPGradleModel +import org.jetbrains.kotlin.gradle.KotlinMPPGradleModelBuilder +import org.jetbrains.kotlin.idea.configuration.getMppModel +import org.jetbrains.plugins.gradle.service.project.AbstractProjectResolverExtension + +@Order(Int.MIN_VALUE) +open class KotlinTestTasksResolver : AbstractProjectResolverExtension() { + companion object { + private const val ENABLED_REGISTRY_KEY = "kotlin.gradle.testing.enabled" + } + + private val LOG by lazy { Logger.getInstance(KotlinTestTasksResolver::class.java) } + + override fun getToolingExtensionsClasses(): Set> { + return setOf(KotlinMPPGradleModelBuilder::class.java, Unit::class.java) + } + + override fun populateModuleTasks( + gradleModule: IdeaModule, + ideModule: DataNode, + ideProject: DataNode + ): MutableCollection { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return super.populateModuleTasks(gradleModule, ideModule, ideProject) + + val mppModel = resolverCtx.getMppModel(gradleModule) + ?: return super.populateModuleTasks(gradleModule, ideModule, ideProject) + + return postprocessTaskData(mppModel, ideModule, nextResolver.populateModuleTasks(gradleModule, ideModule, ideProject)) + } + + private fun postprocessTaskData( + mppModel: KotlinMPPGradleModel, + ideModule: DataNode, + originalTaskData: MutableCollection + ): MutableCollection { + val testTaskNames = mutableSetOf().apply { + mppModel.targets.forEach { target -> + target.testTasks.forEach { testTaskModel -> + add(testTaskModel.taskName) + } + } + } + + fun buildNewTaskDataMarkedAsTest(original: TaskData): TaskData = + TaskData(original.owner, original.name, original.linkedExternalProjectPath, original.description).apply { + group = original.group + type = original.type + isInherited = original.isInherited + + isTest = true + } + + val replacementMap: Map = mutableMapOf().apply { + originalTaskData.forEach { + if (it.name in testTaskNames && !it.isTest) { + put(it, buildNewTaskDataMarkedAsTest(it)) + } + } + } + + ideModule.children.filter { it.data in replacementMap }.forEach { it.clear(true) } + replacementMap.values.forEach { ideModule.createChild(ProjectKeys.TASK, it) } + + return originalTaskData.mapTo(arrayListOf()) { replacementMap[it] ?: it } + } + + override fun enhanceTaskProcessing(taskNames: MutableList, jvmAgentSetup: String?, initScriptConsumer: Consumer) { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return + + try { + //for 191 idea we can't check running task so add listener always + val addTestListenerScript = javaClass + .getResourceAsStream("/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy") + .bufferedReader() + .readText() + val testLoggerScript = javaClass + .getResourceAsStream("/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy") + .bufferedReader() + .readText() + + initScriptConsumer.consume(buildString { + append(addTestListenerScript) + append('\n') + append(testLoggerScript) + }) + } catch (e: Exception) { + LOG.error(e) + } + } +} \ No newline at end of file diff --git a/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.192 b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.192 new file mode 100644 index 00000000000..70c80d51b36 --- /dev/null +++ b/idea/idea-gradle/src/org/jetbrains/kotlin/idea/gradle/testing/KotlinTestTasksResolver.kt.192 @@ -0,0 +1,124 @@ +/* + * Copyright 2010-2019 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.gradle.testing + +import com.intellij.openapi.diagnostic.Logger +import com.intellij.openapi.externalSystem.model.DataNode +import com.intellij.openapi.externalSystem.model.ProjectKeys +import com.intellij.openapi.externalSystem.model.project.ModuleData +import com.intellij.openapi.externalSystem.model.project.ProjectData +import com.intellij.openapi.externalSystem.model.task.TaskData +import com.intellij.openapi.externalSystem.util.Order +import com.intellij.openapi.util.registry.Registry +import com.intellij.util.Consumer +import org.gradle.tooling.model.idea.IdeaModule +import org.jetbrains.kotlin.gradle.KotlinMPPGradleModel +import org.jetbrains.kotlin.gradle.KotlinMPPGradleModelBuilder +import org.jetbrains.kotlin.idea.configuration.getMppModel +import org.jetbrains.plugins.gradle.service.project.AbstractProjectResolverExtension + +@Order(Int.MIN_VALUE) +open class KotlinTestTasksResolver : AbstractProjectResolverExtension() { + companion object { + private const val ENABLED_REGISTRY_KEY = "kotlin.gradle.testing.enabled" + } + + private val LOG by lazy { Logger.getInstance(KotlinTestTasksResolver::class.java) } + + override fun getToolingExtensionsClasses(): Set> { + return setOf(KotlinMPPGradleModelBuilder::class.java, Unit::class.java) + } + + override fun populateModuleTasks( + gradleModule: IdeaModule, + ideModule: DataNode, + ideProject: DataNode + ): MutableCollection { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return super.populateModuleTasks(gradleModule, ideModule, ideProject) + + val mppModel = resolverCtx.getMppModel(gradleModule) + ?: return super.populateModuleTasks(gradleModule, ideModule, ideProject) + + return postprocessTaskData(mppModel, ideModule, nextResolver.populateModuleTasks(gradleModule, ideModule, ideProject)) + } + + private fun postprocessTaskData( + mppModel: KotlinMPPGradleModel, + ideModule: DataNode, + originalTaskData: MutableCollection + ): MutableCollection { + val testTaskNames = mutableSetOf().apply { + mppModel.targets.forEach { target -> + target.testTasks.forEach { testTaskModel -> + add(testTaskModel.taskName) + } + } + } + + fun buildNewTaskDataMarkedAsTest(original: TaskData): TaskData = + TaskData(original.owner, original.name, original.linkedExternalProjectPath, original.description).apply { + group = original.group + type = original.type + isInherited = original.isInherited + + isTest = true + } + + val replacementMap: Map = mutableMapOf().apply { + originalTaskData.forEach { + if (it.name in testTaskNames && !it.isTest) { + put(it, buildNewTaskDataMarkedAsTest(it)) + } + } + } + + ideModule.children.filter { it.data in replacementMap }.forEach { it.clear(true) } + replacementMap.values.forEach { ideModule.createChild(ProjectKeys.TASK, it) } + + return originalTaskData.mapTo(arrayListOf()) { replacementMap[it] ?: it } + } + + override fun enhanceTaskProcessing( + taskNames: MutableList, + jvmParametersSetup: String?, + initScriptConsumer: Consumer, + testExecutionExpected: kotlin.Boolean + ) { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return + + if (testExecutionExpected) { + try { + val addTestListenerScript = javaClass + .getResourceAsStream("/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy") + .bufferedReader() + .readText() + initScriptConsumer.consume(addTestListenerScript) + } catch (e: Exception) { + LOG.error(e) + } + } + + enhanceTaskProcessing(taskNames, jvmParametersSetup, initScriptConsumer) + } + + override fun enhanceTaskProcessing(taskNames: MutableList, jvmAgentSetup: String?, initScriptConsumer: Consumer) { + if (!Registry.`is`(ENABLED_REGISTRY_KEY)) + return + + try { + val testLoggerScript = javaClass + .getResourceAsStream("/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy") + .bufferedReader() + .readText() + + initScriptConsumer.consume(testLoggerScript) + } catch (e: Exception) { + LOG.error(e) + } + } +} \ No newline at end of file diff --git a/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy b/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy index 67c5d003c6f..aaa10a02b91 100644 --- a/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy +++ b/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/KotlinMppTestLogger.groovy @@ -84,23 +84,4 @@ class KotlinMppTestLogger { t.printStackTrace(new PrintWriter(sw)) sw.toString() } -} - -gradle.taskGraph.beforeTask { task -> - def taskSuperClass = task.class - while (taskSuperClass != Object.class) { - if (taskSuperClass.canonicalName == "org.jetbrains.kotlin.gradle.tasks.KotlinTest") { - try { - KotlinMppTestLogger.logTestReportLocation(task.reports?.html?.entryPoint?.path) - KotlinMppTestLogger.configureTestEventLogging(task) - task.testLogging.showStandardStreams = false - } - catch (all) { - logger.error("", all) - } - return - } else { - taskSuperClass = taskSuperClass.superclass - } - } } \ No newline at end of file diff --git a/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy b/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy new file mode 100644 index 00000000000..4db1f5d2769 --- /dev/null +++ b/idea/resources/org/jetbrains/kotlin/idea/gradle/testing/addKotlinMppTestListener.groovy @@ -0,0 +1,18 @@ +gradle.taskGraph.beforeTask { task -> + def taskSuperClass = task.class + while (taskSuperClass != Object.class) { + if (taskSuperClass.canonicalName == "org.jetbrains.kotlin.gradle.tasks.KotlinTest") { + try { + KotlinMppTestLogger.logTestReportLocation(task.reports?.html?.entryPoint?.path) + KotlinMppTestLogger.configureTestEventLogging(task) + task.testLogging.showStandardStreams = false + } + catch (all) { + logger.error("", all) + } + return + } else { + taskSuperClass = taskSuperClass.superclass + } + } +} \ No newline at end of file