From e02c4cd3e62e96d487501003ffb80d6b8b52afcf Mon Sep 17 00:00:00 2001 From: Vladimir Krivosheev Date: Thu, 21 Mar 2024 19:55:31 +0100 Subject: [PATCH] Revert "IJPL-846 refactor (cannot get rid of awaitWithCheckCanceled yet)" This reverts commit 2815ddb2bd068aeb765f12d6791fce22a6c1b4c5. GitOrigin-RevId: 8c0e45657a7bdc99988c8761a3d000d253d051d7 --- .../textmate/bundles/BundleFactory.java | 13 ++-- .../plugins/textmate/bundles/BundleType.kt | 53 ++++++++------- .../jetbrains/plugins/textmate/TestUtil.java | 2 +- .../plugins/textmate/TextMateService.java | 6 +- .../plugins/textmate/TextMateServiceImpl.kt | 66 +++++++++---------- .../plugins/textmate/bundlesLoader.kt | 27 +++----- 6 files changed, 81 insertions(+), 86 deletions(-) diff --git a/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleFactory.java b/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleFactory.java index 1713ed22f9b9..4255aacc11c7 100644 --- a/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleFactory.java +++ b/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleFactory.java @@ -13,7 +13,7 @@ import java.io.IOException; * @deprecated use `TextMateService#readBundle` or `TextMateBundleReader` */ @Deprecated -public final class BundleFactory { +public class BundleFactory { private final PlistReader myPlistReader; public BundleFactory(PlistReader plistReader) { @@ -21,16 +21,17 @@ public final class BundleFactory { } /** - * Create a bundle object from directory. - * Return {code}null{code} if a bundle type can't be defined or - * if IO exception occurred while reading the directory. + * Create bundle object from directory. + * Return {code}null{code} if bundle type can't be defined or + * if IO exception occurred while reading directory. * * @return Bundle object or null * @deprecated use `TextMateService#readBundle#readGrammars` or `TextMateBundleReader` */ @Deprecated - public @Nullable Bundle fromDirectory(@NotNull File directory) throws IOException { - final BundleType type = BundleType.Companion.detectBundleType(directory.toPath()); + @Nullable + public Bundle fromDirectory(@NotNull File directory) throws IOException { + final BundleType type = BundleType.detectBundleType(directory.toPath()); return switch (type) { case TEXTMATE -> fromTextMateBundle(directory); case SUBLIME -> new Bundle(directory.getName(), directory.getPath(), type); diff --git a/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleType.kt b/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleType.kt index f25c0ccccac8..335e911ee6fd 100644 --- a/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleType.kt +++ b/plugins/textmate/core/src/org/jetbrains/plugins/textmate/bundles/BundleType.kt @@ -4,6 +4,9 @@ import org.jetbrains.plugins.textmate.Constants import java.nio.file.Files import java.nio.file.Path import kotlin.io.path.extension +import kotlin.io.path.isDirectory +import kotlin.io.path.isRegularFile +import kotlin.io.path.name import kotlin.streams.asSequence enum class BundleType { @@ -14,7 +17,7 @@ enum class BundleType { companion object { /** - * Detect a bundle type by directory. + * Detect bundle type by directory. * * @param directory Bundle directory. * @return bundle type. @@ -23,34 +26,34 @@ enum class BundleType { */ @JvmStatic fun detectBundleType(directory: Path?): BundleType { - if (directory == null || !Files.isDirectory(directory)) { - return UNDEFINED - } + if (directory != null && directory.isDirectory()) { + if ("tmBundle".equals(directory.extension, ignoreCase = true)) { + return TEXTMATE + } + val packageJson = directory.resolve(Constants.PACKAGE_JSON_NAME) + if (packageJson.isRegularFile()) { + return VSCODE + } - if (directory.extension.endsWith(".tmBundle", ignoreCase = true)) { - return TEXTMATE - } - - val packageJson = directory.resolve(Constants.PACKAGE_JSON_NAME) - if (Files.isRegularFile(packageJson)) { - return VSCODE - } - - val hasTmFiles = runCatching { - Files.list(directory).use { children -> - children.asSequence().any { child -> - val name = child.fileName.toString() - name.endsWith(".tmLanguage", ignoreCase = true) || name.endsWith(".tmPreferences", ignoreCase = true) + val hasTmFiles = runCatching { + Files.list(directory).use { children -> + children.asSequence().any { child -> + child.name.endsWith(".tmLanguage", ignoreCase = true) || + child.name.endsWith(".tmPreferences", ignoreCase = true) + } } } - } - if (hasTmFiles.getOrNull() == true) { - return SUBLIME - } + if (hasTmFiles.getOrNull() == true) { + return SUBLIME + } - val infoPlist = directory.resolve(Constants.BUNDLE_INFO_PLIST_NAME) - val hasInfoPlistFile = Files.isRegularFile(infoPlist) - return if (hasInfoPlistFile) TEXTMATE else UNDEFINED + val infoPlist = directory.resolve(Constants.BUNDLE_INFO_PLIST_NAME) + val hasInfoPlistFile = infoPlist.isRegularFile() + if (hasInfoPlistFile) { + return TEXTMATE + } + } + return UNDEFINED } } } diff --git a/plugins/textmate/core/tests/org/jetbrains/plugins/textmate/TestUtil.java b/plugins/textmate/core/tests/org/jetbrains/plugins/textmate/TestUtil.java index 7580e1ea3dac..342c84af6be8 100644 --- a/plugins/textmate/core/tests/org/jetbrains/plugins/textmate/TestUtil.java +++ b/plugins/textmate/core/tests/org/jetbrains/plugins/textmate/TestUtil.java @@ -60,7 +60,7 @@ public final class TestUtil { public static TextMateBundleReader readBundle(String bundleName) { Path bundleDirectory = getBundleDirectory(bundleName); - BundleType bundleType = BundleType.Companion.detectBundleType(bundleDirectory); + BundleType bundleType = BundleType.detectBundleType(bundleDirectory); return switch (bundleType) { case TEXTMATE -> readTextMateBundle(bundleDirectory); case SUBLIME -> readSublimeBundle(bundleDirectory); diff --git a/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateService.java b/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateService.java index efbafb1c1d79..67602e3761c5 100644 --- a/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateService.java +++ b/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateService.java @@ -25,7 +25,7 @@ public abstract class TextMateService { } /** - * Create a bundle object from a given directory. + * Create bundle object from given directory. * * @return bundle object or {@code null} if directory doesn't exist or bundle type can't be defined */ @@ -38,7 +38,7 @@ public abstract class TextMateService { * Unregister all and register all enabled bundles in IDE {@link TextMateUserBundlesSettings#getBundles()}, {@link TextMateBuiltinBundlesSettings#builtinBundles} * 1. read all enabled bundles * 2. prepare syntax table of supported languages - * 3. prepare preference table of enabled bundles + * 3. prepare preferences table of enabled bundles * 4. fill the extensions mapping for {@link TextMateFileType} */ public abstract void reloadEnabledBundles(); @@ -63,7 +63,7 @@ public abstract class TextMateService { /** * @return custom highlighting colors defined inside bundles (not in themes). - * Note that background color in text attributes is stored in raw format and isn't merged with a default background. + * Note that background color in text attributes is stored in raw format and isn't merged with default background. */ @NotNull public abstract Map getCustomHighlightingColors(); diff --git a/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateServiceImpl.kt b/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateServiceImpl.kt index b32268271f21..cd335673531e 100644 --- a/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateServiceImpl.kt +++ b/plugins/textmate/src/org/jetbrains/plugins/textmate/TextMateServiceImpl.kt @@ -18,8 +18,6 @@ import com.intellij.openapi.util.text.StringUtil import com.intellij.openapi.util.text.Strings import com.intellij.util.containers.Interner import kotlinx.coroutines.CoroutineScope -import kotlinx.coroutines.Dispatchers -import kotlinx.coroutines.withContext import org.jetbrains.annotations.NonNls import org.jetbrains.annotations.TestOnly import org.jetbrains.plugins.textmate.TextMateService.LOG @@ -40,7 +38,7 @@ import java.util.concurrent.ConcurrentHashMap import java.util.concurrent.locks.ReentrantLock import kotlin.concurrent.Volatile -class TextMateServiceImpl(private val scope: CoroutineScope) : TextMateService() { +class TextMateServiceImpl(private val myScope: CoroutineScope) : TextMateService() { private var builtinBundlesDisabled = false @Volatile @@ -87,7 +85,7 @@ class TextMateServiceImpl(private val scope: CoroutineScope) : TextMateService() builtInBundles.filter { !turnedOffBundleNames.contains(it.name) } } registerBundlesInParallel( - scope = scope, + scope = myScope, bundlesToLoad = bundlesToEnable, registrar = { registerBundle(Path.of(it.path), newExtensionsMapping) }, ) @@ -103,9 +101,9 @@ class TextMateServiceImpl(private val scope: CoroutineScope) : TextMateService() } if (!bundlesToLoad.isEmpty()) { registerBundlesInParallel( - scope = scope, + scope = myScope, bundlesToLoad = bundlesToLoad, - registrar = { registerBundle(Path.of(it.path), newExtensionsMapping) }, + registrar = { bundleToLoad -> registerBundle(Path.of(bundleToLoad.path), newExtensionsMapping) }, registrationFailed = { bundleToLoad -> val bundleName = bundleToLoad.name val errorMessage = TextMateBundle.message("textmate.cant.register.bundle", bundleName) @@ -200,29 +198,28 @@ class TextMateServiceImpl(private val scope: CoroutineScope) : TextMateService() } override fun readBundle(directory: Path?): TextMateBundleReader? { - if (directory == null) { - return null - } - - val bundleType = detectBundleType(directory) - return when (bundleType) { - BundleType.TEXTMATE -> readTextMateBundle(directory) - BundleType.SUBLIME -> readSublimeBundle(directory) - BundleType.VSCODE -> readVSCBundle { relativePath -> - try { - return@readVSCBundle Files.newInputStream(directory.resolve(relativePath)) - } - catch (e: NoSuchFileException) { - LOG.warn("Cannot find referenced file `$relativePath` in bundle `$directory`") - return@readVSCBundle null - } - catch (e: Throwable) { - LOG.warn("Cannot read referenced file `$relativePath` in bundle `$directory`", e) - return@readVSCBundle null + if (directory != null) { + val bundleType = detectBundleType(directory) + return when (bundleType) { + BundleType.TEXTMATE -> readTextMateBundle(directory) + BundleType.SUBLIME -> readSublimeBundle(directory) + BundleType.VSCODE -> readVSCBundle { relativePath: String -> + try { + return@readVSCBundle Files.newInputStream(directory.resolve(relativePath)) + } + catch (e: NoSuchFileException) { + LOG.warn("Cannot find referenced file `$relativePath` in bundle `$directory`") + return@readVSCBundle null + } + catch (e: Throwable) { + LOG.warn("Cannot read referenced file `$relativePath` in bundle `$directory`", e) + return@readVSCBundle null + } } + BundleType.UNDEFINED -> null } - BundleType.UNDEFINED -> null } + return null } private fun ensureInitialized() { @@ -239,14 +236,15 @@ class TextMateServiceImpl(private val scope: CoroutineScope) : TextMateService() } } - private suspend fun registerBundle(directory: Path?, extensionMapping: MutableMap): Boolean { - val reader = withContext(Dispatchers.IO) { - readBundle(directory) - } ?: return false - registerLanguageSupport(reader, extensionMapping) - registerPreferences(reader) - registerSnippets(reader) - return true + private fun registerBundle(directory: Path?, extensionMapping: MutableMap): Boolean { + val reader = readBundle(directory) + if (reader != null) { + registerLanguageSupport(reader, extensionMapping) + registerPreferences(reader) + registerSnippets(reader) + return true + } + return false } private fun registerSnippets(reader: TextMateBundleReader) { diff --git a/plugins/textmate/src/org/jetbrains/plugins/textmate/bundlesLoader.kt b/plugins/textmate/src/org/jetbrains/plugins/textmate/bundlesLoader.kt index 8013b1d4f9cc..98a9996a965a 100644 --- a/plugins/textmate/src/org/jetbrains/plugins/textmate/bundlesLoader.kt +++ b/plugins/textmate/src/org/jetbrains/plugins/textmate/bundlesLoader.kt @@ -10,14 +10,13 @@ import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.future.asCompletableFuture import kotlinx.coroutines.launch -import java.util.concurrent.CancellationException import java.util.function.Consumer @IntellijInternalApi @JvmOverloads internal fun registerBundlesInParallel(scope: CoroutineScope, bundlesToLoad: List, - registrar: suspend (TextMateBundleToLoad) -> Boolean, + registrar: (TextMateBundleToLoad) -> Boolean, registrationFailed: Consumer? = null) { fun handleError(bundleToLoad: TextMateBundleToLoad, t: Throwable? = null) { if (registrationFailed == null || ApplicationManager.getApplication().isHeadlessEnvironment) { @@ -30,27 +29,21 @@ internal fun registerBundlesInParallel(scope: CoroutineScope, } } - val initializationJob = scope.launch { - for (bundleToLoad in bundlesToLoad) { + val initializationJob = scope.launch(Dispatchers.IO) { + bundlesToLoad.map { bundleToLoad -> launch { - val registered = try { + runCatching { registrar(bundleToLoad) - } - catch (e: CancellationException) { - throw e - } - catch (e: Throwable) { - handleError(bundleToLoad, e) - null - } - - if (registered != null && !registered) { - handleError(bundleToLoad) + }.onFailure { t -> + handleError(bundleToLoad, t) + }.onSuccess { registered -> + if (!registered) { + handleError(bundleToLoad) + } } } } } - ProgressIndicatorUtils.awaitWithCheckCanceled(initializationJob.asCompletableFuture()) }