Improve message clarity for WRONG_NUMBER_OF_TYPE_ARGUMENTS diagnostics
#KT-9887 Fixed
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 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.
|
||||
@@ -98,7 +98,8 @@ public interface Errors {
|
||||
DiagnosticFactory0<KtTypeProjection> PROJECTION_ON_NON_CLASS_TYPE_ARGUMENT = DiagnosticFactory0.create(ERROR, VARIANCE_IN_PROJECTION);
|
||||
DiagnosticFactory2<KtTypeReference, KotlinType, KotlinType> UPPER_BOUND_VIOLATED = DiagnosticFactory2.create(ERROR);
|
||||
DiagnosticFactory0<KtNullableType> REDUNDANT_NULLABLE = DiagnosticFactory0.create(WARNING, NULLABLE_TYPE);
|
||||
DiagnosticFactory1<KtElement, Integer> WRONG_NUMBER_OF_TYPE_ARGUMENTS = DiagnosticFactory1.create(ERROR);
|
||||
DiagnosticFactory2<KtElement, Integer, DeclarationDescriptor> WRONG_NUMBER_OF_TYPE_ARGUMENTS = DiagnosticFactory2.create(ERROR);
|
||||
DiagnosticFactory1<KtElement, String> TYPE_ARGUMENTS_NOT_ALLOWED = DiagnosticFactory1.create(ERROR);
|
||||
DiagnosticFactory2<KtTypeReference, Integer, String> NO_TYPE_ARGUMENTS_ON_RHS = DiagnosticFactory2.create(ERROR);
|
||||
DiagnosticFactory1<KtTypeProjection, ClassifierDescriptor> CONFLICTING_PROJECTION = DiagnosticFactory1.create(ERROR, VARIANCE_IN_PROJECTION);
|
||||
DiagnosticFactory1<KtTypeProjection, ClassifierDescriptor> REDUNDANT_PROJECTION = DiagnosticFactory1.create(WARNING, VARIANCE_IN_PROJECTION);
|
||||
|
||||
+4
-3
@@ -656,9 +656,10 @@ public class DefaultErrorMessages {
|
||||
|
||||
MAP.put(TYPE_INFERENCE_FAILED_ON_SPECIAL_CONSTRUCT, "Type inference for control flow expression failed. Please specify its type explicitly.");
|
||||
|
||||
MAP.put(WRONG_NUMBER_OF_TYPE_ARGUMENTS, "{0,choice,0#No type arguments|1#Type argument|1<{0,number,integer} type arguments} expected", (DiagnosticParameterRenderer) null);
|
||||
MAP.put(NO_TYPE_ARGUMENTS_ON_RHS, "{0,choice,0#No type arguments|1#Type argument|1<{0,number,integer} type arguments} expected. " +
|
||||
"Use ''{1}'' if you don''t want to pass type arguments", null, STRING);
|
||||
String wrongNumberOfTypeArguments = "{0,choice,0#No type arguments|1#One type argument|1<{0,number,integer} type arguments} expected";
|
||||
MAP.put(WRONG_NUMBER_OF_TYPE_ARGUMENTS, wrongNumberOfTypeArguments + " for {1}", null, WITHOUT_MODIFIERS);
|
||||
MAP.put(NO_TYPE_ARGUMENTS_ON_RHS, wrongNumberOfTypeArguments + ". Use ''{1}'' if you don''t want to pass type arguments", null, STRING);
|
||||
MAP.put(TYPE_ARGUMENTS_NOT_ALLOWED, "Type arguments are not allowed {0}", STRING);
|
||||
|
||||
MAP.put(TYPE_PARAMETER_AS_REIFIED, "Cannot use ''{0}'' as reified type parameter. Use a class instead.", NAME);
|
||||
MAP.put(REIFIED_TYPE_PARAMETER_NO_INLINE, "Only type parameters of inline functions can be reified");
|
||||
|
||||
@@ -433,6 +433,9 @@ object Renderers {
|
||||
|
||||
@JvmField val FQ_NAMES_IN_TYPES = DescriptorRenderer.FQ_NAMES_IN_TYPES.asRenderer()
|
||||
@JvmField val COMPACT = DescriptorRenderer.COMPACT.asRenderer()
|
||||
@JvmField val WITHOUT_MODIFIERS = DescriptorRenderer.withOptions {
|
||||
modifiers = emptySet()
|
||||
}.asRenderer()
|
||||
@JvmField val SHORT_NAMES_IN_TYPES = DescriptorRenderer.SHORT_NAMES_IN_TYPES.asRenderer()
|
||||
@JvmField val COMPACT_WITH_MODIFIERS = DescriptorRenderer.COMPACT_WITH_MODIFIERS.asRenderer()
|
||||
@JvmField val DEPRECATION_RENDERER = DescriptorRenderer.ONLY_NAMES_WITH_SHORT_TYPES.withOptions {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 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.
|
||||
@@ -306,7 +306,7 @@ class TypeResolver(
|
||||
|
||||
val arguments = resolveTypeProjections(c, ErrorUtils.createErrorType("No type").constructor, type.typeArguments)
|
||||
if (!arguments.isEmpty()) {
|
||||
c.trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(type.typeArgumentList!!, 0))
|
||||
c.trace.report(TYPE_ARGUMENTS_NOT_ALLOWED.on(type.typeArgumentList!!, "for type parameters"))
|
||||
}
|
||||
|
||||
val containing = typeParameter.containingDeclaration
|
||||
@@ -445,7 +445,10 @@ class TypeResolver(
|
||||
|
||||
if (currentArguments.size != currentParameters.size) {
|
||||
c.trace.report(
|
||||
WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(qualifierPart.typeArguments ?: qualifierPart.expression, currentParameters.size))
|
||||
WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(
|
||||
qualifierPart.typeArguments ?: qualifierPart.expression, currentParameters.size, classDescriptorChain[index]
|
||||
)
|
||||
)
|
||||
return null
|
||||
}
|
||||
|
||||
@@ -461,7 +464,7 @@ class TypeResolver(
|
||||
|
||||
for (qualifierPart in nonClassQualifierParts) {
|
||||
if (qualifierPart.typeArguments != null) {
|
||||
c.trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(qualifierPart.typeArguments, 0))
|
||||
c.trace.report(TYPE_ARGUMENTS_NOT_ALLOWED.on(qualifierPart.typeArguments, "here"))
|
||||
return null
|
||||
}
|
||||
}
|
||||
@@ -471,7 +474,7 @@ class TypeResolver(
|
||||
val typeParametersToSpecify =
|
||||
parameters.subList(result.size, parameters.size).takeWhile { it.original.containingDeclaration is ClassDescriptor }
|
||||
if (typeParametersToSpecify.any { parameter -> !parameter.isDeclaredInScope(c) }) {
|
||||
c.trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(qualifierParts.last().expression, parameters.size))
|
||||
c.trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(qualifierParts.last().expression, parameters.size, classDescriptor))
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
||||
@@ -135,7 +135,7 @@ class CandidateResolver(
|
||||
|
||||
if (expectedTypeArgumentCount != jetTypeArguments.size) {
|
||||
candidateCall.addStatus(OTHER_ERROR)
|
||||
tracing.wrongNumberOfTypeArguments(trace, expectedTypeArgumentCount)
|
||||
tracing.wrongNumberOfTypeArguments(trace, expectedTypeArgumentCount, candidateDescriptor)
|
||||
}
|
||||
else {
|
||||
checkGenericBoundsInAFunctionCall(jetTypeArguments, typeArguments, candidateDescriptor, substitutor, trace)
|
||||
|
||||
+7
-8
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 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.
|
||||
@@ -103,14 +103,13 @@ public abstract class AbstractTracingStrategy implements TracingStrategy {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount) {
|
||||
public void wrongNumberOfTypeArguments(
|
||||
@NotNull BindingTrace trace, int expectedTypeArgumentCount, @NotNull CallableDescriptor descriptor
|
||||
) {
|
||||
KtTypeArgumentList typeArgumentList = call.getTypeArgumentList();
|
||||
if (typeArgumentList != null) {
|
||||
trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(typeArgumentList, expectedTypeArgumentCount));
|
||||
}
|
||||
else {
|
||||
trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(reference, expectedTypeArgumentCount));
|
||||
}
|
||||
trace.report(WRONG_NUMBER_OF_TYPE_ARGUMENTS.on(
|
||||
typeArgumentList != null ? typeArgumentList : reference, expectedTypeArgumentCount, descriptor
|
||||
));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 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.
|
||||
@@ -67,7 +67,7 @@ public interface TracingStrategy {
|
||||
public void noValueForParameter(@NotNull BindingTrace trace, @NotNull ValueParameterDescriptor valueParameter) {}
|
||||
|
||||
@Override
|
||||
public void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount) {}
|
||||
public void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount, @NotNull CallableDescriptor descriptor) {}
|
||||
|
||||
@Override
|
||||
public <D extends CallableDescriptor> void ambiguity(@NotNull BindingTrace trace, @NotNull Collection<? extends ResolvedCall<D>> descriptors) {}
|
||||
@@ -132,7 +132,11 @@ public interface TracingStrategy {
|
||||
|
||||
void noValueForParameter(@NotNull BindingTrace trace, @NotNull ValueParameterDescriptor valueParameter);
|
||||
|
||||
void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount);
|
||||
void wrongNumberOfTypeArguments(
|
||||
@NotNull BindingTrace trace,
|
||||
int expectedTypeArgumentCount,
|
||||
@NotNull CallableDescriptor descriptor
|
||||
);
|
||||
|
||||
<D extends CallableDescriptor> void ambiguity(@NotNull BindingTrace trace, @NotNull Collection<? extends ResolvedCall<D>> descriptors);
|
||||
|
||||
|
||||
+2
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2010-2015 JetBrains s.r.o.
|
||||
* Copyright 2010-2016 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.
|
||||
@@ -126,7 +126,7 @@ class TracingStrategyForImplicitConstructorDelegationCall(
|
||||
unexpectedError("noReceiverAllowed")
|
||||
}
|
||||
|
||||
override fun wrongNumberOfTypeArguments(trace: BindingTrace, expectedTypeArgumentCount: Int) {
|
||||
override fun wrongNumberOfTypeArguments(trace: BindingTrace, expectedTypeArgumentCount: Int, descriptor: CallableDescriptor) {
|
||||
unexpectedError("wrongNumberOfTypeArguments")
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -542,7 +542,7 @@ public class ControlStructureTypingUtils {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount) {
|
||||
public void wrongNumberOfTypeArguments(@NotNull BindingTrace trace, int expectedTypeArgumentCount, @NotNull CallableDescriptor descriptor) {
|
||||
logError();
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -12,7 +12,7 @@ package foobar.a
|
||||
package foobar
|
||||
|
||||
abstract class Foo<T>() {
|
||||
abstract val x : T<!WRONG_NUMBER_OF_TYPE_ARGUMENTS!><Int><!>
|
||||
abstract val x : T<!TYPE_ARGUMENTS_NOT_ALLOWED!><Int><!>
|
||||
}
|
||||
|
||||
// FILE: b.kt
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
// !DIAGNOSTICS: -UNUSED_PARAMETER
|
||||
|
||||
fun <T> foo(t: T<!WRONG_NUMBER_OF_TYPE_ARGUMENTS!><String, Int><!>) {}
|
||||
fun <T> foo(t: T<!TYPE_ARGUMENTS_NOT_ALLOWED!><String, Int><!>) {}
|
||||
|
||||
interface A
|
||||
class B<T: A>
|
||||
fun <T> foo1(t: T<!WRONG_NUMBER_OF_TYPE_ARGUMENTS!><B<<!UPPER_BOUND_VIOLATED!>String<!>>><!>) {}
|
||||
fun <T> foo1(t: T<!TYPE_ARGUMENTS_NOT_ALLOWED!><B<<!UPPER_BOUND_VIOLATED!>String<!>>><!>) {}
|
||||
+1
-1
@@ -48,4 +48,4 @@ fun error4(): Outer<!TYPE_ARGUMENTS_FOR_OUTER_CLASS_WHEN_NESTED_REFERENCED!><A><
|
||||
fun error5(): Outer<!TYPE_ARGUMENTS_FOR_OUTER_CLASS_WHEN_NESTED_REFERENCED!><A><!>.Obj.Nested2<B>.Inner5<C> = null!!
|
||||
fun error6(): Outer.Obj<!WRONG_NUMBER_OF_TYPE_ARGUMENTS!><A><!>.Nested2<B>.Inner5<C> = null!!
|
||||
|
||||
fun error7(): test<!WRONG_NUMBER_OF_TYPE_ARGUMENTS!><String><!>.Outer.Obj.Nested2<A>.Inner5<B> = null!!
|
||||
fun error7(): test<!TYPE_ARGUMENTS_NOT_ALLOWED!><String><!>.Outer.Obj.Nested2<A>.Inner5<B> = null!!
|
||||
@@ -0,0 +1,7 @@
|
||||
package foo
|
||||
|
||||
open class A<T>
|
||||
|
||||
fun <T> f(<warning>t</warning>: T<error descr="[TYPE_ARGUMENTS_NOT_ALLOWED] Type arguments are not allowed for type parameters"><T></error>) {}
|
||||
|
||||
fun <T> use(<warning>b</warning>: foo<error descr="[TYPE_ARGUMENTS_NOT_ALLOWED] Type arguments are not allowed here"><T></error>.A<T>) {}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
open class A<T>()
|
||||
class G<T>()
|
||||
|
||||
|
||||
class B : A<<error descr="[WRONG_NUMBER_OF_TYPE_ARGUMENTS] One type argument expected for class G<T> defined in root package">G</error>>()
|
||||
@@ -1,5 +1,5 @@
|
||||
// "class org.jetbrains.kotlin.idea.quickfix.AddStarProjectionsFix" "false"
|
||||
// ERROR: 2 type arguments expected
|
||||
// ERROR: 2 type arguments expected for interface Map<K, out V> defined in kotlin.collections
|
||||
public fun foo(a: Any) {
|
||||
a is <caret>Map<Int>
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
// "class org.jetbrains.kotlin.idea.quickfix.AddStarProjectionsFix" "false"
|
||||
// ERROR: 2 type arguments expected
|
||||
// ERROR: 2 type arguments expected for Map
|
||||
public fun foo(a: Any) {
|
||||
a is Map<Int>
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
// "class org.jetbrains.kotlin.idea.quickfix.AddStarProjectionsFix" "false"
|
||||
// ERROR: 2 type arguments expected
|
||||
// ERROR: 2 type arguments expected for interface Map<K, out V> defined in kotlin.collections
|
||||
public fun foo(a: Any) {
|
||||
when (a) {
|
||||
is <caret>Map<Int> -> {}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
// "class org.jetbrains.kotlin.idea.quickfix.AddStarProjectionsFix" "false"
|
||||
// ERROR: 2 type arguments expected
|
||||
// ERROR: 2 type arguments expected for Map
|
||||
public fun foo(a: Any) {
|
||||
when (a) {
|
||||
is Map<Int> -> {}
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
// "Create secondary constructor" "false"
|
||||
// ACTION: Add parameter to constructor 'A'
|
||||
// ACTION: Create function 'A'
|
||||
// ERROR: No type arguments expected
|
||||
// ERROR: No type arguments expected for constructor A() defined in A
|
||||
// ERROR: Too many arguments for public constructor A() defined in A
|
||||
|
||||
class A
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
// "Make 'IterablePipeline' abstract" "true"
|
||||
// ERROR: 'pipe' overrides nothing
|
||||
// ERROR: Type argument expected
|
||||
// ERROR: One type argument expected for interface Pipeline<TPipeline> defined in root package
|
||||
|
||||
// Actually this test is about getting rid of assertion happenning while creating quick fixes
|
||||
// See KT-10409
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
// "Make 'IterablePipeline' abstract" "true"
|
||||
// ERROR: 'pipe' overrides nothing
|
||||
// ERROR: Type argument expected
|
||||
// ERROR: One type argument expected for interface Pipeline<TPipeline> defined in root package
|
||||
|
||||
// Actually this test is about getting rid of assertion happenning while creating quick fixes
|
||||
// See KT-10409
|
||||
|
||||
@@ -343,6 +343,12 @@ public class PsiCheckerTestGenerated extends AbstractPsiCheckerTest {
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("TypeArgumentsNotAllowed.kt")
|
||||
public void testTypeArgumentsNotAllowed() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/checker/TypeArgumentsNotAllowed.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("TypeParameterBounds.kt")
|
||||
public void testTypeParameterBounds() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/checker/TypeParameterBounds.kt");
|
||||
@@ -598,6 +604,12 @@ public class PsiCheckerTestGenerated extends AbstractPsiCheckerTest {
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("kt9887.kt")
|
||||
public void testKt9887() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/checker/regression/kt9887.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("objectLiteralInSupertypeList.kt")
|
||||
public void testObjectLiteralInSupertypeList() throws Exception {
|
||||
String fileName = KotlinTestUtils.navigationMetadata("idea/testData/checker/regression/objectLiteralInSupertypeList.kt");
|
||||
|
||||
+4
-4
@@ -51,16 +51,16 @@ End of files
|
||||
Exit code: ABORT
|
||||
------------------------------------------
|
||||
COMPILATION FAILED
|
||||
Type argument expected
|
||||
Type argument expected
|
||||
Type argument expected
|
||||
One type argument expected for class A<T> defined in foo
|
||||
One type argument expected for class A<T> defined in foo
|
||||
One type argument expected for class A<T> defined in foo
|
||||
Type inference failed: Not enough information to infer parameter T in constructor A<T>()
|
||||
Please specify it explicitly.
|
||||
Type inference failed: Not enough information to infer parameter T in constructor A<T>()
|
||||
Please specify it explicitly.
|
||||
Type inference failed: Not enough information to infer parameter T in constructor A<T>()
|
||||
Please specify it explicitly.
|
||||
Type argument expected
|
||||
One type argument expected for class A<T> defined in foo
|
||||
|
||||
================ Step #2 =================
|
||||
|
||||
|
||||
Reference in New Issue
Block a user