From be2d6d0039ccfeac7caa77189cc19b30e5152fcd Mon Sep 17 00:00:00 2001 From: Vadim Salavatov Date: Wed, 5 Aug 2026 19:05:26 +0200 Subject: [PATCH] [plugins] IJPL-251952 init context: make platform alias compatibility dependencies soft Resolve extracted Core modules added for legacy platform and language alias dependencies against remaining candidates. An extracted module that becomes unavailable no longer excludes the alias consumer. (cherry picked from commit 0cb31bebbc78d65afc7b1a204a04ec1c0792ed2e) GitOrigin-RevId: b7a0e3c1a4fedbe69c77a34582901ef2bd46ebaf --- .../ide/plugins/ProductPluginInitContext.kt | 42 +++++++++---------- .../ide/plugins/PluginDependenciesTest.kt | 33 +++++++++++++++ 2 files changed, 54 insertions(+), 21 deletions(-) diff --git a/platform/core-impl/src/com/intellij/ide/plugins/ProductPluginInitContext.kt b/platform/core-impl/src/com/intellij/ide/plugins/ProductPluginInitContext.kt index 471c0b1365b0..078b5483ac1b 100644 --- a/platform/core-impl/src/com/intellij/ide/plugins/ProductPluginInitContext.kt +++ b/platform/core-impl/src/com/intellij/ide/plugins/ProductPluginInitContext.kt @@ -228,11 +228,6 @@ class ProductPluginInitContext( yield(ref) } } - suspend fun SequenceScope.yieldPlatformAliasCompatibilityDependencies() { - for (contentModuleId in contentModulesExtractedInCorePluginWhichCanBeUsedFromExternalPlugins) { - yieldIfResolves(DependencyRef.of(contentModuleId)) - } - } return sequence { if (descriptor.pluginId != CORE_ID) { yieldIfResolves(DependencyRef.of(CORE_ID)) @@ -307,22 +302,6 @@ class ProductPluginInitContext( } } - if (descriptor !is PluginMainDescriptor || descriptor.pluginId != CORE_ID) { // FIXME violator: DesignedCorePlugin.xml which is xi:included from IdeaPlugin.xml - for (depends in descriptor.pluginDependencies) { - if (depends.subDescriptor != null) { // will be processed when invoked for the sub-descriptor - continue - } - if ((depends.pluginId == PLATFORM_PLUGIN_ALIAS_ID || depends.pluginId == LANG_PLUGIN_ALIAS_ID) && pluginSet.resolvePluginId(depends.pluginId) != null) { - yieldPlatformAliasCompatibilityDependencies() - } - } - } - - if (descriptor is DependsSubDescriptor) { - if ((descriptor.dependsTargetId == PLATFORM_PLUGIN_ALIAS_ID || descriptor.dependsTargetId == LANG_PLUGIN_ALIAS_ID) && pluginSet.resolvePluginId(descriptor.pluginId) != null) { - yieldPlatformAliasCompatibilityDependencies() - } - } } } @@ -345,11 +324,32 @@ class ProductPluginInitContext( yield(ref) } } + suspend fun SequenceScope.yieldPlatformAliasCompatibilityDependencies() { + for (contentModuleId in contentModulesExtractedInCorePluginWhichCanBeUsedFromExternalPlugins) { + yieldIfResolves(DependencyRef.of(contentModuleId)) + } + } if (descriptor is PluginModuleDescriptor && descriptor.pluginId != CORE_ID && isExternalNonBundledPlugin(descriptor)) { for (dependencyRef in externalNonBundledPluginCompatibilityDependencies) { yieldIfResolves(dependencyRef) } } + if (descriptor !is PluginMainDescriptor || descriptor.pluginId != CORE_ID) { // FIXME violator: DesignedCorePlugin.xml which is xi:included from IdeaPlugin.xml + for (depends in descriptor.pluginDependencies) { + if (depends.subDescriptor != null) { // will be processed when invoked for the sub-descriptor + continue + } + if ((depends.pluginId == PLATFORM_PLUGIN_ALIAS_ID || depends.pluginId == LANG_PLUGIN_ALIAS_ID) && remainingCandidates.resolvePluginId(depends.pluginId) != null) { + yieldPlatformAliasCompatibilityDependencies() + } + } + } + + if (descriptor is DependsSubDescriptor) { + if ((descriptor.dependsTargetId == PLATFORM_PLUGIN_ALIAS_ID || descriptor.dependsTargetId == LANG_PLUGIN_ALIAS_ID) && remainingCandidates.resolvePluginId(descriptor.pluginId) != null) { + yieldPlatformAliasCompatibilityDependencies() + } + } } } diff --git a/platform/platform-tests/testSrc/com/intellij/ide/plugins/PluginDependenciesTest.kt b/platform/platform-tests/testSrc/com/intellij/ide/plugins/PluginDependenciesTest.kt index d03514a95f6d..a17b05e9e8c7 100644 --- a/platform/platform-tests/testSrc/com/intellij/ide/plugins/PluginDependenciesTest.kt +++ b/platform/platform-tests/testSrc/com/intellij/ide/plugins/PluginDependenciesTest.kt @@ -1473,6 +1473,39 @@ internal class PluginDependenciesTest { assertThat(withLang).hasExactDirectParentClassloaders(*moduleDescriptors.toTypedArray()) assertThat(withDependencies).hasExactDirectParentClassloaders() } + + @Test + fun `unavailable module extracted from core does not exclude plugin depending on platform alias`() { + plugin("platform.alias.provider") { + vendor = "JetBrains" + pluginAlias("com.intellij.modules.platform") + }.installAt(pluginDirPath) + + plugin("tasks.provider") { + vendor = "JetBrains" + content(namespace = "jetbrains") { + module("intellij.platform.tasks", ModuleLoadingRuleValue.REQUIRED) { + packagePrefix = "intellij.platform.tasks" + moduleVisibility = ModuleVisibilityValue.PUBLIC + dependencies { + module("unavailable.module") + } + } + } + }.installAt(pluginDirPath) + + plugin("consumer") { + vendor = "JetBrains" + depends("com.intellij.modules.platform") + }.installAt(pluginDirPath) + + val pluginSet = buildPluginSet() + + assertThat(pluginSet).hasExactlyEnabledPlugins("consumer", "platform.alias.provider") + assertThat(pluginSet.getEnabledPlugin("consumer")).hasExactDirectParentClassloaders( + pluginSet.getEnabledPlugin("platform.alias.provider") + ) + } } private fun foo() = plugin("foo") {}.installAt(pluginDirPath)