From 7db2e1a56e546796e8a02abf5e8746ba0d9d4660 Mon Sep 17 00:00:00 2001 From: peter Date: Tue, 23 Jan 2018 22:14:51 +0100 Subject: [PATCH] allow CompletionParameters to have nullable editor a step towards retrieving completion suggestions from a headless process --- .../completion/CompletionParameters.java | 22 +++++++++++++++---- .../completion/CompletionService.java | 10 ++++++--- .../CompletionWithoutEditorException.java | 12 ++++++++++ 3 files changed, 37 insertions(+), 7 deletions(-) create mode 100644 platform/lang-api/src/com/intellij/codeInsight/completion/CompletionWithoutEditorException.java diff --git a/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionParameters.java b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionParameters.java index 9b4f32b2ab5a..3a10434ca19b 100644 --- a/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionParameters.java +++ b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionParameters.java @@ -16,10 +16,10 @@ package com.intellij.codeInsight.completion; import com.intellij.openapi.editor.Editor; -import org.jetbrains.annotations.NotNull; -import org.jetbrains.annotations.Nullable; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiFile; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; /** * @author peter @@ -28,12 +28,12 @@ public final class CompletionParameters { private final PsiElement myPosition; private final PsiFile myOriginalFile; private final CompletionType myCompletionType; - private final Editor myEditor; + @Nullable private final Editor myEditor; private final int myOffset; private final int myInvocationCount; CompletionParameters(@NotNull final PsiElement position, @NotNull final PsiFile originalFile, - @NotNull CompletionType completionType, int offset, final int invocationCount, @NotNull Editor editor) { + @NotNull CompletionType completionType, int offset, final int invocationCount, @Nullable Editor editor) { assert position.getTextRange().containsOffset(offset) : position; myPosition = position; assert position.isValid(); @@ -106,8 +106,22 @@ public final class CompletionParameters { return myCompletionType == CompletionType.BASIC && myInvocationCount >= 2; } + /** + * @return the editor where the completion was started, or null if completion API was invoked in absence of editor. + * @see #hasEditor() + */ @NotNull public Editor getEditor() { + if (myEditor == null) throw new CompletionWithoutEditorException(); return myEditor; } + + /** + * @return whether this completion was started within an editor + * @since 181.* + */ + public boolean hasEditor() { + return myEditor != null; + } + } diff --git a/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionService.java b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionService.java index c3d911415936..ee5b32d968c4 100644 --- a/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionService.java +++ b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionService.java @@ -77,10 +77,14 @@ public abstract class CompletionService { for (int i = contributors.indexOf(from) + 1; i < contributors.size(); i++) { ProgressManager.checkCanceled(); - final CompletionContributor contributor = contributors.get(i); + CompletionContributor contributor = contributors.get(i); - final CompletionResultSet result = createResultSet(parameters, consumer, contributor); - contributor.fillCompletionVariants(parameters, result); + CompletionResultSet result = createResultSet(parameters, consumer, contributor); + try { + contributor.fillCompletionVariants(parameters, result); + } + catch (CompletionWithoutEditorException ignore) { + } if (result.isStopped()) { return; } diff --git a/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionWithoutEditorException.java b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionWithoutEditorException.java new file mode 100644 index 000000000000..0c3361784a1e --- /dev/null +++ b/platform/lang-api/src/com/intellij/codeInsight/completion/CompletionWithoutEditorException.java @@ -0,0 +1,12 @@ +// Copyright 2000-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 file. +package com.intellij.codeInsight.completion; + +/** + * An exception thrown when a completion contributor attempts to invoke {@link CompletionParameters#getEditor()} + * for a completion performed in absence of editor. This exception is caught by completion infrastructure, and so + * shouldn't be handled by contributors. To avoid this exception, check {@link CompletionParameters#hasEditor()}. + * + * @since 181.* + */ +public class CompletionWithoutEditorException extends RuntimeException { +}