Disable some features when LV=1.1 API=1.0.

Feature list:
 - bound callable references
 - local delegated properties
 - coroutines.

#KT-16017 Fixed
This commit is contained in:
Stanislav Erokhin
2017-02-13 09:48:55 +03:00
parent be0211cd49
commit b6fa10cf9e
43 changed files with 232 additions and 75 deletions
@@ -25,6 +25,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.kotlin.cfg.WhenMissingCase;
import org.jetbrains.kotlin.config.LanguageFeature;
import org.jetbrains.kotlin.config.LanguageVersion;
import org.jetbrains.kotlin.config.LanguageVersionSettings;
import org.jetbrains.kotlin.descriptors.*;
import org.jetbrains.kotlin.lexer.KtKeywordToken;
import org.jetbrains.kotlin.lexer.KtModifierKeywordToken;
@@ -63,11 +64,11 @@ public interface Errors {
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
DiagnosticFactory1<PsiElement, String> UNSUPPORTED = DiagnosticFactory1.create(ERROR);
DiagnosticFactory1<PsiElement, LanguageFeature> UNSUPPORTED_FEATURE = DiagnosticFactory1.create(ERROR);
DiagnosticFactory1<PsiElement, Pair<LanguageFeature, LanguageVersionSettings>> UNSUPPORTED_FEATURE = DiagnosticFactory1.create(ERROR);
DiagnosticFactory1<PsiElement, Throwable> EXCEPTION_FROM_ANALYZER = DiagnosticFactory1.create(ERROR);
DiagnosticFactory1<PsiElement, LanguageFeature> EXPERIMENTAL_FEATURE_WARNING = DiagnosticFactory1.create(WARNING);
DiagnosticFactory1<PsiElement, LanguageFeature> EXPERIMENTAL_FEATURE_ERROR = DiagnosticFactory1.create(ERROR);
DiagnosticFactory1<PsiElement, Pair<LanguageFeature, LanguageVersionSettings>> EXPERIMENTAL_FEATURE_WARNING = DiagnosticFactory1.create(WARNING);
DiagnosticFactory1<PsiElement, Pair<LanguageFeature, LanguageVersionSettings>> EXPERIMENTAL_FEATURE_ERROR = DiagnosticFactory1.create(ERROR);
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@@ -453,7 +454,6 @@ public interface Errors {
DiagnosticFactory0<KtPropertyDelegate> ABSTRACT_DELEGATED_PROPERTY = DiagnosticFactory0.create(ERROR);
DiagnosticFactory0<KtPropertyAccessor> ACCESSOR_FOR_DELEGATED_PROPERTY = DiagnosticFactory0.create(ERROR);
DiagnosticFactory0<KtPropertyDelegate> DELEGATED_PROPERTY_IN_INTERFACE = DiagnosticFactory0.create(ERROR);
DiagnosticFactory0<KtPropertyDelegate> LOCAL_VARIABLE_WITH_DELEGATE = DiagnosticFactory0.create(ERROR);
DiagnosticFactory0<KtProperty> PROPERTY_WITH_NO_TYPE_NO_INITIALIZER = DiagnosticFactory0.create(ERROR, DECLARATION_SIGNATURE);
@@ -237,7 +237,6 @@ public class DefaultErrorMessages {
MAP.put(ABSTRACT_DELEGATED_PROPERTY, "Delegated property cannot be abstract");
MAP.put(ACCESSOR_FOR_DELEGATED_PROPERTY, "Delegated property cannot have accessors with non-default implementations");
MAP.put(DELEGATED_PROPERTY_IN_INTERFACE, "Delegated properties are not allowed in interfaces");
MAP.put(LOCAL_VARIABLE_WITH_DELEGATE, "Local variables are not allowed to have delegates");
MAP.put(INAPPLICABLE_LATEINIT_MODIFIER, "''lateinit'' modifier {0}", STRING);
@@ -600,30 +599,11 @@ public class DefaultErrorMessages {
MAP.put(UNSAFE_IMPLICIT_INVOKE_CALL, "Reference has a nullable type ''{0}'', use explicit ''?.invoke()'' to make a function-like call instead", RENDER_TYPE);
MAP.put(AMBIGUOUS_LABEL, "Ambiguous label");
MAP.put(UNSUPPORTED, "Unsupported [{0}]", STRING);
MAP.put(UNSUPPORTED_FEATURE, "The feature is {0}", new DiagnosticParameterRenderer<LanguageFeature>() {
@NotNull
@Override
public String render(LanguageFeature feature, @NotNull RenderingContext renderingContext) {
LanguageVersion version = feature.getSinceVersion();
return version != null
? "only available since Kotlin " + version.getVersionString() + ": " + feature.getPresentableText()
: "experimental and should be turned on explicitly via a command line option or in IDE settings: " + feature.getPresentableText();
}
});
MAP.put(EXPERIMENTAL_FEATURE_WARNING, "The feature is experimental: {0}", new DiagnosticParameterRenderer<LanguageFeature>() {
@NotNull
@Override
public String render(LanguageFeature feature, @NotNull RenderingContext renderingContext) {
return feature.getPresentableText();
}
});
MAP.put(EXPERIMENTAL_FEATURE_ERROR, "The experimental feature is disabled: {0}", new DiagnosticParameterRenderer<LanguageFeature>() {
@NotNull
@Override
public String render(LanguageFeature feature, @NotNull RenderingContext renderingContext) {
return feature.getPresentableText();
}
});
MAP.put(UNSUPPORTED_FEATURE, "{0}", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.UNSUPPORTED));
MAP.put(EXPERIMENTAL_FEATURE_WARNING, "{0}", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.WARNING));
MAP.put(EXPERIMENTAL_FEATURE_ERROR, "{0}", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.ERROR));
MAP.put(EXCEPTION_FROM_ANALYZER, "Internal Error occurred while analyzing this expression:\n{0}", THROWABLE);
MAP.put(UNNECESSARY_SAFE_CALL, "Unnecessary safe call on a non-null receiver of type {0}", RENDER_TYPE);
MAP.put(UNEXPECTED_SAFE_CALL, "Safe-call is not allowed here");
@@ -0,0 +1,69 @@
/*
* Copyright 2010-2017 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.diagnostics.rendering
import org.jetbrains.kotlin.config.LanguageFeature
import org.jetbrains.kotlin.config.LanguageVersionSettings
class LanguageFeatureMessageRenderer @JvmOverloads constructor(
private val type: Type,
private val useHtml: Boolean = false
): DiagnosticParameterRenderer<Pair<LanguageFeature, LanguageVersionSettings>> {
enum class Type {
UNSUPPORTED,
WARNING,
ERROR
}
override fun render(obj: Pair<LanguageFeature, LanguageVersionSettings>, renderingContext: RenderingContext): String {
val (feature, settings) = obj
val since = feature.sinceVersion
val sb = StringBuilder()
sb.append("The feature \"").append(feature.presentableName).append("\" is ")
when (type) {
Type.UNSUPPORTED ->
when {
since == null ->
sb.append("experimental and should be enabled explicitly")
since > settings.languageVersion ->
sb.append("only available since language version ").append(since.versionString)
feature.sinceApiVersion > settings.apiVersion ->
sb.append("only available since API version ").append(feature.sinceApiVersion.versionString)
else ->
sb.append("disabled")
}
Type.WARNING -> sb.append("experimental")
Type.ERROR -> sb.append("experimental and disabled")
}
val hintUrl = feature.hintUrl
if (hintUrl != null) {
if (useHtml) {
sb.append(" (").append("see more <a href=\"").append(hintUrl).append("\">here</a>)")
}
else {
sb.append(" (see: ").append(hintUrl).append(")")
}
}
return sb.toString()
}
}
@@ -711,7 +711,7 @@ class DeclarationsChecker(
}
}
else if (property.typeReference == null && !languageVersionSettings.supportsFeature(LanguageFeature.ShortSyntaxForPropertyGetters)) {
trace.report(Errors.UNSUPPORTED_FEATURE.on(property, LanguageFeature.ShortSyntaxForPropertyGetters))
trace.report(Errors.UNSUPPORTED_FEATURE.on(property, LanguageFeature.ShortSyntaxForPropertyGetters to languageVersionSettings))
}
else if (noExplicitTypeOrGetterType(property)) {
trace.report(PROPERTY_WITH_NO_TYPE_NO_INITIALIZER.on(property))
@@ -22,6 +22,7 @@ import com.google.common.collect.Sets;
import com.intellij.openapi.project.Project;
import com.intellij.psi.PsiElement;
import kotlin.Pair;
import kotlin.TuplesKt;
import kotlin.collections.CollectionsKt;
import kotlin.collections.SetsKt;
import kotlin.jvm.functions.Function0;
@@ -324,7 +325,8 @@ public class DescriptorResolver {
Function0<List<VariableDescriptor>> destructuringVariables;
if (destructuringDeclaration != null) {
if (!languageVersionSettings.supportsFeature(LanguageFeature.DestructuringLambdaParameters)) {
trace.report(Errors.UNSUPPORTED_FEATURE.on(valueParameter, LanguageFeature.DestructuringLambdaParameters));
trace.report(Errors.UNSUPPORTED_FEATURE.on(valueParameter,
TuplesKt.to(LanguageFeature.DestructuringLambdaParameters, languageVersionSettings)));
}
destructuringVariables = new Function0<List<VariableDescriptor>>() {
@@ -742,7 +744,8 @@ public class DescriptorResolver {
else if (!languageVersionSettings.supportsFeature(LanguageFeature.TypeAliases)) {
typeResolver.resolveAbbreviatedType(scopeWithTypeParameters, typeReference, trace);
PsiElement typeAliasKeyword = typeAlias.getTypeAliasKeyword();
trace.report(UNSUPPORTED_FEATURE.on(typeAliasKeyword != null ? typeAliasKeyword : typeAlias, LanguageFeature.TypeAliases));
trace.report(UNSUPPORTED_FEATURE.on(typeAliasKeyword != null ? typeAliasKeyword : typeAlias,
TuplesKt.to(LanguageFeature.TypeAliases, languageVersionSettings)));
typeAliasDescriptor.initialize(
typeParameterDescriptors,
ErrorUtils.createErrorType(name.asString()),
@@ -77,7 +77,7 @@ class LocalVariableResolver(
val delegateExpression = property.delegateExpression
if (delegateExpression != null) {
if (!languageVersionSettings.supportsFeature(LanguageFeature.LocalDelegatedProperties)) {
context.trace.report(LOCAL_VARIABLE_WITH_DELEGATE.on(property.delegate!!))
context.trace.report(UNSUPPORTED_FEATURE.on(property.delegate!!, LanguageFeature.LocalDelegatedProperties to languageVersionSettings))
}
if (propertyDescriptor is VariableDescriptorWithAccessors) {
@@ -277,6 +277,7 @@ object ModifierCheckerCore {
val errorOnDependencyFeature = errorOnFeature[dependency]?.let { languageVersionSettings.supportsFeature(it) } ?: false
val supportsFeature = languageVersionSettings.supportsFeature(dependency)
val diagnosticData = dependency to languageVersionSettings
if (!supportsFeature || errorOnDependencyFeature) {
val restrictedTargets = featureDependenciesTargets[dependency]
if (restrictedTargets != null && actualTargets.intersect(restrictedTargets).isEmpty()) {
@@ -284,17 +285,17 @@ object ModifierCheckerCore {
}
if (!supportsFeature) {
trace.report(Errors.UNSUPPORTED_FEATURE.on(node.psi, dependency))
trace.report(Errors.UNSUPPORTED_FEATURE.on(node.psi, diagnosticData))
}
else if (errorOnDependencyFeature) {
trace.report(Errors.EXPERIMENTAL_FEATURE_ERROR.on(node.psi, dependency))
trace.report(Errors.EXPERIMENTAL_FEATURE_ERROR.on(node.psi, diagnosticData))
}
return false
}
val pairedWarningFeature = warningOnFeature[dependency]
if (pairedWarningFeature != null && languageVersionSettings.supportsFeature(pairedWarningFeature)) {
trace.report(Errors.EXPERIMENTAL_FEATURE_WARNING.on(node.psi, dependency))
trace.report(Errors.EXPERIMENTAL_FEATURE_WARNING.on(node.psi, diagnosticData))
}
return true
@@ -66,7 +66,7 @@ object OperatorModifierChecker {
private fun checkSupportsFeature(feature: LanguageFeature, languageVersionSettings: LanguageVersionSettings, diagnosticHolder: DiagnosticSink, modifier: PsiElement) {
if (!languageVersionSettings.supportsFeature(feature)) {
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(modifier, feature))
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(modifier, feature to languageVersionSettings))
}
}
}
@@ -512,7 +512,7 @@ class TypeResolver(
return createErrorTypeForTypeConstructor(c, projectionFromAllQualifierParts, typeConstructor)
}
if (!languageVersionSettings.supportsFeature(LanguageFeature.TypeAliases)) {
c.trace.report(UNSUPPORTED_FEATURE.on(type, LanguageFeature.TypeAliases))
c.trace.report(UNSUPPORTED_FEATURE.on(type, LanguageFeature.TypeAliases to languageVersionSettings))
return createErrorTypeForTypeConstructor(c, projectionFromAllQualifierParts, typeConstructor)
}
@@ -35,7 +35,8 @@ class CallableReferenceCompatibilityChecker : CallChecker {
val callableReferenceResolvedCall = argumentExpression.callableReference.getResolvedCall(context.trace.bindingContext) ?: continue@inner
if (callableReferenceResolvedCall.call.isCallableReference() &&
callableReferenceResolvedCall.candidateDescriptor.typeParameters.isNotEmpty()) {
context.trace.report(Errors.UNSUPPORTED_FEATURE.on(argumentExpression, typeInferenceForCallableReferencesFeature))
context.trace.report(Errors.UNSUPPORTED_FEATURE.on(argumentExpression,
typeInferenceForCallableReferencesFeature to context.languageVersionSettings))
}
}
}
@@ -89,14 +89,15 @@ object BuilderFunctionsCallChecker : CallChecker {
}
fun checkCoroutinesFeature(languageVersionSettings: LanguageVersionSettings, diagnosticHolder: DiagnosticSink, reportOn: PsiElement) {
val diagnosticData = LanguageFeature.Coroutines to languageVersionSettings
if (!languageVersionSettings.supportsFeature(LanguageFeature.Coroutines)) {
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(reportOn, LanguageFeature.Coroutines))
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(reportOn, diagnosticData))
}
else if (languageVersionSettings.supportsFeature(LanguageFeature.ErrorOnCoroutines)) {
diagnosticHolder.report(Errors.EXPERIMENTAL_FEATURE_ERROR.on(reportOn, LanguageFeature.Coroutines))
diagnosticHolder.report(Errors.EXPERIMENTAL_FEATURE_ERROR.on(reportOn, diagnosticData))
}
else if (languageVersionSettings.supportsFeature(LanguageFeature.WarnOnCoroutines)) {
diagnosticHolder.report(Errors.EXPERIMENTAL_FEATURE_WARNING.on(reportOn, LanguageFeature.Coroutines))
diagnosticHolder.report(Errors.EXPERIMENTAL_FEATURE_WARNING.on(reportOn, diagnosticData))
}
}
@@ -42,7 +42,7 @@ object UnderscoreChecker : DeclarationChecker {
diagnosticHolder.report(Errors.UNDERSCORE_IS_RESERVED.on(identifier))
}
else if (isValidSingleUnderscore && !languageVersionSettings.supportsFeature(LanguageFeature.SingleUnderscoreForParameterName)) {
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(identifier, LanguageFeature.SingleUnderscoreForParameterName))
diagnosticHolder.report(Errors.UNSUPPORTED_FEATURE.on(identifier, LanguageFeature.SingleUnderscoreForParameterName to languageVersionSettings))
}
}
@@ -22,6 +22,7 @@ import com.intellij.psi.PsiElement;
import com.intellij.psi.tree.IElementType;
import com.intellij.psi.tree.TokenSet;
import com.intellij.psi.util.PsiTreeUtil;
import kotlin.TuplesKt;
import kotlin.jvm.functions.Function0;
import kotlin.jvm.functions.Function1;
import org.jetbrains.annotations.NotNull;
@@ -238,7 +239,8 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor {
if (!text.contains("_")) return;
if (!components.languageVersionSettings.supportsFeature(LanguageFeature.UnderscoresInNumericLiterals)) {
context.trace.report(Errors.UNSUPPORTED_FEATURE.on(expression, LanguageFeature.UnderscoresInNumericLiterals));
context.trace.report(Errors.UNSUPPORTED_FEATURE.on(expression,
TuplesKt.to(LanguageFeature.UnderscoresInNumericLiterals, components.languageVersionSettings)));
return;
}
@@ -198,7 +198,7 @@ class DoubleColonExpressionResolver(
private fun reportUnsupportedIfNeeded(expression: KtDoubleColonExpression, c: ExpressionTypingContext) {
if (!languageVersionSettings.supportsFeature(LanguageFeature.BoundCallableReferences)) {
c.trace.report(UNSUPPORTED_FEATURE.on(expression.receiverExpression!!, LanguageFeature.BoundCallableReferences))
c.trace.report(UNSUPPORTED_FEATURE.on(expression.receiverExpression!!, LanguageFeature.BoundCallableReferences to languageVersionSettings))
}
}
+4 -1
View File
@@ -1,4 +1,7 @@
compiler/testData/cli/jvm/apiVersion.kt:2:5: error: the feature "bound callable references" is only available since API version 1.1
""::class.isInstance(42)
^
compiler/testData/cli/jvm/apiVersion.kt:2:15: error: unresolved reference: isInstance
""::class.isInstance(42)
^
COMPILATION_ERROR
COMPILATION_ERROR
+7
View File
@@ -0,0 +1,7 @@
$TESTDATA_DIR$/apiVersion1.0.kt
-d
$TEMP_DIR$
-language-version
1.1
-api-version
1.0
+16
View File
@@ -0,0 +1,16 @@
typealias Foo = Int
sealed class A
data class B(val foo: Int): A()
inline val f get() = ""
suspend fun test() {
""::class
""::toString
Foo::class
Foo::toString
val b by lazy { "" }
}
+13
View File
@@ -0,0 +1,13 @@
compiler/testData/cli/jvm/apiVersion1.0.kt:8:1: error: the feature "coroutines" is only available since API version 1.1 (see: https://kotlinlang.org/docs/diagnostics/experimental-coroutines)
suspend fun test() {
^
compiler/testData/cli/jvm/apiVersion1.0.kt:9:5: error: the feature "bound callable references" is only available since API version 1.1
""::class
^
compiler/testData/cli/jvm/apiVersion1.0.kt:10:5: error: the feature "bound callable references" is only available since API version 1.1
""::toString
^
compiler/testData/cli/jvm/apiVersion1.0.kt:15:11: error: the feature "local delegated properties" is only available since API version 1.1
val b by lazy { "" }
^
COMPILATION_ERROR
+4 -1
View File
@@ -1,4 +1,7 @@
compiler/testData/cli/jvm/apiVersion.kt:2:5: error: the feature "bound callable references" is only available since API version 1.1
""::class.isInstance(42)
^
compiler/testData/cli/jvm/apiVersion.kt:2:15: error: unresolved reference: isInstance
""::class.isInstance(42)
^
COMPILATION_ERROR
COMPILATION_ERROR
+1
View File
@@ -0,0 +1 @@
suspend fun simple() = 5
+4
View File
@@ -0,0 +1,4 @@
$TESTDATA_DIR$/coroutines.kt
-d
$TEMP_DIR$
-Xcoroutines=enable
+1
View File
@@ -0,0 +1 @@
OK
+4
View File
@@ -0,0 +1,4 @@
$TESTDATA_DIR$/coroutines.kt
-d
$TEMP_DIR$
-Xcoroutines=error
+4
View File
@@ -0,0 +1,4 @@
compiler/testData/cli/jvm/coroutines.kt:1:1: error: the feature "coroutines" is experimental and disabled (see: https://kotlinlang.org/docs/diagnostics/experimental-coroutines)
suspend fun simple() = 5
^
COMPILATION_ERROR
+4
View File
@@ -0,0 +1,4 @@
$TESTDATA_DIR$/coroutines.kt
-d
$TEMP_DIR$
-Xcoroutines=warn
+4
View File
@@ -0,0 +1,4 @@
compiler/testData/cli/jvm/coroutines.kt:1:1: warning: the feature "coroutines" is experimental (see: https://kotlinlang.org/docs/diagnostics/experimental-coroutines)
suspend fun simple() = 5
^
OK
+2 -2
View File
@@ -1,10 +1,10 @@
compiler/testData/cli/jvm/languageVersion.kt:5:17: error: this type is sealed, so it can be inherited by only its own nested classes or objects
class Derived : Base()
^
compiler/testData/cli/jvm/languageVersion.kt:8:5: error: the feature is only available since Kotlin 1.1: bound callable references
compiler/testData/cli/jvm/languageVersion.kt:8:5: error: the feature "bound callable references" is only available since language version 1.1
""::class.isInstance(42)
^
compiler/testData/cli/jvm/languageVersion.kt:8:15: error: unresolved reference: isInstance
""::class.isInstance(42)
^
COMPILATION_ERROR
COMPILATION_ERROR
+1 -1
View File
@@ -1,4 +1,4 @@
compiler/testData/cli/jvm/unsupportedTypeAlias.kt:3:1: error: the feature is only available since Kotlin 1.1: type aliases
compiler/testData/cli/jvm/unsupportedTypeAlias.kt:3:1: error: the feature "type aliases" is only available since language version 1.1
typealias Unused = String
^
COMPILATION_ERROR
@@ -6,13 +6,13 @@ class Delegate {
}
fun foo(): Int {
val prop: Int <!LOCAL_VARIABLE_WITH_DELEGATE!>by Delegate()<!>
val prop: Int <!UNSUPPORTED_FEATURE!>by Delegate()<!>
val prop2: Int <!LOCAL_VARIABLE_WITH_DELEGATE!>by <!DELEGATE_SPECIAL_FUNCTION_MISSING!>123<!><!>
val prop2: Int <!UNSUPPORTED_FEATURE!>by <!DELEGATE_SPECIAL_FUNCTION_MISSING!>123<!><!>
val obj = object {
fun v(): Int {
val prop3: Int <!LOCAL_VARIABLE_WITH_DELEGATE!>by Delegate()<!>
val prop3: Int <!UNSUPPORTED_FEATURE!>by Delegate()<!>
return prop3
}
}
@@ -8,9 +8,9 @@ class Delegate {
}
fun foo(): Int {
val prop: Int <!LOCAL_VARIABLE_WITH_DELEGATE!>by Delegate()<!>
val prop: Int <!UNSUPPORTED_FEATURE!>by Delegate()<!>
val prop2: Int <!LOCAL_VARIABLE_WITH_DELEGATE!>by <!DELEGATE_SPECIAL_FUNCTION_MISSING!>123<!><!>
val prop2: Int <!UNSUPPORTED_FEATURE!>by <!DELEGATE_SPECIAL_FUNCTION_MISSING!>123<!><!>
return prop + prop2
}
@@ -4,11 +4,11 @@
import kotlin.coroutines.experimental.*
import kotlin.coroutines.experimental.intrinsics.*
suspend fun foo(): Unit = <!UNRESOLVED_REFERENCE!>suspendCoroutine<!> {
<!UNSUPPORTED_FEATURE!>suspend<!> fun foo(): Unit = <!UNRESOLVED_REFERENCE!>suspendCoroutine<!> {
<!UNRESOLVED_REFERENCE!>it<!>.<!DEBUG_INFO_ELEMENT_WITH_ERROR_TYPE!>resume<!>(Unit)
}
suspend fun bar(): Unit = <!UNRESOLVED_REFERENCE!>suspendCoroutineOrReturn<!> {
<!UNSUPPORTED_FEATURE!>suspend<!> fun bar(): Unit = <!UNRESOLVED_REFERENCE!>suspendCoroutineOrReturn<!> {
<!UNRESOLVED_REFERENCE!>it<!>.<!DEBUG_INFO_ELEMENT_WITH_ERROR_TYPE!>resume<!>(Unit)
<!UNRESOLVED_REFERENCE!>COROUTINE_SUSPENDED<!>
}
@@ -104,8 +104,10 @@ abstract class BaseDiagnosticsTest : KotlinMultiFileTestWithJava<TestModule, Tes
override val apiVersion: ApiVersion,
override val languageVersion: LanguageVersion
) : LanguageVersionSettings {
private val delegate = LanguageVersionSettingsImpl(languageVersion, apiVersion)
override fun supportsFeature(feature: LanguageFeature): Boolean =
languageFeatures[feature] ?: LanguageVersionSettingsImpl.DEFAULT.supportsFeature(feature)
languageFeatures[feature] ?: delegate.supportsFeature(feature)
}
inner class TestFile(
@@ -44,6 +44,12 @@ public class CliTestGenerated extends AbstractCliTest {
doJvmTest(fileName);
}
@TestMetadata("apiVersion1.0.args")
public void testApiVersion1_0() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/apiVersion1.0.args");
doJvmTest(fileName);
}
@TestMetadata("apiVersionAndSinceNewerKotlin.args")
public void testApiVersionAndSinceNewerKotlin() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/apiVersionAndSinceNewerKotlin.args");
@@ -116,12 +122,24 @@ public class CliTestGenerated extends AbstractCliTest {
doJvmTest(fileName);
}
@TestMetadata("coroutinesEnable.args")
public void testCoroutinesEnable() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesEnable.args");
doJvmTest(fileName);
}
@TestMetadata("coroutinesEnableWarnAndErrorClash.args")
public void testCoroutinesEnableWarnAndErrorClash() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesEnableWarnAndErrorClash.args");
doJvmTest(fileName);
}
@TestMetadata("coroutinesError.args")
public void testCoroutinesError() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesError.args");
doJvmTest(fileName);
}
@TestMetadata("coroutinesErrorAndEnableClash.args")
public void testCoroutinesErrorAndEnableClash() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesErrorAndEnableClash.args");
@@ -140,6 +158,12 @@ public class CliTestGenerated extends AbstractCliTest {
doJvmTest(fileName);
}
@TestMetadata("coroutinesWarninig.args")
public void testCoroutinesWarninig() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/coroutinesWarninig.args");
doJvmTest(fileName);
}
@TestMetadata("diagnosticsOrder.args")
public void testDiagnosticsOrder() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("compiler/testData/cli/jvm/diagnosticsOrder.args");
@@ -19,13 +19,17 @@ package org.jetbrains.kotlin.config
import org.jetbrains.kotlin.config.LanguageVersion.KOTLIN_1_1
import org.jetbrains.kotlin.utils.DescriptionAware
enum class LanguageFeature(val sinceVersion: LanguageVersion?, val hintUrl: String? = null) {
enum class LanguageFeature(
val sinceVersion: LanguageVersion?,
val sinceApiVersion: ApiVersion = ApiVersion.KOTLIN_1_0,
val hintUrl: String? = null
) {
// Note: names of these entries are also used in diagnostic tests and in user-visible messages (see presentableText below)
TypeAliases(KOTLIN_1_1),
BoundCallableReferences(KOTLIN_1_1),
LocalDelegatedProperties(KOTLIN_1_1),
BoundCallableReferences(KOTLIN_1_1, ApiVersion.KOTLIN_1_1),
LocalDelegatedProperties(KOTLIN_1_1, ApiVersion.KOTLIN_1_1),
TopLevelSealedInheritance(KOTLIN_1_1),
Coroutines(KOTLIN_1_1, "https://kotlinlang.org/docs/diagnostics/experimental-coroutines"),
Coroutines(KOTLIN_1_1, ApiVersion.KOTLIN_1_1, "https://kotlinlang.org/docs/diagnostics/experimental-coroutines"),
AdditionalBuiltInsMembers(KOTLIN_1_1),
DataClassInheritance(KOTLIN_1_1),
InlineProperties(KOTLIN_1_1),
@@ -106,7 +110,7 @@ class LanguageVersionSettingsImpl @JvmOverloads constructor(
override fun supportsFeature(feature: LanguageFeature): Boolean {
val since = feature.sinceVersion
return (since != null && languageVersion >= since) || feature in additionalFeatures
return (since != null && languageVersion >= since && apiVersion >= feature.sinceApiVersion) || feature in additionalFeatures
}
override fun toString() = buildString {
@@ -171,6 +171,10 @@ public class IdeErrorMessages {
MAP.put(ErrorsJs.JSCODE_ERROR, "<html>JavaScript: {0}</html>", JsCallDataHtmlRenderer.INSTANCE);
MAP.put(ErrorsJs.JSCODE_WARNING, "<html>JavaScript: {0}</html>", JsCallDataHtmlRenderer.INSTANCE);
MAP.put(UNSUPPORTED_FEATURE, "<html>{0}</html>", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.UNSUPPORTED, true));
MAP.put(EXPERIMENTAL_FEATURE_WARNING, "<html>{0}</html>", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.WARNING, true));
MAP.put(EXPERIMENTAL_FEATURE_ERROR, "<html>{0}</html>", new LanguageFeatureMessageRenderer(LanguageFeatureMessageRenderer.Type.ERROR, true));
MAP.setImmutable();
}
@@ -85,11 +85,11 @@ sealed class ChangeCoroutineSupportFix(
override fun doCreateActions(diagnostic: Diagnostic): List<IntentionAction> {
val newCoroutineSupports = when (diagnostic.factory) {
Errors.EXPERIMENTAL_FEATURE_ERROR -> {
if (Errors.EXPERIMENTAL_FEATURE_ERROR.cast(diagnostic).a != LanguageFeature.Coroutines) return emptyList()
if (Errors.EXPERIMENTAL_FEATURE_ERROR.cast(diagnostic).a.first != LanguageFeature.Coroutines) return emptyList()
listOf(CoroutineSupport.ENABLED_WITH_WARNING, CoroutineSupport.ENABLED)
}
Errors.EXPERIMENTAL_FEATURE_WARNING -> {
if (Errors.EXPERIMENTAL_FEATURE_WARNING.cast(diagnostic).a != LanguageFeature.Coroutines) return emptyList()
if (Errors.EXPERIMENTAL_FEATURE_WARNING.cast(diagnostic).a.first != LanguageFeature.Coroutines) return emptyList()
listOf(CoroutineSupport.ENABLED, CoroutineSupport.DISABLED)
}
else -> return emptyList()
@@ -79,7 +79,7 @@ sealed class EnableUnsupportedFeatureFix(
companion object : KotlinSingleIntentionActionFactory() {
override fun createAction(diagnostic: Diagnostic): EnableUnsupportedFeatureFix? {
val targetVersion = Errors.UNSUPPORTED_FEATURE.cast(diagnostic).a.sinceVersion ?: return null
val targetVersion = Errors.UNSUPPORTED_FEATURE.cast(diagnostic).a.first.sinceVersion ?: return null
val module = ModuleUtilCore.findModuleForPsiElement(diagnostic.psiElement) ?: return null
if (KotlinPluginUtil.isMavenModule(module)) return null
if (!KotlinPluginUtil.isGradleModule(module)) {
@@ -0,0 +1,3 @@
<!-- unsupportedFeature1 -->
<html>
The feature "destructuring lambda parameters" is only available since language version 1.1</html>
@@ -1,2 +0,0 @@
<!-- unsupportedFeature1 -->
The feature is only available since Kotlin 1.1: destructuring lambda parameters
-2
View File
@@ -1,2 +0,0 @@
<!-- urlMultiproject1 -->
The feature is experimental and should be turned on explicitly via a command line option or in IDE settings: multi platform projects (See: https://kotlinlang.org/docs/diagnostics/experimental-multitraget-projects)
@@ -1,5 +1,5 @@
// !DIAGNOSTICS_NUMBER: 1
// !DIAGNOSTICS: UNSUPPORTED_FEATURE
// !MESSAGE_TYPE: TEXT
// LANGUAGE_VERSION: 1.0
impl fun test() {}
suspend fun test() {}
+3
View File
@@ -0,0 +1,3 @@
<!-- urlRender1 -->
<html>
The feature "coroutines" is only available since language version 1.1 (see more <a href="https://kotlinlang.org/docs/diagnostics/experimental-coroutines">here</a>)</html>
@@ -324,9 +324,9 @@ public class DiagnosticMessageTestGenerated extends AbstractDiagnosticMessageTes
doTest(fileName);
}
@TestMetadata("urlMultiproject.kt")
public void testUrlMultiproject() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/diagnosticMessage/urlMultiproject.kt");
@TestMetadata("urlRender.kt")
public void testUrlRender() throws Exception {
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/diagnosticMessage/urlRender.kt");
doTest(fileName);
}
}