Skip to content

Commit 4ea4423

Browse files
Kordyjanzarechenskiy
authored andcommitted
Adds support for gradle projects with multiple modules
1 parent ea398c3 commit 4ea4423

File tree

4 files changed

+64
-32
lines changed

4 files changed

+64
-32
lines changed

kotlin-eclipse-core/src/org/jetbrains/kotlin/core/filesystem/KotlinLightClassManager.java

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,13 @@
1616
import org.eclipse.core.resources.IFile;
1717
import org.eclipse.core.resources.IFolder;
1818
import org.eclipse.core.resources.IProject;
19-
import org.eclipse.core.resources.IResource;
2019
import org.eclipse.core.resources.ResourcesPlugin;
2120
import org.eclipse.core.resources.WorkspaceJob;
22-
import org.eclipse.core.runtime.*;
21+
import org.eclipse.core.runtime.CoreException;
22+
import org.eclipse.core.runtime.IPath;
23+
import org.eclipse.core.runtime.IProgressMonitor;
24+
import org.eclipse.core.runtime.IStatus;
25+
import org.eclipse.core.runtime.Path;
2326
import org.eclipse.jdt.internal.core.util.LRUCache;
2427
import org.jetbrains.annotations.NotNull;
2528
import org.jetbrains.annotations.Nullable;
@@ -44,8 +47,6 @@
4447
import com.intellij.psi.PsiElement;
4548
import com.intellij.psi.util.PsiTreeUtil;
4649

