Preserve type annotations on type parameter when substituting

Subsitute(@A T, T:@B String) = @B @A String

Nullability when loading Java:
Subsitute(@NotNull T, T:String) = @NotNull String
Subsitute(@NotNull T, T:String!) = @NotNull String
Subsitute(@NotNull T, T:String?) = @NotNull String

Subsitute(@Nullable T, T:String) = @Nullable String?
Subsitute(@Nullable T, T:String!) = @Nullable String?
Subsitute(@Nullable T, T:String?) = @Nullable String?
This commit is contained in:
Denis Zharkov
2015-07-14 14:20:39 +03:00
parent 2b541a560e
commit e23c7f457b
11 changed files with 128 additions and 10 deletions
@@ -69,6 +69,8 @@ class FilteredAnnotations(
class CompositeAnnotations(
private val delegates: List<Annotations>
) : Annotations {
constructor(vararg delegates: Annotations): this(delegates.toList())
override fun isEmpty() = delegates.all { it.isEmpty() }
override fun findAnnotation(fqName: FqName) = delegates.asSequence().map { it.findAnnotation(fqName) }.filterNotNull().firstOrNull()
@@ -20,6 +20,7 @@ import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.kotlin.builtins.KotlinBuiltIns;
import org.jetbrains.kotlin.descriptors.TypeParameterDescriptor;
import org.jetbrains.kotlin.descriptors.annotations.CompositeAnnotations;
import org.jetbrains.kotlin.resolve.calls.inference.InferencePackage;
import org.jetbrains.kotlin.resolve.scopes.SubstitutingScope;
import org.jetbrains.kotlin.types.typeUtil.TypeUtilPackage;
@@ -221,6 +222,14 @@ public class TypeSubstitutor {
substitutedType = TypeUtils.makeNullableIfNeeded(replacement.getType(), type.isMarkedNullable());
}
// substitutionType.annotations = replacement.annotations ++ type.annotations
if (!type.getAnnotations().isEmpty()) {
substitutedType = TypeUtilPackage.replaceAnnotations(
substitutedType,
new CompositeAnnotations(substitutedType.getAnnotations(), type.getAnnotations())
);
}
Variance resultingProjectionKind = varianceConflict == VarianceConflictType.NO_CONFLICT
? combine(originalProjectionKind, replacement.getProjectionKind())
: originalProjectionKind;