gradle.kts, minor: move isInAffectedGradleProjectFiles inside GradleBuildRootsManager

This commit is contained in:
Sergey Rostov
2020-05-07 14:48:49 +03:00
parent b2729f977a
commit 06e43027cf
9 changed files with 64 additions and 37 deletions
@@ -9,12 +9,16 @@ import com.intellij.openapi.externalSystem.service.project.autoimport.AsyncFileC
import com.intellij.openapi.vfs.VirtualFile import com.intellij.openapi.vfs.VirtualFile
import com.intellij.openapi.vfs.VirtualFileManager import com.intellij.openapi.vfs.VirtualFileManager
import com.intellij.openapi.vfs.newvfs.events.VFileEvent import com.intellij.openapi.vfs.newvfs.events.VFileEvent
import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager
fun addVfsListener(watcher: GradleScriptListener) { fun addVfsListener(
watcher: GradleScriptListener,
buildRootsManager: GradleBuildRootsManager
) {
VirtualFileManager.getInstance().addAsyncFileListener( VirtualFileManager.getInstance().addAsyncFileListener(
object : AsyncFileChangeListenerBase() { object : AsyncFileChangeListenerBase() {
override fun isRelevant(path: String): Boolean { override fun isRelevant(path: String): Boolean {
return isInAffectedGradleProjectFiles(watcher.project, path) return buildRootsManager.maybeAffectedGradleProjectFile(path)
} }
override fun updateFile(file: VirtualFile, event: VFileEvent) { override fun updateFile(file: VirtualFile, event: VFileEvent) {
@@ -9,8 +9,12 @@ import com.intellij.openapi.vfs.VirtualFileManager
import com.intellij.openapi.vfs.newvfs.BulkFileListener import com.intellij.openapi.vfs.newvfs.BulkFileListener
import com.intellij.openapi.vfs.newvfs.events.VFileEvent import com.intellij.openapi.vfs.newvfs.events.VFileEvent
import com.intellij.util.concurrency.SequentialTaskExecutor import com.intellij.util.concurrency.SequentialTaskExecutor
import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager
fun addVfsListener(watcher: GradleScriptListener) { fun addVfsListener(
watcher: GradleScriptListener,
buildRootsManager: GradleBuildRootsManager
) {
watcher.project.messageBus.connect().subscribe( watcher.project.messageBus.connect().subscribe(
VirtualFileManager.VFS_CHANGES, VirtualFileManager.VFS_CHANGES,
object : BulkFileListener { object : BulkFileListener {
@@ -22,7 +26,7 @@ fun addVfsListener(watcher: GradleScriptListener) {
if (watcher.project.isDisposed) return@Runnable if (watcher.project.isDisposed) return@Runnable
for (event in events) { for (event in events) {
val file = event.file ?: continue val file = event.file ?: continue
if (isInAffectedGradleProjectFiles(watcher.project, event.path)) { if (buildRootsManager.maybeAffectedGradleProjectFile(event.path)) {
watcher.fileChanged(event.path, file.timeStamp) watcher.fileChanged(event.path, file.timeStamp)
} }
} }
@@ -9,12 +9,16 @@ import com.intellij.openapi.externalSystem.autoimport.AsyncFileChangeListenerBas
import com.intellij.openapi.vfs.VirtualFile import com.intellij.openapi.vfs.VirtualFile
import com.intellij.openapi.vfs.VirtualFileManager import com.intellij.openapi.vfs.VirtualFileManager
import com.intellij.openapi.vfs.newvfs.events.VFileEvent import com.intellij.openapi.vfs.newvfs.events.VFileEvent
import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager
fun addVfsListener(watcher: GradleScriptListener) { fun addVfsListener(
watcher: GradleScriptListener,
buildRootsManager: GradleBuildRootsManager
) {
VirtualFileManager.getInstance().addAsyncFileListener( VirtualFileManager.getInstance().addAsyncFileListener(
object : AsyncFileChangeListenerBase() { object : AsyncFileChangeListenerBase() {
override fun isRelevant(path: String): Boolean { override fun isRelevant(path: String): Boolean {
return isInAffectedGradleProjectFiles(watcher.project, path) return buildRootsManager.maybeAffectedGradleProjectFile(path)
} }
override fun updateFile(file: VirtualFile, event: VFileEvent) { override fun updateFile(file: VirtualFile, event: VFileEvent) {
@@ -18,7 +18,7 @@ class GradleScriptListener(project: Project) : ScriptChangeListener(project) {
init { init {
// listen changes using VFS events, including gradle-configuration related files // listen changes using VFS events, including gradle-configuration related files
addVfsListener(this) addVfsListener(this, buildRootsManager)
} }
fun fileChanged(filePath: String, ts: Long) = fun fileChanged(filePath: String, ts: Long) =
@@ -17,7 +17,7 @@ import org.jetbrains.kotlin.idea.core.script.configuration.loader.ScriptConfigur
import org.jetbrains.kotlin.idea.core.util.EDT import org.jetbrains.kotlin.idea.core.util.EDT
import org.jetbrains.kotlin.idea.scripting.gradle.getGradleScriptInputsStamp import org.jetbrains.kotlin.idea.scripting.gradle.getGradleScriptInputsStamp
import org.jetbrains.kotlin.idea.scripting.gradle.isGradleKotlinScript import org.jetbrains.kotlin.idea.scripting.gradle.isGradleKotlinScript
import org.jetbrains.kotlin.idea.scripting.gradle.isInAffectedGradleProjectFiles import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager
import org.jetbrains.kotlin.idea.scripting.gradle.useScriptConfigurationFromImportOnly import org.jetbrains.kotlin.idea.scripting.gradle.useScriptConfigurationFromImportOnly
import org.jetbrains.kotlin.idea.util.application.runWriteAction import org.jetbrains.kotlin.idea.util.application.runWriteAction
import org.jetbrains.kotlin.psi.KtFile import org.jetbrains.kotlin.psi.KtFile
@@ -58,6 +58,8 @@ class GradleLegacyScriptConfigurationLoaderForOutOfProjectScripts(project: Proje
* TODO(gradle6): remove * TODO(gradle6): remove
*/ */
class GradleLegacyScriptConfigurationLoader(project: Project) : DefaultScriptConfigurationLoader(project) { class GradleLegacyScriptConfigurationLoader(project: Project) : DefaultScriptConfigurationLoader(project) {
private val buildRootsManager = GradleBuildRootsManager.getInstance(project)
override fun shouldRunInBackground(scriptDefinition: ScriptDefinition): Boolean { override fun shouldRunInBackground(scriptDefinition: ScriptDefinition): Boolean {
return if (useScriptConfigurationFromImportOnly()) false else super.shouldRunInBackground(scriptDefinition) return if (useScriptConfigurationFromImportOnly()) false else super.shouldRunInBackground(scriptDefinition)
} }
@@ -78,7 +80,7 @@ class GradleLegacyScriptConfigurationLoader(project: Project) : DefaultScriptCon
return true return true
} }
if (!isInAffectedGradleProjectFiles(ktFile.project, vFile.path)) { if (!buildRootsManager.isAffectedGradleProjectFile(vFile.path)) {
ScriptConfigurationManager.markFileWithManualConfigurationLoading(vFile) ScriptConfigurationManager.markFileWithManualConfigurationLoading(vFile)
return true return true
} }
@@ -9,13 +9,13 @@ import com.intellij.openapi.project.Project
import com.intellij.openapi.vfs.VirtualFile import com.intellij.openapi.vfs.VirtualFile
import org.jetbrains.kotlin.idea.core.script.configuration.listener.ScriptChangeListener import org.jetbrains.kotlin.idea.core.script.configuration.listener.ScriptChangeListener
import org.jetbrains.kotlin.idea.scripting.gradle.isGradleKotlinScript import org.jetbrains.kotlin.idea.scripting.gradle.isGradleKotlinScript
import org.jetbrains.kotlin.idea.scripting.gradle.isInAffectedGradleProjectFiles
import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager import org.jetbrains.kotlin.idea.scripting.gradle.roots.GradleBuildRootsManager
import org.jetbrains.kotlin.idea.scripting.gradle.useScriptConfigurationFromImportOnly
// called from GradleScriptListener // called from GradleScriptListener
// todo(gradle6): remove // todo(gradle6): remove
class GradleLegacyScriptListener(project: Project) : ScriptChangeListener(project) { class GradleLegacyScriptListener(project: Project) : ScriptChangeListener(project) {
private val buildRootsManager = GradleBuildRootsManager.getInstance(project)
override fun isApplicable(vFile: VirtualFile) = override fun isApplicable(vFile: VirtualFile) =
isGradleKotlinScript(vFile) isGradleKotlinScript(vFile)
@@ -26,7 +26,7 @@ class GradleLegacyScriptListener(project: Project) : ScriptChangeListener(projec
checkUpToDate(vFile) checkUpToDate(vFile)
private fun checkUpToDate(vFile: VirtualFile) { private fun checkUpToDate(vFile: VirtualFile) {
if (!isInAffectedGradleProjectFiles(project, vFile.path)) return if (!buildRootsManager.isAffectedGradleProjectFile(vFile.path)) return
val file = getAnalyzableKtFileForScript(vFile) val file = getAnalyzableKtFileForScript(vFile)
if (file != null) { if (file != null) {
@@ -27,7 +27,7 @@ class GradleBuildRootIndex {
} }
@Synchronized @Synchronized
fun getBuildRoot(dir: String) = byWorkingDir[dir] fun getBuildByRootDir(dir: String) = byWorkingDir[dir]
@Synchronized @Synchronized
fun findNearestRoot(path: String): GradleBuildRoot.Linked? { fun findNearestRoot(path: String): GradleBuildRoot.Linked? {
@@ -26,12 +26,12 @@ import org.jetbrains.kotlin.idea.scripting.gradle.*
import org.jetbrains.kotlin.idea.scripting.gradle.importing.KotlinDslGradleBuildSync import org.jetbrains.kotlin.idea.scripting.gradle.importing.KotlinDslGradleBuildSync
import org.jetbrains.kotlin.psi.KtFile import org.jetbrains.kotlin.psi.KtFile
import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstance import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstance
import org.jetbrains.kotlin.utils.addToStdlib.lastIndexOfOrNull
import org.jetbrains.plugins.gradle.config.GradleSettingsListenerAdapter import org.jetbrains.plugins.gradle.config.GradleSettingsListenerAdapter
import org.jetbrains.plugins.gradle.settings.* import org.jetbrains.plugins.gradle.settings.*
import org.jetbrains.plugins.gradle.util.GradleConstants import org.jetbrains.plugins.gradle.util.GradleConstants
import java.io.File import java.io.File
import java.nio.file.Paths import java.nio.file.Paths
import java.util.concurrent.CompletableFuture
import java.util.concurrent.atomic.AtomicBoolean import java.util.concurrent.atomic.AtomicBoolean
/** /**
@@ -119,6 +119,39 @@ class GradleBuildRootsManager(val project: Project) : ScriptingSupport.Provider(
fun findScriptBuildRoot(gradleKtsFile: VirtualFile): ScriptUnderRoot? = fun findScriptBuildRoot(gradleKtsFile: VirtualFile): ScriptUnderRoot? =
findScriptBuildRoot(gradleKtsFile.path) findScriptBuildRoot(gradleKtsFile.path)
/**
* Fast method that can return false positive
*/
fun maybeAffectedGradleProjectFile(filePath: String): Boolean =
filePath.endsWith("/gradle.properties") ||
filePath.endsWith("/gradle.local") ||
filePath.endsWith("/gradle-wrapper.properties") ||
filePath.endsWith("/build.gradle.kts") ||
filePath.endsWith("/settings.gradle.kts") ||
filePath.endsWith("/init.gradle.kts")
fun isAffectedGradleProjectFile(filePath: String): Boolean =
findAffectedFileRoot(filePath) != null
fun fileChanged(filePath: String, ts: Long = System.currentTimeMillis()) {
findAffectedFileRoot(filePath)?.fileChanged(filePath, ts)
}
private fun findAffectedFileRoot(filePath: String): GradleBuildRoot.Linked? {
if (filePath.endsWith("/gradle.properties") ||
filePath.endsWith("/gradle.local")
) {
return roots.getBuildByProjectDir(filePath.substringBeforeLast("/"))
} else if (filePath.endsWith("/gradle-wrapper.properties")) {
val gradleWrapperDirIndex = filePath.lastIndexOfOrNull('/') ?: return null
val gradleDirIndex = filePath.lastIndexOfOrNull('/', gradleWrapperDirIndex) ?: return null
val buildDirIndex = filePath.lastIndexOfOrNull('/', gradleDirIndex) ?: return null
return roots.getBuildByRootDir(filePath.substring(0, buildDirIndex))
}
return findScriptBuildRoot(filePath, searchNearestLegacy = false)?.root as? GradleBuildRoot.Linked
}
private fun findScriptBuildRoot(filePath: String, searchNearestLegacy: Boolean = true): ScriptUnderRoot? { private fun findScriptBuildRoot(filePath: String, searchNearestLegacy: Boolean = true): ScriptUnderRoot? {
if (!filePath.endsWith(".gradle.kts")) return null if (!filePath.endsWith(".gradle.kts")) return null
@@ -151,12 +184,7 @@ class GradleBuildRootsManager(val project: Project) : ScriptingSupport.Provider(
roots.getBuildByProjectDir(localPath) != null roots.getBuildByProjectDir(localPath) != null
fun getBuildRoot(gradleWorkingDir: String) = fun getBuildRoot(gradleWorkingDir: String) =
roots.getBuildRoot(gradleWorkingDir) roots.getBuildByRootDir(gradleWorkingDir)
fun fileChanged(filePath: String, ts: Long = System.currentTimeMillis()) {
val root = findScriptBuildRoot(filePath, searchNearestLegacy = false)?.root as? GradleBuildRoot.Linked
root?.fileChanged(filePath, ts)
}
fun markImportingInProgress(workingDir: String, inProgress: Boolean = true) { fun markImportingInProgress(workingDir: String, inProgress: Boolean = true) {
actualizeBuildRoot(workingDir)?.importing = inProgress actualizeBuildRoot(workingDir)?.importing = inProgress
@@ -167,7 +195,7 @@ class GradleBuildRootsManager(val project: Project) : ScriptingSupport.Provider(
fun update(build: KotlinDslGradleBuildSync) { fun update(build: KotlinDslGradleBuildSync) {
// fast path for linked gradle builds without .gradle.kts support // fast path for linked gradle builds without .gradle.kts support
if (build.models.isEmpty()) { if (build.models.isEmpty()) {
val root = roots.getBuildRoot(build.workingDir) ?: return val root = roots.getBuildByRootDir(build.workingDir) ?: return
if (root is GradleBuildRoot.Imported && root.data.models.isEmpty()) return if (root is GradleBuildRoot.Imported && root.data.models.isEmpty()) return
} }
@@ -256,7 +284,7 @@ class GradleBuildRootsManager(val project: Project) : ScriptingSupport.Provider(
*/ */
private fun actualizeBuildRoot(workingDir: String): GradleBuildRoot.Linked? { private fun actualizeBuildRoot(workingDir: String): GradleBuildRoot.Linked? {
val actualSettings = getGradleProjectSettings(workingDir) val actualSettings = getGradleProjectSettings(workingDir)
val buildRoot = roots.getBuildRoot(workingDir) val buildRoot = roots.getBuildByRootDir(workingDir)
return when { return when {
buildRoot != null -> when { buildRoot != null -> when {
@@ -29,21 +29,6 @@ private val sections = arrayListOf("buildscript", "plugins", "initscript", "plug
fun isGradleKotlinScript(virtualFile: VirtualFile) = virtualFile.name.endsWith(".gradle.kts") fun isGradleKotlinScript(virtualFile: VirtualFile) = virtualFile.name.endsWith(".gradle.kts")
fun isInAffectedGradleProjectFiles(project: Project, filePath: String): Boolean {
if (filePath.endsWith("/gradle.properties")) return true
if (filePath.endsWith("/gradle-wrapper.properties")) return true
if (filePath.endsWith(".gradle") || filePath.endsWith(".gradle.kts")) {
if (ApplicationManager.getApplication().isUnitTestModeWithoutAffectedGradleProjectFilesCheck) {
return true
}
return GradleBuildRootsManager.getInstance(project).isUnderProjectDir(filePath.substringBeforeLast("/"))
}
return false
}
fun getGradleScriptInputsStamp( fun getGradleScriptInputsStamp(
project: Project, project: Project,
file: VirtualFile, file: VirtualFile,