From 306a035c68eebd769db0ee24be02e30771927405 Mon Sep 17 00:00:00 2001 From: Mark Punzalan Date: Sat, 21 Aug 2021 08:42:27 +0000 Subject: [PATCH] HL API: Fix argument mapping for lambda arguments (+ more tests). --- .../api/fir/components/KtFirCallResolver.kt | 4 +-- .../functionCallWithLambdaArgument.kt | 7 +++++ .../functionCallWithLambdaArgument.txt | 3 ++ .../functionCallWithNamedArgument.kt | 7 +++++ .../functionCallWithNamedArgument.txt | 3 ++ ...nctionCallWithNonTrailingLambdaArgument.kt | 7 +++++ ...ctionCallWithNonTrailingLambdaArgument.txt | 3 ++ .../functionCallWithSpreadArgument.kt | 8 +++++ .../functionCallWithSpreadArgument.txt | 3 ++ .../functionCallWithVarargArgument.kt | 7 +++++ .../functionCallWithVarargArgument.txt | 3 ++ .../api/fir/AbstractResolveCallTest.kt | 6 ++-- .../api/fir/ResolveCallTestGenerated.java | 30 +++++++++++++++++++ 13 files changed, 85 insertions(+), 6 deletions(-) create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.kt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.txt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.kt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.txt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.kt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.txt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.kt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.txt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.kt create mode 100644 idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.txt diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirCallResolver.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirCallResolver.kt index 8870bc082f2..ca1ecb94d8d 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirCallResolver.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirCallResolver.kt @@ -180,10 +180,10 @@ internal class KtFirCallResolver( val ktArgumentMapping = LinkedHashMap() argumentMapping?.let { fun FirExpression.findKtExpression(): KtExpression? { - // For spread and named arguments, the source is the KtValueArgument. + // For spread, named, and lambda arguments, the source is the KtValueArgument. // For other arguments (including array indices), the source is the KtExpression. return when (this) { - is FirNamedArgumentExpression, is FirSpreadArgumentExpression -> + is FirNamedArgumentExpression, is FirSpreadArgumentExpression, is FirLambdaArgumentExpression -> realPsi.safeAs()?.getArgumentExpression() else -> realPsi as? KtExpression } diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.kt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.kt new file mode 100644 index 00000000000..68ca0505ffb --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.kt @@ -0,0 +1,7 @@ +fun function(a: Int, b: (String) -> Boolean) {} + +fun call() { + function(1) { s -> true } +} + +// CALL: KtFunctionCall: targetFunction = /function(a: kotlin.Int, b: (kotlin.String) -> kotlin.Boolean): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.txt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.txt new file mode 100644 index 00000000000..c436fa4c52c --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.txt @@ -0,0 +1,3 @@ +KtFunctionCall: +argumentMapping = { 1 -> (a: kotlin.Int), { s -> true } -> (b: kotlin.Function1) } +targetFunction = /function(a: kotlin.Int, b: kotlin.Function1): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.kt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.kt new file mode 100644 index 00000000000..c46bca5b477 --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.kt @@ -0,0 +1,7 @@ +fun function(a: Int, b: String) {} + +fun call() { + function(b = "foo", a = 1) +} + +// CALL: KtFunctionCall: targetFunction = /function(a: kotlin.Int, b: kotlin.String): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.txt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.txt new file mode 100644 index 00000000000..250c5189ddd --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.txt @@ -0,0 +1,3 @@ +KtFunctionCall: +argumentMapping = { "foo" -> (b: kotlin.String), 1 -> (a: kotlin.Int) } +targetFunction = /function(a: kotlin.Int, b: kotlin.String): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.kt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.kt new file mode 100644 index 00000000000..73d704818d5 --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.kt @@ -0,0 +1,7 @@ +fun function(a: Int, b: (String) -> Boolean) {} + +fun call() { + function(1, { s -> true }) +} + +// CALL: KtFunctionCall: targetFunction = /function(a: kotlin.Int, b: (String) -> Boolean): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.txt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.txt new file mode 100644 index 00000000000..c436fa4c52c --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.txt @@ -0,0 +1,3 @@ +KtFunctionCall: +argumentMapping = { 1 -> (a: kotlin.Int), { s -> true } -> (b: kotlin.Function1) } +targetFunction = /function(a: kotlin.Int, b: kotlin.Function1): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.kt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.kt new file mode 100644 index 00000000000..cca491e3f41 --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.kt @@ -0,0 +1,8 @@ +fun function(vararg a: Int) {} + +fun call() { + val args = intArrayOf(1, 2, 3) + function(*args) +} + +// CALL: KtFunctionCall: targetFunction = /function(vararg a: kotlin.IntArray): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.txt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.txt new file mode 100644 index 00000000000..1d9df90e365 --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.txt @@ -0,0 +1,3 @@ +KtFunctionCall: +argumentMapping = { args -> (vararg a: kotlin.IntArray) } +targetFunction = /function(vararg a: kotlin.IntArray): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.kt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.kt new file mode 100644 index 00000000000..f59177ae2af --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.kt @@ -0,0 +1,7 @@ +fun function(vararg a: Int) {} + +fun call() { + function(1, 2, 3) +} + +// CALL: KtFunctionCall: targetFunction = /function(vararg a: kotlin.IntArray): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.txt b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.txt new file mode 100644 index 00000000000..5dc3bdaea10 --- /dev/null +++ b/idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.txt @@ -0,0 +1,3 @@ +KtFunctionCall: +argumentMapping = { 1 -> (vararg a: kotlin.IntArray), 2 -> (vararg a: kotlin.IntArray), 3 -> (vararg a: kotlin.IntArray) } +targetFunction = /function(vararg a: kotlin.IntArray): kotlin.Unit \ No newline at end of file diff --git a/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/AbstractResolveCallTest.kt b/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/AbstractResolveCallTest.kt index 0a8e686b258..fe5be4b0787 100644 --- a/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/AbstractResolveCallTest.kt +++ b/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/AbstractResolveCallTest.kt @@ -61,13 +61,11 @@ private fun KtCall.stringRepresentation(): String { append(": ${receiver.type.render()}") if (valueParameters.isNotEmpty()) append(", ") } - valueParameters.joinTo(this) { parameter -> - "${parameter.name}: ${parameter.annotatedType.type.render()}" - } + valueParameters.joinTo(this) { it.stringValue() } append(")") append(": ${annotatedType.type.render()}") } - is KtValueParameterSymbol -> "$name: ${annotatedType.type.render()}" + is KtValueParameterSymbol -> "${if (isVararg) "vararg " else ""}$name: ${annotatedType.type.render()}" is KtSuccessCallTarget -> symbol.stringValue() is KtErrorCallTarget -> "ERR<${this.diagnostic.defaultMessage}, [${candidates.joinToString { it.stringValue() }}]>" is Boolean -> toString() diff --git a/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/ResolveCallTestGenerated.java b/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/ResolveCallTestGenerated.java index b7d5432e48d..a4d0d231135 100644 --- a/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/ResolveCallTestGenerated.java +++ b/idea/idea-frontend-fir/tests/org/jetbrains/kotlin/idea/fir/frontend/api/fir/ResolveCallTestGenerated.java @@ -54,6 +54,36 @@ public class ResolveCallTestGenerated extends AbstractResolveCallTest { runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallInTheSameFile.kt"); } + @Test + @TestMetadata("functionCallWithLambdaArgument.kt") + public void testFunctionCallWithLambdaArgument() throws Exception { + runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithLambdaArgument.kt"); + } + + @Test + @TestMetadata("functionCallWithNamedArgument.kt") + public void testFunctionCallWithNamedArgument() throws Exception { + runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNamedArgument.kt"); + } + + @Test + @TestMetadata("functionCallWithNonTrailingLambdaArgument.kt") + public void testFunctionCallWithNonTrailingLambdaArgument() throws Exception { + runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithNonTrailingLambdaArgument.kt"); + } + + @Test + @TestMetadata("functionCallWithSpreadArgument.kt") + public void testFunctionCallWithSpreadArgument() throws Exception { + runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithSpreadArgument.kt"); + } + + @Test + @TestMetadata("functionCallWithVarargArgument.kt") + public void testFunctionCallWithVarargArgument() throws Exception { + runTest("idea/idea-frontend-fir/testData/analysisSession/resolveCall/functionCallWithVarargArgument.kt"); + } + @Test @TestMetadata("functionWithReceiverCall.kt") public void testFunctionWithReceiverCall() throws Exception {