diff --git a/platform/lang-impl/src/com/intellij/openapi/module/impl/moduleFileListener.kt b/platform/lang-impl/src/com/intellij/openapi/module/impl/moduleFileListener.kt index 74c5d5b1c945..3a65f970d09f 100644 --- a/platform/lang-impl/src/com/intellij/openapi/module/impl/moduleFileListener.kt +++ b/platform/lang-impl/src/com/intellij/openapi/module/impl/moduleFileListener.kt @@ -18,6 +18,8 @@ package com.intellij.openapi.module.impl import com.intellij.openapi.components.StateStorage import com.intellij.openapi.components.stateStore import com.intellij.openapi.module.Module +import com.intellij.openapi.roots.impl.ModuleRootManagerImpl +import com.intellij.openapi.roots.impl.ProjectRootManagerComponent import com.intellij.openapi.roots.impl.storage.ClasspathStorage import com.intellij.openapi.util.io.FileUtil import com.intellij.openapi.vfs.VirtualFile @@ -25,6 +27,8 @@ import com.intellij.openapi.vfs.newvfs.BulkFileListener import com.intellij.openapi.vfs.newvfs.events.VFileEvent import com.intellij.openapi.vfs.newvfs.events.VFileMoveEvent import com.intellij.openapi.vfs.newvfs.events.VFilePropertyChangeEvent +import com.intellij.project.rootManager +import gnu.trove.THashSet /** * Why this class is required if we have StorageVirtualFileTracker? @@ -50,7 +54,7 @@ internal class ModuleFileListener(private val moduleManager: ModuleManagerCompon val parentPath = event.file.parent?.path ?: return var someModulePathIsChanged = false for (module in moduleManager.modules) { - if (!module.isLoaded) { + if (!module.isLoaded || module.isDisposed) { continue } @@ -72,10 +76,13 @@ internal class ModuleFileListener(private val moduleManager: ModuleManagerCompon return } + val roots = THashSet() + val dirName = event.file.nameSequence val ancestorPath = "${event.oldParent.path}/$dirName" + val newAncestorPath = "${event.newParent.path}/$dirName" for (module in moduleManager.modules) { - if (!module.isLoaded) { + if (!module.isLoaded || module.isDisposed) { continue } @@ -83,6 +90,18 @@ internal class ModuleFileListener(private val moduleManager: ModuleManagerCompon if (FileUtil.isAncestor(ancestorPath, moduleFilePath, true)) { setModuleFilePath(module, "${event.newParent.path}/$dirName/${FileUtil.getRelativePath(ancestorPath, moduleFilePath, '/')}") } + + // https://youtrack.jetbrains.com/issue/IDEA-168933 + roots.clear() + + val moduleRootManager = module.rootManager as? ModuleRootManagerImpl ?: continue + ProjectRootManagerComponent.addRootsToTrack(moduleRootManager.contentRootUrls, roots, roots) + ProjectRootManagerComponent.addRootsToTrack(moduleRootManager.sourceRootUrls, roots, roots) + + if (roots.contains(newAncestorPath)) { + moduleRootManager.stateChanged() + break + } } } diff --git a/platform/lang-impl/src/com/intellij/openapi/roots/impl/ProjectRootManagerComponent.java b/platform/lang-impl/src/com/intellij/openapi/roots/impl/ProjectRootManagerComponent.java index 42485a9897e3..8d6908663583 100644 --- a/platform/lang-impl/src/com/intellij/openapi/roots/impl/ProjectRootManagerComponent.java +++ b/platform/lang-impl/src/com/intellij/openapi/roots/impl/ProjectRootManagerComponent.java @@ -263,7 +263,7 @@ public class ProjectRootManagerComponent extends ProjectRootManagerImpl implemen return Pair.create(recursive, flat); } - private static void addRootsToTrack(final String[] urls, final Collection recursive, final Collection flat) { + public static void addRootsToTrack(final String[] urls, final Collection recursive, final Collection flat) { for (String url : urls) { if (url != null) { final String protocol = VirtualFileManager.extractProtocol(url); diff --git a/platform/projectModel-impl/src/com/intellij/openapi/roots/impl/ModuleRootManagerImpl.java b/platform/projectModel-impl/src/com/intellij/openapi/roots/impl/ModuleRootManagerImpl.java index 569cfda2ad94..72fdbf0487b0 100644 --- a/platform/projectModel-impl/src/com/intellij/openapi/roots/impl/ModuleRootManagerImpl.java +++ b/platform/projectModel-impl/src/com/intellij/openapi/roots/impl/ModuleRootManagerImpl.java @@ -368,7 +368,7 @@ public class ModuleRootManagerImpl extends ModuleRootManager implements Disposab } } - void stateChanged() { + public void stateChanged() { if (Registry.is("store.track.module.root.manager.changes", false)) { LOG.error("ModelRootManager state changed"); }