diff --git a/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeAliasExpander.kt b/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeAliasExpander.kt index 53e24a674d2..dad93fb3fe7 100644 --- a/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeAliasExpander.kt +++ b/compiler/frontend/src/org/jetbrains/kotlin/resolve/TypeAliasExpander.kt @@ -214,25 +214,16 @@ class TypeAliasExpander( withAbbreviatedType = false ) + val substitutedType = type.substituteArguments(typeAliasExpansion, recursionDepth) + // 'dynamic' type can't be abbreviated - will be reported separately val typeWithAbbreviation = - if (nestedExpandedType.isDynamic()) nestedExpandedType else nestedExpandedType.withAbbreviation(type) + if (nestedExpandedType.isDynamic()) nestedExpandedType else nestedExpandedType.withAbbreviation(substitutedType) TypeProjectionImpl(originalProjection.projectionKind, typeWithAbbreviation) } else -> { - val substitutedArguments = type.arguments.mapIndexed { i, originalArgument -> - val projection = expandTypeProjection( - originalArgument, typeAliasExpansion, typeConstructor.parameters[i], recursionDepth + 1 - ) - if (projection.isStarProjection) projection - else TypeProjectionImpl( - projection.projectionKind, - TypeUtils.makeNullableIfNeeded(projection.type, originalArgument.type.isMarkedNullable) - ) - } - - val substitutedType = type.replace(newArguments = substitutedArguments) + val substitutedType = type.substituteArguments(typeAliasExpansion, recursionDepth) checkTypeArgumentsSubstitution(type, substitutedType) @@ -241,6 +232,23 @@ class TypeAliasExpander( } } + private fun SimpleType.substituteArguments(typeAliasExpansion: TypeAliasExpansion, recursionDepth: Int): SimpleType { + val typeConstructor = this.constructor + + val substitutedArguments = this.arguments.mapIndexed { i, originalArgument -> + val projection = expandTypeProjection( + originalArgument, typeAliasExpansion, typeConstructor.parameters[i], recursionDepth + 1 + ) + if (projection.isStarProjection) projection + else TypeProjectionImpl( + projection.projectionKind, + TypeUtils.makeNullableIfNeeded(projection.type, originalArgument.type.isMarkedNullable) + ) + } + + return this.replace(newArguments = substitutedArguments) + } + private fun checkTypeArgumentsSubstitution(unsubstitutedType: KotlinType, substitutedType: KotlinType) { val typeSubstitutor = TypeSubstitutor.create(substitutedType) diff --git a/compiler/testData/compileKotlinAgainstKotlin/kt21775.kt b/compiler/testData/compileKotlinAgainstKotlin/kt21775.kt new file mode 100644 index 00000000000..a683731e927 --- /dev/null +++ b/compiler/testData/compileKotlinAgainstKotlin/kt21775.kt @@ -0,0 +1,43 @@ +// FILE: lib.kt + +package lib + +class TestObserver { + fun assertValue(valuePredicate: (T) -> Boolean): Unit = TODO() +} + +class Single { + fun test(): TestObserver = TODO() +} + +class Employee + +class Either + +typealias DomainEither = Either +typealias DomainSingle = Single> + +fun provideDomainSingle(): DomainSingle = TODO() + +class CreateEmployeeUseCaseAccessor { + fun testNormalName() { + val testObs = provideDomainSingle().test() + testObs.assertValue { true } + } +} + + +// FILE: main.kt + +import lib.* + +class CreateEmployeeUseCaseTest { + fun testNormalName() { + val testObs = provideDomainSingle().test() + testObs.assertValue { true } + } +} + +fun box(): String { + return "OK" +} \ No newline at end of file diff --git a/compiler/testData/compileKotlinAgainstKotlin/nestedFunctionTypeAliasExpansion.kt b/compiler/testData/compileKotlinAgainstKotlin/nestedFunctionTypeAliasExpansion.kt new file mode 100644 index 00000000000..dd56222f2ed --- /dev/null +++ b/compiler/testData/compileKotlinAgainstKotlin/nestedFunctionTypeAliasExpansion.kt @@ -0,0 +1,17 @@ +// FILE: lib.kt + +package lib + +typealias Dispatch = (Msg) -> Unit +typealias Effect = (Dispatch) -> Unit + +fun noEffect(): Effect = TODO() + +// FILE: main.kt + +import lib.* + +fun box(): String { + val s = { noEffect() } + return "OK" +} \ No newline at end of file diff --git a/compiler/testData/compileKotlinAgainstKotlin/nestedTypeAliasExpansion.kt b/compiler/testData/compileKotlinAgainstKotlin/nestedTypeAliasExpansion.kt new file mode 100644 index 00000000000..4ec42b0eb62 --- /dev/null +++ b/compiler/testData/compileKotlinAgainstKotlin/nestedTypeAliasExpansion.kt @@ -0,0 +1,19 @@ +// FILE: lib.kt + +package lib + +class Inv + +typealias A = Inv +typealias B = Inv> + +fun materialize(): B? = null + +// FILE: main.kt + +import lib.* + +fun box(): String { + val s = { materialize() } + return "OK" +} \ No newline at end of file diff --git a/compiler/tests/org/jetbrains/kotlin/codegen/CompileKotlinAgainstKotlinTestGenerated.java b/compiler/tests/org/jetbrains/kotlin/codegen/CompileKotlinAgainstKotlinTestGenerated.java index 57f579db828..683a2c03ddd 100644 --- a/compiler/tests/org/jetbrains/kotlin/codegen/CompileKotlinAgainstKotlinTestGenerated.java +++ b/compiler/tests/org/jetbrains/kotlin/codegen/CompileKotlinAgainstKotlinTestGenerated.java @@ -213,6 +213,11 @@ public class CompileKotlinAgainstKotlinTestGenerated extends AbstractCompileKotl runTest("compiler/testData/compileKotlinAgainstKotlin/kt14012_multi.kt"); } + @TestMetadata("kt21775.kt") + public void testKt21775() throws Exception { + runTest("compiler/testData/compileKotlinAgainstKotlin/kt21775.kt"); + } + @TestMetadata("multifileClassInlineFunctionAccessingProperty.kt") public void testMultifileClassInlineFunctionAccessingProperty() throws Exception { runTest("compiler/testData/compileKotlinAgainstKotlin/multifileClassInlineFunctionAccessingProperty.kt"); @@ -233,11 +238,21 @@ public class CompileKotlinAgainstKotlinTestGenerated extends AbstractCompileKotl runTest("compiler/testData/compileKotlinAgainstKotlin/nestedEnum.kt"); } + @TestMetadata("nestedFunctionTypeAliasExpansion.kt") + public void testNestedFunctionTypeAliasExpansion() throws Exception { + runTest("compiler/testData/compileKotlinAgainstKotlin/nestedFunctionTypeAliasExpansion.kt"); + } + @TestMetadata("nestedObject.kt") public void testNestedObject() throws Exception { runTest("compiler/testData/compileKotlinAgainstKotlin/nestedObject.kt"); } + @TestMetadata("nestedTypeAliasExpansion.kt") + public void testNestedTypeAliasExpansion() throws Exception { + runTest("compiler/testData/compileKotlinAgainstKotlin/nestedTypeAliasExpansion.kt"); + } + @TestMetadata("optionalAnnotation.kt") public void testOptionalAnnotation() throws Exception { runTest("compiler/testData/compileKotlinAgainstKotlin/optionalAnnotation.kt");