Synthetic extensions suggested in completion
This commit is contained in:
@@ -13,5 +13,6 @@
|
||||
<orderEntry type="module" module-name="deserialization" />
|
||||
<orderEntry type="module" module-name="descriptor.loader.java" exported="" />
|
||||
<orderEntry type="module" module-name="util" />
|
||||
<orderEntry type="module" module-name="util.runtime" />
|
||||
</component>
|
||||
</module>
|
||||
+39
-9
@@ -31,6 +31,8 @@ import org.jetbrains.kotlin.resolve.lazy.FileScopeProvider
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.storage.StorageManager
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.utils.addIfNotNull
|
||||
import java.util.*
|
||||
|
||||
interface SyntheticExtensionPropertyDescriptor : PropertyDescriptor {
|
||||
val getMethod: FunctionDescriptor
|
||||
@@ -50,12 +52,12 @@ class SyntheticExtensionsScope(storageManager: StorageManager) : JetScope by Jet
|
||||
|
||||
private fun syntheticPropertyInClass(javaClass: JavaClassDescriptor, type: JetType, name: Name): PropertyDescriptor? {
|
||||
val memberScope = javaClass.getMemberScope(type.getArguments())
|
||||
val getMethod = memberScope.getFunctions(name.toGetMethodName()).singleOrNull {
|
||||
val getMethod = memberScope.getFunctions(toGetMethodName(name)).singleOrNull {
|
||||
it.getValueParameters().isEmpty() && it.getTypeParameters().isEmpty() && it.getVisibility() == Visibilities.PUBLIC //TODO: what about protected and package-local?
|
||||
} ?: return null
|
||||
|
||||
val propertyType = getMethod.getReturnType() ?: return null
|
||||
val setMethod = memberScope.getFunctions(name.toSetMethodName()).singleOrNull {
|
||||
val setMethod = memberScope.getFunctions(toSetMethodName(name)).singleOrNull {
|
||||
it.getValueParameters().singleOrNull()?.getType() == propertyType
|
||||
&& it.getTypeParameters().isEmpty()
|
||||
&& it.getReturnType()?.let { KotlinBuiltIns.isUnit(it) } ?: false
|
||||
@@ -68,10 +70,10 @@ class SyntheticExtensionsScope(storageManager: StorageManager) : JetScope by Jet
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor> {
|
||||
if (name.isSpecial()) return emptyList()
|
||||
if (name.getIdentifier()[0].isUpperCase()) return emptyList()
|
||||
return collectSyntheticProperties(null, receiverType, name) ?: emptyList()
|
||||
return collectSyntheticPropertiesByName(null, receiverType, name) ?: emptyList()
|
||||
}
|
||||
|
||||
private fun collectSyntheticProperties(result: SmartList<PropertyDescriptor>?, type: JetType, name: Name): SmartList<PropertyDescriptor>? {
|
||||
private fun collectSyntheticPropertiesByName(result: SmartList<PropertyDescriptor>?, type: JetType, name: Name): SmartList<PropertyDescriptor>? {
|
||||
@suppress("NAME_SHADOWING")
|
||||
var result = result
|
||||
|
||||
@@ -81,11 +83,32 @@ class SyntheticExtensionsScope(storageManager: StorageManager) : JetScope by Jet
|
||||
result = result.add(syntheticPropertyInClass(Triple(classifier, type, name)))
|
||||
}
|
||||
|
||||
typeConstructor.getSupertypes().forEach { result = collectSyntheticProperties(result, it, name) }
|
||||
typeConstructor.getSupertypes().forEach { result = collectSyntheticPropertiesByName(result, it, name) }
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor> {
|
||||
val result = ArrayList<PropertyDescriptor>()
|
||||
result.collectSyntheticProperties(receiverType)
|
||||
return result
|
||||
}
|
||||
|
||||
private fun MutableList<PropertyDescriptor>.collectSyntheticProperties(type: JetType) {
|
||||
val typeConstructor = type.getConstructor()
|
||||
val classifier = typeConstructor.getDeclarationDescriptor()
|
||||
if (classifier is JavaClassDescriptor) {
|
||||
for (descriptor in classifier.getMemberScope(type.getArguments()).getAllDescriptors()) {
|
||||
if (descriptor is FunctionDescriptor) {
|
||||
val propertyName = fromGetMethodName(descriptor.getName()) ?: continue
|
||||
addIfNotNull(syntheticPropertyInClass(classifier, type, propertyName))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
typeConstructor.getSupertypes().forEach { collectSyntheticProperties(it) }
|
||||
}
|
||||
|
||||
private fun SmartList<PropertyDescriptor>?.add(property: PropertyDescriptor?): SmartList<PropertyDescriptor>? {
|
||||
if (property == null) return this
|
||||
val list = if (this != null) this else SmartList()
|
||||
@@ -96,12 +119,19 @@ class SyntheticExtensionsScope(storageManager: StorageManager) : JetScope by Jet
|
||||
//TODO: "is"?
|
||||
//TODO: methods like "getURL"?
|
||||
//TODO: reuse code with generation?
|
||||
private fun Name.toGetMethodName(): Name {
|
||||
return Name.identifier("get" + getIdentifier().capitalize())
|
||||
private fun toGetMethodName(propertyName: Name): Name {
|
||||
return Name.identifier("get" + propertyName.getIdentifier().capitalize())
|
||||
}
|
||||
|
||||
private fun Name.toSetMethodName(): Name {
|
||||
return Name.identifier("set" + getIdentifier().capitalize())
|
||||
private fun toSetMethodName(propertyName: Name): Name {
|
||||
return Name.identifier("set" + propertyName.getIdentifier().capitalize())
|
||||
}
|
||||
|
||||
private fun fromGetMethodName(methodName: Name): Name? {
|
||||
if (methodName.isSpecial()) return null
|
||||
val identifier = methodName.getIdentifier()
|
||||
if (!identifier.startsWith("get")) return null
|
||||
return Name.identifier(identifier.removePrefix("get").decapitalize())
|
||||
}
|
||||
|
||||
private class MyPropertyDescriptor(
|
||||
|
||||
@@ -57,6 +57,10 @@ class AllUnderImportsScope : JetScope {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverType, name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor> {
|
||||
return scopes.flatMap { it.getSyntheticExtensionProperties(receiverType) }
|
||||
}
|
||||
|
||||
override fun getPackage(name: Name): PackageViewDescriptor? = null // packages are not imported by all under imports
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
|
||||
@@ -19,11 +19,11 @@ package org.jetbrains.kotlin.resolve
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScopeImpl
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.utils.Printer
|
||||
|
||||
class SingleImportScope(private val aliasName: Name, private val descriptors: Collection<DeclarationDescriptor>) : JetScope {
|
||||
class SingleImportScope(private val aliasName: Name, private val descriptors: Collection<DeclarationDescriptor>) : JetScopeImpl() {
|
||||
override fun getClassifier(name: Name)
|
||||
= if (name == aliasName) descriptors.filterIsInstance<ClassifierDescriptor>().singleOrNull() else null
|
||||
|
||||
@@ -36,20 +36,10 @@ class SingleImportScope(private val aliasName: Name, private val descriptors: Co
|
||||
override fun getFunctions(name: Name)
|
||||
= if (name == aliasName) descriptors.filterIsInstance<FunctionDescriptor>() else emptyList()
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor> = emptyList()
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
|
||||
override fun getContainingDeclaration(): DeclarationDescriptor = throw UnsupportedOperationException()
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = emptyList()
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter, nameFilter: (Name) -> Boolean) = descriptors
|
||||
|
||||
override fun getImplicitReceiversHierarchy(): List<ReceiverParameterDescriptor> = emptyList()
|
||||
|
||||
override fun getOwnDeclaredDescriptors(): Collection<DeclarationDescriptor> = emptyList()
|
||||
|
||||
override fun printScopeStructure(p: Printer) {
|
||||
p.println(javaClass.getSimpleName(), ": ", aliasName)
|
||||
}
|
||||
|
||||
@@ -260,6 +260,17 @@ class LazyImportScope(
|
||||
return importResolver.collectFromImports(name, LookupMode.EVERYTHING) { scope, name -> scope.getSyntheticExtensionProperties(receiverType, name) }
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor> {
|
||||
// we do not perform any filtering by visibility here because all descriptors from both visible/invisible filter scopes are to be added anyway
|
||||
if (filteringKind == FilteringKind.INVISIBLE_CLASSES) return listOf()
|
||||
|
||||
return importResolver.resolveSession.getStorageManager().compute {
|
||||
importResolver.indexedImports.imports.flatMapTo(LinkedHashSet<VariableDescriptor>()) { import ->
|
||||
importResolver.getImportScope(import, LookupMode.EVERYTHING).getSyntheticExtensionProperties(receiverType)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = listOf()
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter, nameFilter: (Name) -> Boolean): Collection<DeclarationDescriptor> {
|
||||
|
||||
+2
-9
@@ -28,6 +28,7 @@ import org.jetbrains.kotlin.resolve.lazy.data.JetScriptInfo
|
||||
import org.jetbrains.kotlin.resolve.lazy.declarations.DeclarationProvider
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScopeImpl
|
||||
import org.jetbrains.kotlin.storage.MemoizedFunctionToNotNull
|
||||
import org.jetbrains.kotlin.storage.StorageManager
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
@@ -41,7 +42,7 @@ protected constructor(
|
||||
protected val declarationProvider: DP,
|
||||
protected val thisDescriptor: D,
|
||||
protected val trace: BindingTrace
|
||||
) : JetScope {
|
||||
) : JetScopeImpl() {
|
||||
|
||||
protected val storageManager: StorageManager = c.storageManager
|
||||
private val classDescriptors: MemoizedFunctionToNotNull<Name, List<ClassDescriptor>> = storageManager.createMemoizedFunction { resolveClassDescriptor(it) }
|
||||
@@ -111,12 +112,6 @@ protected constructor(
|
||||
|
||||
protected abstract fun getNonDeclaredProperties(name: Name, result: MutableSet<VariableDescriptor>)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = listOf<VariableDescriptor>()
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name) = setOf<DeclarationDescriptor>()
|
||||
|
||||
protected fun computeDescriptorsFromDeclaredElements(kindFilter: DescriptorKindFilter,
|
||||
nameFilter: (Name) -> Boolean): List<DeclarationDescriptor> {
|
||||
val declarations = declarationProvider.getDeclarations(kindFilter, nameFilter)
|
||||
@@ -163,8 +158,6 @@ protected constructor(
|
||||
return result.toReadOnlyList()
|
||||
}
|
||||
|
||||
override fun getImplicitReceiversHierarchy() = listOf<ReceiverParameterDescriptor>()
|
||||
|
||||
// Do not change this, override in concrete subclasses:
|
||||
// it is very easy to compromise laziness of this class, and fail all the debugging
|
||||
// a generic implementation can't do this properly
|
||||
|
||||
+2
-6
@@ -39,6 +39,7 @@ import org.jetbrains.kotlin.resolve.jvm.PLATFORM_TYPES
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindExclude.NonExtensions
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScopeImpl
|
||||
import org.jetbrains.kotlin.storage.NotNullLazyValue
|
||||
import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.types.TypeUtils
|
||||
@@ -51,7 +52,7 @@ import java.util.LinkedHashSet
|
||||
public abstract class LazyJavaMemberScope(
|
||||
protected val c: LazyJavaResolverContext,
|
||||
private val containingDeclaration: DeclarationDescriptor
|
||||
) : JetScope {
|
||||
) : JetScopeImpl() {
|
||||
// this lazy value is not used at all in LazyPackageFragmentScopeForJavaPackage because we do not use caching there
|
||||
// but is placed in the base class to not duplicate code
|
||||
private val allDescriptors = c.storageManager.createRecursionTolerantLazyValue<Collection<DeclarationDescriptor>>(
|
||||
@@ -297,11 +298,6 @@ public abstract class LazyJavaMemberScope(
|
||||
|
||||
override fun getProperties(name: Name): Collection<VariableDescriptor> = properties(name)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = listOf<VariableDescriptor>()
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
override fun getDeclarationsByLabel(labelName: Name) = listOf<DeclarationDescriptor>()
|
||||
|
||||
override fun getOwnDeclaredDescriptors() = getDescriptors()
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter,
|
||||
|
||||
@@ -51,6 +51,10 @@ public abstract class AbstractScopeAdapter : JetScope {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverType, name)
|
||||
}
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor> {
|
||||
return workerScope.getSyntheticExtensionProperties(receiverType)
|
||||
}
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? {
|
||||
return workerScope.getLocalVariable(name)
|
||||
}
|
||||
|
||||
@@ -68,6 +68,9 @@ public open class ChainedScope(
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverType, name) }
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor>
|
||||
= getFromAllScopes { it.getSyntheticExtensionProperties(receiverType) }
|
||||
|
||||
override fun getImplicitReceiversHierarchy(): List<ReceiverParameterDescriptor> {
|
||||
if (implicitReceiverHierarchy == null) {
|
||||
val result = ArrayList<ReceiverParameterDescriptor>()
|
||||
@@ -82,12 +85,8 @@ public open class ChainedScope(
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name) = scopeChain.flatMap { it.getDeclarationsByLabel(labelName) }
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter,
|
||||
nameFilter: (Name) -> Boolean): Collection<DeclarationDescriptor> {
|
||||
val result = LinkedHashSet<DeclarationDescriptor>()
|
||||
scopeChain.flatMapTo(result) { it.getDescriptors(kindFilter, nameFilter) }
|
||||
return result
|
||||
}
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter, nameFilter: (Name) -> Boolean)
|
||||
= getFromAllScopes { it.getDescriptors(kindFilter, nameFilter) }
|
||||
|
||||
override fun getOwnDeclaredDescriptors(): Collection<DeclarationDescriptor> {
|
||||
throw UnsupportedOperationException()
|
||||
|
||||
@@ -22,29 +22,19 @@ import org.jetbrains.kotlin.types.JetType
|
||||
import org.jetbrains.kotlin.utils.Printer
|
||||
import org.jetbrains.kotlin.utils.addToStdlib.firstIsInstanceOrNull
|
||||
|
||||
public class ExplicitImportsScope(private val descriptors: Collection<DeclarationDescriptor>) : JetScope {
|
||||
public class ExplicitImportsScope(private val descriptors: Collection<DeclarationDescriptor>) : JetScopeImpl() {
|
||||
override fun getClassifier(name: Name) = descriptors.filter { it.getName() == name }.firstIsInstanceOrNull<ClassifierDescriptor>()
|
||||
|
||||
override fun getPackage(name: Name)= descriptors.filter { it.getName() == name }.firstIsInstanceOrNull<PackageViewDescriptor>()
|
||||
|
||||
override fun getProperties(name: Name) = descriptors.filter { it.getName() == name }.filterIsInstance<VariableDescriptor>()
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
|
||||
override fun getFunctions(name: Name) = descriptors.filter { it.getName() == name }.filterIsInstance<FunctionDescriptor>()
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor> = listOf()
|
||||
|
||||
override fun getContainingDeclaration() = throw UnsupportedOperationException()
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name) = emptyList<DeclarationDescriptor>()
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter, nameFilter: (Name) -> Boolean) = descriptors
|
||||
|
||||
override fun getImplicitReceiversHierarchy() = emptyList<ReceiverParameterDescriptor>()
|
||||
|
||||
override fun getOwnDeclaredDescriptors() = emptyList<DeclarationDescriptor>()
|
||||
|
||||
override fun printScopeStructure(p: Printer) {
|
||||
p.println(javaClass.getName())
|
||||
}
|
||||
|
||||
@@ -38,6 +38,8 @@ public class FilteringScope(private val workerScope: JetScope, private val predi
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = workerScope.getSyntheticExtensionProperties(receiverType, name).filter(predicate)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType) = workerScope.getSyntheticExtensionProperties(receiverType).filter(predicate)
|
||||
|
||||
override fun getLocalVariable(name: Name) = filterDescriptor(workerScope.getLocalVariable(name))
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter,
|
||||
|
||||
@@ -37,6 +37,8 @@ public trait JetScope {
|
||||
|
||||
public fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor>
|
||||
|
||||
public fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor>
|
||||
|
||||
public fun getContainingDeclaration(): DeclarationDescriptor
|
||||
|
||||
public fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor>
|
||||
|
||||
@@ -34,6 +34,8 @@ public abstract class JetScopeImpl : JetScope {
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name): Collection<VariableDescriptor> = listOf()
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType): Collection<VariableDescriptor> = listOf()
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = listOf()
|
||||
|
||||
override fun getDescriptors(kindFilter: DescriptorKindFilter,
|
||||
|
||||
+1
-7
@@ -27,7 +27,7 @@ import kotlin.properties.Delegates
|
||||
|
||||
public class StaticScopeForKotlinClass(
|
||||
private val containingClass: ClassDescriptor
|
||||
) : JetScope {
|
||||
) : JetScopeImpl() {
|
||||
override fun getClassifier(name: Name) = null // TODO
|
||||
|
||||
private val functions: List<FunctionDescriptor> by Delegates.lazy {
|
||||
@@ -46,13 +46,7 @@ public class StaticScopeForKotlinClass(
|
||||
|
||||
override fun getFunctions(name: Name) = functions.filterTo(ArrayList<FunctionDescriptor>(2)) { it.getName() == name }
|
||||
|
||||
override fun getPackage(name: Name) = null
|
||||
override fun getProperties(name: Name) = listOf<VariableDescriptor>()
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = listOf<VariableDescriptor>()
|
||||
override fun getLocalVariable(name: Name) = null
|
||||
override fun getContainingDeclaration() = containingClass
|
||||
override fun getDeclarationsByLabel(labelName: Name) = listOf<DeclarationDescriptor>()
|
||||
override fun getImplicitReceiversHierarchy() = listOf<ReceiverParameterDescriptor>()
|
||||
|
||||
override fun printScopeStructure(p: Printer) {
|
||||
p.println("Static scope for $containingClass")
|
||||
|
||||
@@ -71,6 +71,8 @@ public class SubstitutingScope(private val workerScope: JetScope, private val su
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = substitute(workerScope.getSyntheticExtensionProperties(receiverType, name))
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType) = substitute(workerScope.getSyntheticExtensionProperties(receiverType))
|
||||
|
||||
override fun getPackage(name: Name) = workerScope.getPackage(name)
|
||||
|
||||
override fun getImplicitReceiversHierarchy(): List<ReceiverParameterDescriptor> {
|
||||
|
||||
@@ -99,6 +99,12 @@ public class ErrorUtils {
|
||||
return ERROR_PROPERTY_GROUP;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<VariableDescriptor> getSyntheticExtensionProperties(@NotNull JetType receiverType) {
|
||||
return ERROR_PROPERTY_GROUP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public VariableDescriptor getLocalVariable(@NotNull Name name) {
|
||||
return ERROR_PROPERTY;
|
||||
@@ -209,6 +215,12 @@ public class ErrorUtils {
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<VariableDescriptor> getSyntheticExtensionProperties(@NotNull JetType receiverType) {
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public DeclarationDescriptor getContainingDeclaration() {
|
||||
|
||||
+2
-10
@@ -19,7 +19,7 @@ package org.jetbrains.kotlin.serialization.deserialization.descriptors
|
||||
import org.jetbrains.kotlin.descriptors.*
|
||||
import org.jetbrains.kotlin.name.Name
|
||||
import org.jetbrains.kotlin.resolve.scopes.DescriptorKindFilter
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScope
|
||||
import org.jetbrains.kotlin.resolve.scopes.JetScopeImpl
|
||||
import org.jetbrains.kotlin.serialization.Flags
|
||||
import org.jetbrains.kotlin.serialization.ProtoBuf
|
||||
import org.jetbrains.kotlin.serialization.ProtoBuf.Callable.CallableKind
|
||||
@@ -34,7 +34,7 @@ import java.util.LinkedHashSet
|
||||
public abstract class DeserializedMemberScope protected constructor(
|
||||
protected val c: DeserializationContext,
|
||||
membersList: Collection<ProtoBuf.Callable>
|
||||
) : JetScope {
|
||||
) : JetScopeImpl() {
|
||||
|
||||
private data class ProtoKey(val name: Name, val kind: Kind, val isExtension: Boolean)
|
||||
private enum class Kind { FUNCTION, PROPERTY }
|
||||
@@ -112,16 +112,8 @@ public abstract class DeserializedMemberScope protected constructor(
|
||||
|
||||
protected abstract fun addClassDescriptors(result: MutableCollection<DeclarationDescriptor>, nameFilter: (Name) -> Boolean)
|
||||
|
||||
override fun getSyntheticExtensionProperties(receiverType: JetType, name: Name) = listOf<VariableDescriptor>()
|
||||
|
||||
override fun getPackage(name: Name): PackageViewDescriptor? = null
|
||||
|
||||
override fun getLocalVariable(name: Name): VariableDescriptor? = null
|
||||
|
||||
override fun getContainingDeclaration() = c.containingDeclaration
|
||||
|
||||
override fun getDeclarationsByLabel(labelName: Name): Collection<DeclarationDescriptor> = listOf()
|
||||
|
||||
protected fun computeDescriptors(kindFilter: DescriptorKindFilter,
|
||||
nameFilter: (Name) -> Boolean): Collection<DeclarationDescriptor> {
|
||||
//NOTE: descriptors should be in the same order they were serialized in
|
||||
|
||||
+29
-21
@@ -88,6 +88,8 @@ public class ReferenceVariantsHelper(
|
||||
|
||||
val descriptors = LinkedHashSet<DeclarationDescriptor>()
|
||||
|
||||
val dataFlowInfo = context.getDataFlowInfo(expression)
|
||||
|
||||
val pair = getExplicitReceiverData(expression)
|
||||
if (pair != null) {
|
||||
val (receiverExpression, callType) = pair
|
||||
@@ -104,25 +106,17 @@ public class ReferenceVariantsHelper(
|
||||
context.getType(receiverExpression)
|
||||
if (expressionType != null && !expressionType.isError()) {
|
||||
val receiverValue = ExpressionReceiver(receiverExpression, expressionType)
|
||||
val dataFlowInfo = context.getDataFlowInfo(expression)
|
||||
|
||||
for (variant in SmartCastUtils.getSmartCastVariantsWithLessSpecificExcluded(receiverValue, context, containingDeclaration, dataFlowInfo)) {
|
||||
descriptors.addMembersFromReceiver(variant, callType, kindFilter, nameFilter)
|
||||
}
|
||||
descriptors.addMembersFromReceiverAndSyntheticExtensions(receiverValue, callType, kindFilter, nameFilter, resolutionScope, dataFlowInfo)
|
||||
|
||||
descriptors.addCallableExtensions(resolutionScope, receiverValue, dataFlowInfo, callType, kindFilter, nameFilter)
|
||||
}
|
||||
}
|
||||
else {
|
||||
val dataFlowInfo = context.getDataFlowInfo(expression)
|
||||
|
||||
// process instance members that can be called via implicit receiver's instances
|
||||
val receivers = resolutionScope.getImplicitReceiversWithInstance()
|
||||
val receiverValues = receivers.map { it.getValue() }
|
||||
for (receiverValue in receiverValues) {
|
||||
for (variant in SmartCastUtils.getSmartCastVariantsWithLessSpecificExcluded(receiverValue, context, containingDeclaration, dataFlowInfo)) {
|
||||
descriptors.addMembersFromReceiver(variant, CallType.NORMAL, kindFilter, nameFilter)
|
||||
}
|
||||
descriptors.addMembersFromReceiverAndSyntheticExtensions(receiverValue, CallType.NORMAL, kindFilter, nameFilter, resolutionScope, dataFlowInfo)
|
||||
}
|
||||
|
||||
// process extensions and non-instance members
|
||||
@@ -143,22 +137,36 @@ public class ReferenceVariantsHelper(
|
||||
return descriptors
|
||||
}
|
||||
|
||||
private fun MutableCollection<DeclarationDescriptor>.addMembersFromReceiver(
|
||||
receiverType: JetType,
|
||||
private fun MutableSet<DeclarationDescriptor>.addMembersFromReceiverAndSyntheticExtensions(
|
||||
receiverValue: ReceiverValue,
|
||||
callType: CallType,
|
||||
kindFilter: DescriptorKindFilter,
|
||||
nameFilter: (Name) -> Boolean
|
||||
nameFilter: (Name) -> Boolean,
|
||||
resolutionScope: JetScope,
|
||||
dataFlowInfo: DataFlowInfo
|
||||
) {
|
||||
var memberFilter = kindFilter exclude DescriptorKindExclude.Extensions
|
||||
val members = receiverType.getMemberScope().getDescriptorsFiltered(DescriptorKindFilter.ALL, nameFilter) // filter by kind later because of constructors
|
||||
for (member in members) {
|
||||
if (member is ClassDescriptor) {
|
||||
if (member.isInner()) {
|
||||
member.getConstructors().filterTo(this) { callType.canCall(it) && memberFilter.accepts(it) }
|
||||
val memberFilter = kindFilter exclude DescriptorKindExclude.Extensions
|
||||
val containingDeclaration = resolutionScope.getContainingDeclaration()
|
||||
|
||||
for (receiverType in SmartCastUtils.getSmartCastVariantsWithLessSpecificExcluded(receiverValue, context, containingDeclaration, dataFlowInfo)) {
|
||||
val members = receiverType.getMemberScope().getDescriptorsFiltered(DescriptorKindFilter.ALL, nameFilter) // filter by kind later because of constructors
|
||||
for (member in members) {
|
||||
if (member is ClassDescriptor) {
|
||||
if (member.isInner()) {
|
||||
member.getConstructors().filterTo(this) { callType.canCall(it) && memberFilter.accepts(it) }
|
||||
}
|
||||
}
|
||||
else if (callType.canCall(member) && memberFilter.accepts(member)) {
|
||||
this.add(member)
|
||||
}
|
||||
}
|
||||
else if (callType.canCall(member) && memberFilter.accepts(member)) {
|
||||
this.add(member)
|
||||
|
||||
if (!kindFilter.excludes.contains(DescriptorKindExclude.Extensions)) {
|
||||
for (extension in resolutionScope.getSyntheticExtensionProperties(receiverType)) {
|
||||
if (nameFilter(extension.getName()) && kindFilter.accepts(extension)) {
|
||||
addAll(extension.substituteExtensionIfCallable(receiverValue, callType, context, dataFlowInfo, containingDeclaration))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+12
-8
@@ -217,16 +217,20 @@ public class LookupElementFactory(
|
||||
|
||||
if (descriptor is CallableDescriptor) {
|
||||
if (descriptor.getExtensionReceiverParameter() != null) {
|
||||
val container = descriptor.getContainingDeclaration()
|
||||
val containerPresentation = if (container is ClassDescriptor) {
|
||||
DescriptorUtils.getFqNameFromTopLevelClass(container).toString()
|
||||
}
|
||||
else {
|
||||
DescriptorUtils.getFqName(container).toString()
|
||||
}
|
||||
val originalReceiver = descriptor.getOriginal().getExtensionReceiverParameter()!!
|
||||
val receiverPresentation = DescriptorRenderer.SHORT_NAMES_IN_TYPES.renderType(originalReceiver.getType())
|
||||
element = element.appendTailText(" for $receiverPresentation in $containerPresentation", true)
|
||||
element = element.appendTailText(" for $receiverPresentation", true)
|
||||
|
||||
val container = descriptor.getContainingDeclaration()
|
||||
val containerPresentation = if (container is ClassDescriptor)
|
||||
DescriptorUtils.getFqNameFromTopLevelClass(container).toString()
|
||||
else if (container is PackageFragmentDescriptor)
|
||||
container.fqName.toString()
|
||||
else
|
||||
null
|
||||
if (containerPresentation != null) {
|
||||
element = element.appendTailText(" in $containerPresentation", true)
|
||||
}
|
||||
}
|
||||
else {
|
||||
val container = descriptor.getContainingDeclaration()
|
||||
|
||||
@@ -3,6 +3,8 @@ package a.b
|
||||
class Some {
|
||||
inner class Inner {
|
||||
fun foo() {
|
||||
fun String.localExtension() = 1
|
||||
|
||||
"".<caret>
|
||||
}
|
||||
|
||||
@@ -19,3 +21,4 @@ val String.extProp: Int get() = 1
|
||||
// EXIST: { lookupString: "extProp", itemText: "extProp", tailText: " for String in a.b", typeText: "Int" }
|
||||
// EXIST: { lookupString: "memberExtFun", itemText: "memberExtFun", tailText: "() for String in Some.Inner", typeText: "Unit" }
|
||||
// EXIST: { lookupString: "memberExtProp", itemText: "memberExtProp", tailText: " for String in Some", typeText: "Int" }
|
||||
// EXIST: { lookupString: "localExtension", itemText: "localExtension", tailText: "() for String", typeText: "Int" }
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
import java.io.File
|
||||
|
||||
fun foo(file: File) {
|
||||
file.<caret>
|
||||
}
|
||||
|
||||
// EXIST_JAVA_ONLY: { lookupString: "absolutePath", itemText: "absolutePath", tailText: " for File", typeText: "String!" }
|
||||
@@ -0,0 +1,7 @@
|
||||
import java.io.File
|
||||
|
||||
fun File.foo() {
|
||||
<caret>
|
||||
}
|
||||
|
||||
// EXIST_JAVA_ONLY: { lookupString: "absolutePath", itemText: "absolutePath", tailText: " for File", typeText: "String!" }
|
||||
@@ -0,0 +1,7 @@
|
||||
import java.io.File
|
||||
|
||||
fun foo(file: File) {
|
||||
file.abs<caret>
|
||||
}
|
||||
|
||||
// ELEMENT: absolutePath
|
||||
@@ -0,0 +1,7 @@
|
||||
import java.io.File
|
||||
|
||||
fun foo(file: File) {
|
||||
file.absolutePath<caret>
|
||||
}
|
||||
|
||||
// ELEMENT: absolutePath
|
||||
+12
@@ -1209,6 +1209,18 @@ public class JSBasicCompletionTestGenerated extends AbstractJSBasicCompletionTes
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SyntheticExtensions1.kt")
|
||||
public void testSyntheticExtensions1() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/SyntheticExtensions1.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SyntheticExtensions2.kt")
|
||||
public void testSyntheticExtensions2() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/SyntheticExtensions2.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("WrongExplicitReceiver.kt")
|
||||
public void testWrongExplicitReceiver() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/WrongExplicitReceiver.kt");
|
||||
|
||||
+12
@@ -1209,6 +1209,18 @@ public class JvmBasicCompletionTestGenerated extends AbstractJvmBasicCompletionT
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SyntheticExtensions1.kt")
|
||||
public void testSyntheticExtensions1() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/SyntheticExtensions1.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SyntheticExtensions2.kt")
|
||||
public void testSyntheticExtensions2() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/SyntheticExtensions2.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("WrongExplicitReceiver.kt")
|
||||
public void testWrongExplicitReceiver() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/basic/common/extensions/WrongExplicitReceiver.kt");
|
||||
|
||||
+6
@@ -119,6 +119,12 @@ public class BasicCompletionHandlerTestGenerated extends AbstractBasicCompletion
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("SyntheticExtension.kt")
|
||||
public void testSyntheticExtension() throws Exception {
|
||||
String fileName = JetTestUtils.navigationMetadata("idea/idea-completion/testData/handlers/basic/SyntheticExtension.kt");
|
||||
doTest(fileName);
|
||||
}
|
||||
|
||||
@TestMetadata("idea/idea-completion/testData/handlers/basic/exclChar")
|
||||
@TestDataPath("$PROJECT_ROOT")
|
||||
@RunWith(JUnit3RunnerWithInners.class)
|
||||
|
||||
Reference in New Issue
Block a user