[BTA] Add Java+Kotlin mixed test and fix compat for mixed scenario

Relates to KT-78196
Merge-request: KT-MR-23164
Merged-by: Alexander Likhachev <Alexander.Likhachev@jetbrains.com>
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java
new file mode 100644
index 0000000..73c4480
--- /dev/null
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java
@@ -0,0 +1,13 @@
+package apkg;
+
+import bpkg.*;
+
+public class AClass {
+    public static String getString() {
+        return (new BClass()).X() + "Z";
+    }
+
+    public static String getY() {
+        return "Y";
+    }
+}
\ No newline at end of file
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java.add-argument b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java.add-argument
new file mode 100644
index 0000000..4b5ae3f
--- /dev/null
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/apkg/AClass.java.add-argument
@@ -0,0 +1,13 @@
+package apkg;
+
+import bpkg.*;
+
+public class AClass {
+    public static String getString(String suffix) {
+        return (new BClass()).X() + "Z" + suffix;
+    }
+
+    public static String getY() {
+        return "Y";
+    }
+}
\ No newline at end of file
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/bpkg/BClass.kt b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/bpkg/BClass.kt
new file mode 100644
index 0000000..2d9dade
--- /dev/null
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/bpkg/BClass.kt
@@ -0,0 +1,7 @@
+package bpkg
+
+import apkg.AClass
+
+class BClass {
+    fun X() = "X" + AClass.getY()
+}
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt
new file mode 100644
index 0000000..f3bbc16
--- /dev/null
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt
@@ -0,0 +1,5 @@
+package bpkg
+
+fun main() {
+    println("Output: <${apkg.AClass.getString()}>")
+}
\ No newline at end of file
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt.add-argument b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt.add-argument
new file mode 100644
index 0000000..eafd977f
--- /dev/null
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/main/resources/modules/kotlin-java-mixed/main.kt.add-argument
@@ -0,0 +1,5 @@
+package bpkg
+
+fun main() {
+    println("Output: <${apkg.AClass.getString("some_suffix")}>")
+}
\ No newline at end of file
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/IncrementalCompilationSmokeTest.kt b/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/IncrementalCompilationSmokeTest.kt
index ce54188..2d0a861 100644
--- a/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/IncrementalCompilationSmokeTest.kt
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/IncrementalCompilationSmokeTest.kt
@@ -36,6 +36,42 @@
         runMultiModuleTest(strategyConfig, useTrackedModules = true)
     }
 
+    @DisplayName("IC works with a mixed Java+Kotlin project via our internal machinery, similarly to Maven")
+    @DefaultStrategyAgnosticCompilationTest
+    @TestMetadata("kotlin-java-mixed")
+    fun mixedModuleInternallyTracked(strategyConfig: CompilerExecutionStrategyConfiguration) {
+        val kotlinToolchain = strategyConfig.first
+        Assumptions.assumeTrue(
+            KotlinToolingVersion(kotlinToolchain.getCompilerVersion()) >= KotlinToolingVersion(2, 1, 20, "Beta1"),
+            "Internal tracking is supported only since Kotlin 2.1.20-Beta1: KT-70556, the current version is ${kotlinToolchain.getCompilerVersion()}"
+        )
+        runMixedModuleTest(strategyConfig, useTrackedModules = true)
+    }
+
+    @DisplayName("IC works with a mixed Java+Kotlin project with the externally tracked changes, similarly to Gradle")
+    @DefaultStrategyAgnosticCompilationTest
+    @TestMetadata("kotlin-java-mixed")
+    fun mixedModuleExternallyTracked(strategyConfig: CompilerExecutionStrategyConfiguration) {
+        runMixedModuleTest(strategyConfig, useTrackedModules = false)
+    }
+
+    private fun runMixedModuleTest(strategyConfig: CompilerExecutionStrategyConfiguration, useTrackedModules: Boolean) {
+        scenario(strategyConfig) {
+            val module1 = if (useTrackedModules) {
+                trackedModule("kotlin-java-mixed")
+            } else {
+                module("kotlin-java-mixed")
+            }
+
+            module1.replaceFileWithVersion("main.kt", "add-argument")
+            module1.replaceFileWithVersion("apkg/AClass.java", "add-argument")
+            module1.compile { module, scenarioModule ->
+                assertCompiledSources(module, "main.kt", "bpkg/BClass.kt")
+                assertOutputs(module, "bpkg/MainKt.class", "bpkg/BClass.class")
+            }
+        }
+    }
+
     private fun runMultiModuleTest(strategyConfig: CompilerExecutionStrategyConfiguration, useTrackedModules: Boolean) {
         scenario(strategyConfig) {
             val module1 = if (useTrackedModules) {
diff --git a/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/NonIncrementalCompilationSmokeTest.kt b/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/NonIncrementalCompilationSmokeTest.kt
index 32d49837..4356874 100644
--- a/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/NonIncrementalCompilationSmokeTest.kt
+++ b/compiler/build-tools/kotlin-build-tools-api-tests/src/testCompatibility/kotlin/NonIncrementalCompilationSmokeTest.kt
@@ -35,6 +35,19 @@
         }
     }
 
+    @DisplayName("Non-incremental compilation produces only expected outputs with mixed java+kotlin setup")
+    @DefaultStrategyAgnosticCompilationTest
+    @TestMetadata("kotlin-java-mixed")
+    fun mixedJavaKotlin(strategyConfig: CompilerExecutionStrategyConfiguration) {
+        project(strategyConfig) {
+            val module1 = module("kotlin-java-mixed")
+
+            module1.compile { module ->
+                assertOutputs(module, "bpkg/MainKt.class", "bpkg/BClass.class")
+            }
+        }
+    }
+
     @OptIn(ExperimentalCompilerArgument::class, RemovedCompilerArgument::class)
     @DisplayName("Using removed argument throws on unsupported compiler versions")
     @DefaultStrategyAgnosticCompilationTest
diff --git a/compiler/build-tools/kotlin-build-tools-compat/src/main/kotlin/KotlinToolchainV1Adapter.kt b/compiler/build-tools/kotlin-build-tools-compat/src/main/kotlin/KotlinToolchainV1Adapter.kt
index 4d88629..8063685 100644
--- a/compiler/build-tools/kotlin-build-tools-compat/src/main/kotlin/KotlinToolchainV1Adapter.kt
+++ b/compiler/build-tools/kotlin-build-tools-compat/src/main/kotlin/KotlinToolchainV1Adapter.kt
@@ -26,6 +26,7 @@
 import org.jetbrains.kotlin.buildtools.internal.compat.JvmCompilationOperationV1Adapter.JvmSnapshotBasedIncrementalCompilationOptionsV1Adapter.Companion.ROOT_PROJECT_DIR
 import org.jetbrains.kotlin.buildtools.internal.compat.JvmCompilationOperationV1Adapter.JvmSnapshotBasedIncrementalCompilationOptionsV1Adapter.Companion.USE_FIR_RUNNER
 import org.jetbrains.kotlin.buildtools.internal.compat.arguments.JvmCompilerArgumentsImpl
+import org.jetbrains.kotlin.incremental.isJavaFile
 import java.nio.file.Path
 import kotlin.io.path.absolutePathString
 import kotlin.time.Duration
@@ -185,7 +186,7 @@
             compilerArguments.toArgumentStrings().fixForFirCheck() + listOf(
                 "-d",
                 destinationDirectory.absolutePathString()
-            )
+            ) + kotlinSources.filter { it.toFile().isJavaFile() }.map { it.absolutePathString() }
         )
     }