K/N: Clean-up logic for import of K/N projects from Gradle
This commit is contained in:
committed by
Mikhail Glukhikh
parent
dd203830a8
commit
88638ef655
@@ -1,14 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.gradle
|
||||
|
||||
import com.intellij.openapi.project.Project
|
||||
import org.jetbrains.konan.settings.KonanModelProvider
|
||||
import java.nio.file.Path
|
||||
|
||||
class GradleKonanModelProvider : KonanModelProvider {
|
||||
override fun getKonanHome(project: Project): Path? = null
|
||||
}
|
||||
@@ -1,17 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.gradle
|
||||
|
||||
import com.intellij.openapi.project.Project
|
||||
import org.jetbrains.konan.settings.KonanProjectComponent
|
||||
import org.jetbrains.plugins.gradle.settings.GradleSettings
|
||||
|
||||
class GradleKonanProjectComponent(project: Project) : KonanProjectComponent(project) {
|
||||
override fun looksLikeKotlinNativeProject(): Boolean {
|
||||
//TODO not just any gradle project
|
||||
return GradleSettings.getInstance(project).linkedProjectsSettings.isNotEmpty()
|
||||
}
|
||||
}
|
||||
@@ -1,96 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan
|
||||
|
||||
import com.intellij.openapi.application.ApplicationManager
|
||||
import com.intellij.openapi.diagnostic.Logger
|
||||
import com.intellij.openapi.progress.ProgressIndicator
|
||||
import com.intellij.openapi.progress.Task
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.util.SystemProperties.getUserHome
|
||||
import com.intellij.util.io.exists
|
||||
import com.intellij.util.net.IOExceptionDialog
|
||||
import org.jetbrains.konan.settings.KonanProjectComponent
|
||||
import org.jetbrains.kotlin.konan.target.HostManager
|
||||
import org.jetbrains.kotlin.konan.util.DependencyDownloaderHTTPResponseException
|
||||
import org.jetbrains.kotlin.konan.util.DependencyProcessor
|
||||
import org.jetbrains.kotlin.konan.util.DependencySource
|
||||
import java.nio.file.Path
|
||||
import java.nio.file.Paths
|
||||
|
||||
class KotlinNativeToolchain(
|
||||
val version: String,
|
||||
val repoUrl: String
|
||||
) {
|
||||
private val artifactName = "kotlin-native-$KONAN_OS-$version"
|
||||
val baseDir: Path get() = Paths.get("${getUserHome()}/.konan/$artifactName")
|
||||
val konanc: Path get() = baseDir.resolve("bin/konanc")
|
||||
val cinterop: Path get() = baseDir.resolve("bin/cinterop")
|
||||
|
||||
|
||||
fun ensureExists(project: Project) {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread()
|
||||
if (baseDir.exists()) return
|
||||
|
||||
for (attempt in 0..3) {
|
||||
var exception: Throwable? = null
|
||||
object : Task.Modal(project, "Downloading Kotlin/Native $version", false) {
|
||||
override fun run(progress: ProgressIndicator) {
|
||||
DependencyProcessor(
|
||||
baseDir.parent.toFile(),
|
||||
repoUrl,
|
||||
mapOf(artifactName to listOf(DependencySource.Remote.Public)),
|
||||
customProgressCallback = { _, downloaded, total ->
|
||||
progress.fraction = downloaded / maxOf(total, downloaded, 1).toDouble()
|
||||
}
|
||||
).run()
|
||||
ApplicationManager.getApplication().invokeLater {
|
||||
project.getComponent(KonanProjectComponent::class.java).reloadLibraries()
|
||||
}
|
||||
}
|
||||
|
||||
override fun onThrowable(error: Throwable) {
|
||||
exception = error
|
||||
}
|
||||
}.queue()
|
||||
|
||||
val ex = exception
|
||||
val tryAgain = if (ex == null) {
|
||||
false
|
||||
} else {
|
||||
val details = if (ex is DependencyDownloaderHTTPResponseException) {
|
||||
"Server returned ${ex.responseCode} when trying to download ${ex.url}."
|
||||
} else {
|
||||
LOG.error(ex)
|
||||
"Unknown error occurred."
|
||||
}
|
||||
IOExceptionDialog.showErrorDialog(
|
||||
"Failed to download Kotlin/Native",
|
||||
details
|
||||
)
|
||||
}
|
||||
if (!tryAgain) break
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
fun looksLikeBundledToolchain(path: String): Boolean =
|
||||
Paths.get(path).startsWith(Paths.get("${getUserHome()}/.konan/"))
|
||||
|
||||
private val KONAN_OS = HostManager.simpleOsName()
|
||||
|
||||
//todo: fixme
|
||||
private val BUNDLED_VERSION = "0.8" //bundledFile("kotlin-native-version").readText().trim()
|
||||
private val BUILD_DIR = "releases"
|
||||
|
||||
val BUNDLED = KotlinNativeToolchain(
|
||||
version = BUNDLED_VERSION,
|
||||
repoUrl = "https://download.jetbrains.com/kotlin/native/builds/$BUILD_DIR/$BUNDLED_VERSION/$KONAN_OS"
|
||||
)
|
||||
|
||||
private val LOG = Logger.getInstance(KotlinNativeToolchain::class.java)
|
||||
}
|
||||
}
|
||||
@@ -1,24 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan
|
||||
|
||||
import com.intellij.openapi.application.ApplicationManager
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.openapi.startup.StartupActivity
|
||||
import org.jetbrains.konan.settings.KonanProjectComponent
|
||||
|
||||
class SetupKotlinNativeStartupActivity : StartupActivity {
|
||||
override fun runActivity(project: Project) {
|
||||
//todo: looks like without default project component (like disabled Gradle plugin) we will get exception here (that's bad)
|
||||
if (!KonanProjectComponent.getInstance(project).looksLikeKotlinNativeProject()) return
|
||||
ensureKotlinNativeExists(project)
|
||||
}
|
||||
|
||||
private fun ensureKotlinNativeExists(project: Project) {
|
||||
ApplicationManager.getApplication().assertIsDispatchThread()
|
||||
KotlinNativeToolchain.BUNDLED.ensureExists(project)
|
||||
}
|
||||
}
|
||||
@@ -1,25 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.settings
|
||||
|
||||
import org.jetbrains.kotlin.konan.target.CompilerOutputKind
|
||||
import org.jetbrains.kotlin.konan.target.CompilerOutputKind.*
|
||||
import org.jetbrains.kotlin.konan.target.KonanTarget
|
||||
import java.nio.file.Path
|
||||
|
||||
data class KonanArtifact(
|
||||
val targetName: String,
|
||||
val moduleName: String,
|
||||
val type: CompilerOutputKind,
|
||||
val target: KonanTarget?,
|
||||
val libraryDependencies: List<String>,
|
||||
val sources: List<Path>,
|
||||
val output: Path
|
||||
)
|
||||
|
||||
val CompilerOutputKind.isLibrary: Boolean get() = this == LIBRARY || this == DYNAMIC || this == STATIC || this == FRAMEWORK
|
||||
val CompilerOutputKind.isExecutable: Boolean get() = this == PROGRAM
|
||||
val CompilerOutputKind.isTest: Boolean get() = false //TODO
|
||||
@@ -1,25 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.settings;
|
||||
|
||||
import com.intellij.openapi.extensions.ExtensionPointName;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.util.messages.Topic;
|
||||
import org.jetbrains.annotations.ApiStatus;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.nio.file.Path;
|
||||
|
||||
@ApiStatus.Experimental
|
||||
public interface KonanModelProvider {
|
||||
Topic<Runnable> RELOAD_TOPIC = new Topic<>("Kotlin/Native Project Model Updater", Runnable.class);
|
||||
|
||||
ExtensionPointName<KonanModelProvider> EP_NAME = ExtensionPointName.create("org.jetbrains.kotlin.native.konanModelProvider");
|
||||
|
||||
@Nullable
|
||||
Path getKonanHome(@NotNull Project project);
|
||||
}
|
||||
@@ -1,55 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.settings
|
||||
|
||||
import com.intellij.openapi.components.ProjectComponent
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.util.io.exists
|
||||
import com.intellij.util.io.isDirectory
|
||||
import org.jetbrains.konan.KotlinNativeToolchain
|
||||
import org.jetbrains.kotlin.konan.library.*
|
||||
import org.jetbrains.kotlin.konan.target.HostManager
|
||||
import org.jetbrains.kotlin.konan.target.KonanTarget
|
||||
import java.nio.file.Files
|
||||
import java.nio.file.Path
|
||||
import java.util.stream.Collectors
|
||||
|
||||
open class KonanPaths(protected val project: Project) : ProjectComponent {
|
||||
companion object {
|
||||
fun getInstance(project: Project): KonanPaths = project.getComponent(KonanPaths::class.java)
|
||||
|
||||
fun bundledKonanDist(): Path = KotlinNativeToolchain.BUNDLED.baseDir
|
||||
}
|
||||
|
||||
override fun getComponentName() = "Kotlin/Native Compiler Paths"
|
||||
|
||||
fun konanStdlib(): Path? = konanDist()?.resolve(konanCommonLibraryPath(KONAN_STDLIB_NAME))
|
||||
|
||||
open fun konanDist(): Path? {
|
||||
for (provider in KonanModelProvider.EP_NAME.extensions) {
|
||||
provider.getKonanHome(project)?.existing()?.let { return it }
|
||||
}
|
||||
return bundledKonanDist()
|
||||
}
|
||||
|
||||
open fun libraryPaths(): Set<Path> = emptySet()
|
||||
|
||||
fun konanPlatformLibraries(): List<Path> {
|
||||
|
||||
val resolvedTargetName = HostManager.resolveAlias(target().name)
|
||||
val klibPath =
|
||||
konanDist()?.resolve(konanSpecificPlatformLibrariesPath(resolvedTargetName))?.existing() ?: return emptyList()
|
||||
|
||||
return Files.walk(klibPath, 1).filter {
|
||||
it.isDirectory() && it.fileName.toString() != KONAN_STDLIB_NAME && it != klibPath
|
||||
}.collect(Collectors.toList())
|
||||
}
|
||||
|
||||
//todo: this is wrong, we are not allowing multiple targets in project
|
||||
open fun target(): KonanTarget = HostManager.host
|
||||
}
|
||||
|
||||
private fun Path.existing(): Path? = takeIf { exists() }
|
||||
@@ -1,64 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2018 JetBrains s.r.o. 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.konan.settings
|
||||
|
||||
import com.intellij.openapi.application.ApplicationManager
|
||||
import com.intellij.openapi.application.runWriteAction
|
||||
import com.intellij.openapi.components.ProjectComponent
|
||||
import com.intellij.openapi.module.ModuleManager
|
||||
import com.intellij.openapi.project.Project
|
||||
import com.intellij.openapi.roots.ModuleRootManager
|
||||
import com.intellij.openapi.roots.OrderRootType
|
||||
import com.intellij.openapi.roots.libraries.LibraryTable
|
||||
import com.intellij.openapi.vfs.*
|
||||
import org.jetbrains.konan.KotlinNativeToolchain
|
||||
import org.jetbrains.konan.settings.KonanModelProvider.RELOAD_TOPIC
|
||||
import org.jetbrains.kotlin.utils.addIfNotNull
|
||||
import java.nio.file.Path
|
||||
|
||||
abstract class KonanProjectComponent(val project: Project) : ProjectComponent {
|
||||
companion object {
|
||||
fun getInstance(project: Project): KonanProjectComponent = project.getComponent(KonanProjectComponent::class.java)
|
||||
}
|
||||
|
||||
protected var libraryPaths: Set<String> = emptySet()
|
||||
|
||||
override fun getComponentName(): String = "Kotlin/Native Project Component"
|
||||
|
||||
override fun projectOpened() {
|
||||
VirtualFileManager.getInstance().addVirtualFileListener(object : VirtualFileListener {
|
||||
override fun fileCreated(event: VirtualFileEvent) {
|
||||
val filePath = event.file.path
|
||||
if (libraryPaths.contains(filePath)) reloadLibraries()
|
||||
}
|
||||
}, project)
|
||||
|
||||
val connection = project.messageBus.connect(project)
|
||||
connection.subscribe(RELOAD_TOPIC, Runnable {
|
||||
ApplicationManager.getApplication().invokeLater {
|
||||
KotlinNativeToolchain.BUNDLED.ensureExists(project)
|
||||
reloadLibraries()
|
||||
}
|
||||
})
|
||||
|
||||
if (looksLikeKotlinNativeProject()) {
|
||||
reloadLibraries()
|
||||
}
|
||||
}
|
||||
|
||||
open fun reloadLibraries(): Unit = synchronized(this) {
|
||||
}
|
||||
|
||||
protected open fun collectLibraryPaths(): MutableSet<Path> {
|
||||
val konanPaths = KonanPaths.getInstance(project)
|
||||
return mutableSetOf<Path>().apply {
|
||||
addIfNotNull(konanPaths.konanStdlib())
|
||||
addAll(konanPaths.konanPlatformLibraries())
|
||||
}
|
||||
}
|
||||
|
||||
abstract fun looksLikeKotlinNativeProject(): Boolean
|
||||
}
|
||||
@@ -17,15 +17,5 @@
|
||||
<implementation-class>org.jetbrains.konan.gradle.internal.KotlinNativeIdeInitializer</implementation-class>
|
||||
</component>
|
||||
</application-components>
|
||||
|
||||
<project-components>
|
||||
<component>
|
||||
<interface-class>org.jetbrains.konan.settings.KonanProjectComponent</interface-class>
|
||||
<implementation-class>org.jetbrains.konan.gradle.GradleKonanProjectComponent</implementation-class>
|
||||
</component>
|
||||
</project-components>
|
||||
|
||||
<extensions defaultExtensionNs="org.jetbrains.kotlin.native">
|
||||
<konanModelProvider implementation="org.jetbrains.konan.gradle.GradleKonanModelProvider"/>
|
||||
</extensions>
|
||||
<!-- /NATIVE PART -->
|
||||
</idea-plugin>
|
||||
|
||||
@@ -8,18 +8,7 @@
|
||||
</component>
|
||||
</application-components>
|
||||
|
||||
<project-components>
|
||||
<component>
|
||||
<implementation-class>org.jetbrains.konan.settings.KonanPaths</implementation-class>
|
||||
</component>
|
||||
</project-components>
|
||||
|
||||
<extensionPoints>
|
||||
<extensionPoint qualifiedName="org.jetbrains.kotlin.native.konanModelProvider" interface="org.jetbrains.konan.settings.KonanModelProvider"/>
|
||||
</extensionPoints>
|
||||
|
||||
<extensions defaultExtensionNs="com.intellij">
|
||||
<postStartupActivity implementation="org.jetbrains.konan.SetupKotlinNativeStartupActivity"/>
|
||||
<psi.classFileDecompiler implementation="org.jetbrains.konan.analyser.index.KonanMetadataDecompiler"/>
|
||||
|
||||
<fileType.fileViewProviderFactory filetype="KNM"
|
||||
@@ -32,7 +21,6 @@
|
||||
|
||||
<extensions defaultExtensionNs="org.jetbrains.kotlin">
|
||||
<binaryExtension implementation="org.jetbrains.konan.analyser.index.KonanMetaBinary"/>
|
||||
<!--<idePlatformSupport implementation="org.jetbrains.konan.analyser.KonanPlatformSupport" order="first"/>-->
|
||||
<idePlatformKind implementation="org.jetbrains.kotlin.ide.konan.NativeIdePlatformKind"/>
|
||||
<idePlatformKindTooling implementation="org.jetbrains.kotlin.ide.konan.NativeIdePlatformKindTooling"/>
|
||||
<idePlatformKindResolution implementation="org.jetbrains.kotlin.ide.konan.NativePlatformKindResolution"/>
|
||||
|
||||
Reference in New Issue
Block a user