From dd28aa97c62dcd417de7569ae73d8647f5657d30 Mon Sep 17 00:00:00 2001 From: Max Medvedev Date: Sun, 30 Sep 2012 22:34:28 +0300 Subject: [PATCH] IDEA-71638 Type inferrence loses methods of generic parameter --- .../completion/EachWithIndexClosureCompleter.java | 7 ++++++- .../psi/typeEnhancers/ClosureParameterEnhancer.java | 3 ++- .../groovy/lang/resolve/TypeInferenceTest.groovy | 12 ++++++++++++ 3 files changed, 20 insertions(+), 2 deletions(-) diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/completion/EachWithIndexClosureCompleter.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/completion/EachWithIndexClosureCompleter.java index cb3434e16dbf..520de663aa88 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/completion/EachWithIndexClosureCompleter.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/completion/EachWithIndexClosureCompleter.java @@ -23,7 +23,9 @@ import com.intellij.psi.util.InheritanceUtil; import com.intellij.psi.util.PsiUtil; import org.jetbrains.annotations.Nullable; import org.jetbrains.plugins.groovy.lang.completion.closureParameters.ClosureParameterInfo; +import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression; import org.jetbrains.plugins.groovy.lang.psi.api.statements.typedef.members.GrGdkMethod; +import org.jetbrains.plugins.groovy.lang.psi.impl.PsiImplUtil; import org.jetbrains.plugins.groovy.lang.psi.util.GroovyCommonClassNames; import java.util.Arrays; @@ -61,7 +63,10 @@ public class EachWithIndexClosureCompleter extends ClosureCompleter { final PsiType iterable = PsiUtil.extractIterableTypeParameter(collection, true); if (iterable != null) { - return Arrays.asList(new ClosureParameterInfo(iterable.getCanonicalText(), "entry"), new ClosureParameterInfo("int", "i")); + return Arrays.asList( + new ClosureParameterInfo(PsiImplUtil.normalizeWildcardTypeByPosition(iterable, (GrExpression)parent).getCanonicalText(), "entry"), + new ClosureParameterInfo("int", "i") + ); } if (InheritanceUtil.isInheritor(collection, CommonClassNames.JAVA_UTIL_MAP)) { diff --git a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/typeEnhancers/ClosureParameterEnhancer.java b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/typeEnhancers/ClosureParameterEnhancer.java index 2353c049fa75..8148ac1e5ce2 100644 --- a/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/typeEnhancers/ClosureParameterEnhancer.java +++ b/plugins/groovy/src/org/jetbrains/plugins/groovy/lang/psi/typeEnhancers/ClosureParameterEnhancer.java @@ -16,6 +16,7 @@ import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.arithmet import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.literals.GrStringInjection; import org.jetbrains.plugins.groovy.lang.psi.impl.GrRangeType; import org.jetbrains.plugins.groovy.lang.psi.impl.GrTupleType; +import org.jetbrains.plugins.groovy.lang.psi.impl.PsiImplUtil; import org.jetbrains.plugins.groovy.lang.psi.impl.statements.expressions.TypesUtil; import org.jetbrains.plugins.groovy.lang.psi.util.GdkMethodUtil; import org.jetbrains.plugins.groovy.lang.psi.util.GroovyCommonClassNames; @@ -257,7 +258,7 @@ public class ClosureParameterEnhancer extends AbstractClosureParameterEnhancer { PsiType res = PsiUtil.extractIterableTypeParameter(iterType, true); if (res != null) { - return res; + return PsiImplUtil.normalizeWildcardTypeByPosition(res, qualifier); } if (TypesUtil.isClassType(iterType, CommonClassNames.JAVA_LANG_STRING) || TypesUtil.isClassType(iterType, JAVA_IO_FILE)) { diff --git a/plugins/groovy/test/org/jetbrains/plugins/groovy/lang/resolve/TypeInferenceTest.groovy b/plugins/groovy/test/org/jetbrains/plugins/groovy/lang/resolve/TypeInferenceTest.groovy index f050d08d5ea3..6be551bac269 100644 --- a/plugins/groovy/test/org/jetbrains/plugins/groovy/lang/resolve/TypeInferenceTest.groovy +++ b/plugins/groovy/test/org/jetbrains/plugins/groovy/lang/resolve/TypeInferenceTest.groovy @@ -556,6 +556,18 @@ private void getCommonAncestor() { } + void testWildcardClosureParam() { + doTest('''\ +class Tx { + def methodOfT() {} +} + +def method(List t) { + t.collect { print it } +} +''', 'Tx') + } + private void doTest(String text, String type) { def file = myFixture.configureByText('_.groovy', text) def ref = file.findReferenceAt(myFixture.editor.caretModel.offset) as GrReferenceExpression