47-
import kotlin.jvm.functions.Function1;
48-
4950
public class KotlinLightClassManager {
5051
private static final int LIGHT_CLASSES_CACHE_SIZE = 300;
5152

@@ -112,8 +113,7 @@ public void updateLightClasses(@NotNull Set<IFile> affectedFiles, Boolean resour
112113
if (lightClassIFile == null) continue;
113114

114115
LightClassFile lightClassFile = new LightClassFile(lightClassIFile);
115-
116-
createParentDirsFor(lightClassFile);
116+
117117
if (!lightClassFile.exists()) {
118118
toCreate.add(lightClassFile);
119119
}
@@ -147,6 +147,7 @@ public IStatus runInWorkspace(IProgressMonitor monitor) {
147147

148148
private void updateLightClasses(List<LightClassFile> toCreate, List<LightClassFile> toRemove) {
149149
for (LightClassFile lightClassFile: toCreate) {
150+
createParentDirsFor(lightClassFile);
150151
lightClassFile.createIfNotExists();
151152
}
152153
for (LightClassFile lightClassFile: toRemove) {
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
package org.jetbrains.kotlin.gradle.model
2+
3+
import java.io.Serializable
4+
5+
interface GradleMultiProjectForEclipse : Serializable {
6+
operator fun get(name: String): GradleProjectForEclipse?
7+
}
8+
9+
class GradleMultiProjectForEclipseImpl(
10+
private val subprojects: Map<String, GradleProjectForEclipse>
11+
) : GradleMultiProjectForEclipse {
12+
override fun get(name: String) = subprojects[name]
13+
}

kotlin-eclipse-gradle/scripts/init.gradle.kts

Lines changed: 32 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ import org.gradle.tooling.provider.model.ToolingModelBuilder
55
import org.gradle.tooling.provider.model.ToolingModelBuilderRegistry
66
import org.jetbrains.kotlin.gradle.model.GradleProjectForEclipse
77
import org.jetbrains.kotlin.gradle.model.GradleProjectForEclipseImpl
8+
import org.jetbrains.kotlin.gradle.model.GradleMultiProjectForEclipse
9+
import org.jetbrains.kotlin.gradle.model.GradleMultiProjectForEclipseImpl
810
import org.jetbrains.kotlin.gradle.model.NoKotlinProject
911
import org.jetbrains.kotlin.gradle.model.CompilerPluginConfig
1012
import org.jetbrains.kotlin.gradle.model.AllOpen
@@ -27,28 +29,36 @@ allprojects {
2729
apply<GradleProjectForEclipseInstaller>()
2830
}
2931

30-
class GradleProjectForEclipseInstaller @Inject constructor(val registry: ToolingModelBuilderRegistry) : Plugin<Project> {
32+
class GradleProjectForEclipseInstaller @Inject constructor(val registry: ToolingModelBuilderRegistry) :
33+
Plugin<Project> {
3134
override fun apply(project: Project) {
3235
registry.register(GradleProjectForEclipseBuilder())
3336
}
3437
}
3538

3639
class GradleProjectForEclipseBuilder() : ToolingModelBuilder {
37-
override fun canBuild(modelName: String) = (modelName == GradleProjectForEclipse::class.qualifiedName)
38-
39-
override fun buildAll(modelName: String, project: Project): Any {
40-
val task = project.tasks.findByName("compileKotlin")
41-
42-
return task?.dynamicCall("kotlinOptions")?.run {
43-
GradleProjectForEclipseImpl(
44-
project.findProperty("kotlin.code.style") as? String,
45-
property("apiVersion"),
46-
property("languageVersion"),
47-
property("jvmTarget"),
48-
collectPlugins(project)
49-
)
50-
} ?: return NoKotlinProject
51-
}
40+
41+
override fun canBuild(modelName: String) = (modelName == GradleMultiProjectForEclipse::class.qualifiedName)
42+
43+
override fun buildAll(modelName: String, project: Project): Any =
44+
GradleMultiProjectForEclipseImpl(process(project).toMap())
45+
46+
private fun process(project: Project): List<Pair<String, GradleProjectForEclipse>> =
47+
project.childProjects.values.flatMap(::process) +
48+
(project.name to buildForSubproject(project))
49+
50+
private fun buildForSubproject(project: Project): GradleProjectForEclipse =
51+
project.tasks.findByName("compileKotlin")
52+
?.dynamicCall("kotlinOptions")
53+
?.run {
54+
GradleProjectForEclipseImpl(
55+
project.findProperty("kotlin.code.style") as? String,
56+
property("apiVersion"),
57+
property("languageVersion"),
58+
property("jvmTarget"),
59+
collectPlugins(project)
60+
)
61+
} ?: NoKotlinProject
5262

5363
private fun collectPlugins(project: Project): List<CompilerPluginConfig> {
5464
val result = arrayListOf<CompilerPluginConfig>()
@@ -74,16 +84,16 @@ class GradleProjectForEclipseBuilder() : ToolingModelBuilder {
7484
it.dynamicCall("myPresets") as List<String>
7585
)
7686
}?.also { result += it }
77-
87+
7888
return result
7989
}
80-
90+
8191
// We need this method, because there is no way for us to get here classes that are added to classpath alongside
82-
// the kotlin gradle plugin. Even if we add them to the classpath of this initscript, they will have different
83-
// classloader.
92+
// the kotlin gradle plugin. Even if we add them to the classpath of this initscript, they will have different
93+
// classloader.
8494
fun Any.dynamicCall(name: String, vararg args: Any?): Any? =
8595
this::class.members.first { it.name == name && it.parameters.size == args.size + 1 }
86-
.call(this, *args)
87-
96+
.call(this, *args)
97+
8898
fun Any.property(name: String): String? = dynamicCall(name) as? String
8999
}

kotlin-eclipse-gradle/src/org/jetbrains/kotlin/gradle/configurator/KotlinProjectConfigurator.kt

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -16,21 +16,29 @@ import org.jetbrains.kotlin.core.preferences.KotlinProperties
1616
import org.jetbrains.kotlin.core.utils.ProjectUtils
1717
import org.jetbrains.kotlin.gradle.model.GradleProjectForEclipse
1818
import org.jetbrains.kotlin.core.log.KotlinLogger
19+
import org.jetbrains.kotlin.gradle.model.GradleMultiProjectForEclipse
1920

2021
class KotlinProjectConfigurator : ProjectConfigurator {
2122

22-
lateinit var model: GradleProjectForEclipse
23+
lateinit var multiModel: GradleMultiProjectForEclipse
2324

2425
override fun init(context: InitializationContext, monitor: IProgressMonitor) {
2526
context.gradleBuild.withConnection({
26-
model = it.getModel(GradleProjectForEclipse::class.java)
27+
multiModel = it.getModel(GradleMultiProjectForEclipse::class.java)
2728
}, monitor)
2829
}
2930

3031
override fun configure(context: ProjectContext, monitor: IProgressMonitor) {
31-
if (!::model.isInitialized || !model.isKotlinProject) return
32-
3332
val project = context.project
33+
34+
if (!::multiModel.isInitialized) return
35+
val model = multiModel[project.name]
36+
if (model == null || !model.isKotlinProject) {
37+
// Kotlin nature may left in .project file after editing out kotlin plugin from gradle buildfile.
38+
// This leads to nasty bugs so we have to unconfigure project.
39+
unconfigure(context, monitor)
40+
return
41+
}
3442

3543
KotlinNature.addNature(project)
3644
if (!ProjectUtils.hasKotlinRuntime(project)) {

0 commit comments

Comments
 (0)