diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/KtAnalysisSession.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/KtAnalysisSession.kt index 5f0ee715544..4c4c866000f 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/KtAnalysisSession.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/KtAnalysisSession.kt @@ -5,24 +5,9 @@ package org.jetbrains.kotlin.idea.frontend.api -import com.intellij.openapi.util.TextRange -import com.intellij.psi.PsiElement -import org.jetbrains.kotlin.idea.frontend.api.calls.KtCall import org.jetbrains.kotlin.idea.frontend.api.components.* -import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnostic -import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnosticWithPsi -import org.jetbrains.kotlin.idea.frontend.api.scopes.* import org.jetbrains.kotlin.idea.frontend.api.symbols.* -import org.jetbrains.kotlin.idea.frontend.api.symbols.markers.KtSymbolWithDeclarations -import org.jetbrains.kotlin.idea.frontend.api.symbols.markers.KtSymbolWithKind -import org.jetbrains.kotlin.idea.frontend.api.symbols.markers.KtSymbolWithMembers import org.jetbrains.kotlin.idea.frontend.api.symbols.pointers.KtSymbolPointer -import org.jetbrains.kotlin.idea.frontend.api.types.KtType -import org.jetbrains.kotlin.idea.references.KtReference -import org.jetbrains.kotlin.idea.references.KtSimpleReference -import org.jetbrains.kotlin.name.ClassId -import org.jetbrains.kotlin.name.FqName -import org.jetbrains.kotlin.name.Name import org.jetbrains.kotlin.psi.* /** @@ -37,175 +22,69 @@ import org.jetbrains.kotlin.psi.* * * To create analysis session consider using [analyze] */ -abstract class KtAnalysisSession(final override val token: ValidityToken) : ValidityTokenOwner { - protected abstract val smartCastProvider: KtSmartCastProvider - protected abstract val diagnosticProvider: KtDiagnosticProvider - protected abstract val scopeProvider: KtScopeProvider - protected abstract val containingDeclarationProvider: KtSymbolContainingDeclarationProvider - protected abstract val symbolProvider: KtSymbolProvider - protected abstract val callResolver: KtCallResolver - protected abstract val completionCandidateChecker: KtCompletionCandidateChecker - protected abstract val symbolDeclarationOverridesProvider: KtSymbolDeclarationOverridesProvider - protected abstract val referenceShortener: KtReferenceShortener +abstract class KtAnalysisSession(final override val token: ValidityToken) : ValidityTokenOwner, + KtSmartCastProviderMixIn, + KtCallResolverMixIn, + KtDiagnosticProviderMixIn, + KtScopeProviderMixIn, + KtCompletionCandidateCheckerMixIn, + KtTypeRendererMixIn, + KtSymbolDeclarationOverridesProviderMixIn, + KtExpressionTypeProviderMixIn, + KtTypeProviderMixIn, + KtSymbolProviderMixIn, + KtSymbolContainingDeclarationProviderMixIn, + KtSubtypingComponentMixIn, + KtExpressionInfoProviderMixIn, + KtSymbolsMixIn, + KtReferenceResolveMixIn, + KtReferenceShortenerMixIn { - @Suppress("LeakingThis") - - protected open val typeRenderer: KtTypeRenderer = KtDefaultTypeRenderer(this, token) - protected abstract val expressionTypeProvider: KtExpressionTypeProvider - protected abstract val typeProvider: KtTypeProvider - protected abstract val subtypingComponent: KtSubtypingComponent - protected abstract val expressionHandlingComponent: KtExpressionHandlingComponent + override val analysisSession: KtAnalysisSession get() = this abstract fun createContextDependentCopy(originalKtFile: KtFile, fakeKtElement: KtElement): KtAnalysisSession + internal val smartCastProvider: KtSmartCastProvider get() = smartCastProviderImpl + protected abstract val smartCastProviderImpl: KtSmartCastProvider - /** - * Return a list of **all** symbols which are overridden by symbol - * - * E.g, if we have `A.foo` overrides `B.foo` overrides `C.foo`, all two super declarations `B.foo`, `C.foo` will be returned - * - * Unwraps substituted overridden symbols (see [org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin.INTERSECTION_OVERRIDE]) - * - * @see getDirectlyOverriddenSymbols - */ - fun KtCallableSymbol.getAllOverriddenSymbols(): List = - symbolDeclarationOverridesProvider.getAllOverriddenSymbols(this) + internal val diagnosticProvider: KtDiagnosticProvider get() = diagnosticProviderImpl + protected abstract val diagnosticProviderImpl: KtDiagnosticProvider - /** - * Return a list of symbols which are **directly** overridden by symbol - ** - * E.g, if we have `A.foo` overrides `B.foo` overrides `C.foo`, only declarations directly overriden `B.foo` will be returned - * - * Unwraps substituted overridden symbols (see [org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin.INTERSECTION_OVERRIDE]) - * - * @see getAllOverriddenSymbols - */ - fun KtCallableSymbol.getDirectlyOverriddenSymbols(): List = - symbolDeclarationOverridesProvider.getDirectlyOverriddenSymbols(this) + internal val scopeProvider: KtScopeProvider get() = scopeProviderImpl + protected abstract val scopeProviderImpl: KtScopeProvider - fun KtCallableSymbol.getIntersectionOverriddenSymbols(): Collection = - symbolDeclarationOverridesProvider.getIntersectionOverriddenSymbols(this) + internal val containingDeclarationProvider: KtSymbolContainingDeclarationProvider get() = containingDeclarationProviderImpl + protected abstract val containingDeclarationProviderImpl: KtSymbolContainingDeclarationProvider - fun KtExpression.getSmartCast(): KtType? = smartCastProvider.getSmartCastedToType(this) + internal val symbolProvider: KtSymbolProvider get() = symbolProviderImpl + protected abstract val symbolProviderImpl: KtSymbolProvider - fun KtExpression.getImplicitReceiverSmartCast(): Collection = - smartCastProvider.getImplicitReceiverSmartCast(this) + internal val callResolver: KtCallResolver get() = callResolverImpl + protected abstract val callResolverImpl: KtCallResolver - fun KtExpression.getKtType(): KtType = expressionTypeProvider.getKtExpressionType(this) + internal val completionCandidateChecker: KtCompletionCandidateChecker get() = completionCandidateCheckerImpl + protected abstract val completionCandidateCheckerImpl: KtCompletionCandidateChecker - fun KtDeclaration.getReturnKtType(): KtType = expressionTypeProvider.getReturnTypeForKtDeclaration(this) + internal val symbolDeclarationOverridesProvider: KtSymbolDeclarationOverridesProvider get() = symbolDeclarationOverridesProviderImpl + protected abstract val symbolDeclarationOverridesProviderImpl: KtSymbolDeclarationOverridesProvider - infix fun KtType.isEqualTo(other: KtType): Boolean = subtypingComponent.isEqualTo(this, other) + internal val referenceShortener: KtReferenceShortener get() = referenceShortenerImpl + protected abstract val referenceShortenerImpl: KtReferenceShortener - infix fun KtType.isSubTypeOf(superType: KtType): Boolean = subtypingComponent.isSubTypeOf(this, superType) - infix fun KtType.isNotSubTypeOf(superType: KtType): Boolean = !subtypingComponent.isSubTypeOf(this, superType) + @Suppress("LeakingThis") + protected open val typeRendererImpl: KtTypeRenderer = KtDefaultTypeRenderer(this, token) + internal val typeRenderer: KtTypeRenderer get() = typeRendererImpl - fun PsiElement.getExpectedType(): KtType? = expressionTypeProvider.getExpectedType(this) + internal val expressionTypeProvider: KtExpressionTypeProvider get() = expressionTypeProviderImpl + protected abstract val expressionTypeProviderImpl: KtExpressionTypeProvider - val builtinTypes: KtBuiltinTypes get() = typeProvider.builtinTypes + internal val typeProvider: KtTypeProvider get() = typeProviderImpl + protected abstract val typeProviderImpl: KtTypeProvider - /** - * Approximates [KtType] with the a supertype which can be rendered in a source code - * - * Return `null` if the type do not need approximation and can be rendered as is - * Otherwise, for type `T` return type `S` such `T <: S` and `T` and every it type argument is [org.jetbrains.kotlin.idea.frontend.api.types.KtDenotableType]` - */ - fun KtType.approximateToSuperPublicDenotable(): KtType? = typeProvider.approximateToSuperPublicDenotableType(this) + internal val subtypingComponent: KtSubtypingComponent get() = subtypingComponentImpl + protected abstract val subtypingComponentImpl: KtSubtypingComponent - fun KtClassOrObjectSymbol.buildSelfClassType(): KtType = typeProvider.buildSelfClassType(this) - - fun KtElement.getDiagnostics(filter: KtDiagnosticCheckerFilter): Collection = - diagnosticProvider.getDiagnosticsForElement(this, filter) - - fun KtFile.collectDiagnosticsForFile(filter: KtDiagnosticCheckerFilter): Collection> = - diagnosticProvider.collectDiagnosticsForFile(this, filter) - - fun KtSymbolWithKind.getContainingSymbol(): KtSymbolWithKind? = containingDeclarationProvider.getContainingDeclaration(this) - - fun KtSymbolWithMembers.getMemberScope(): KtMemberScope = scopeProvider.getMemberScope(this) - - fun KtSymbolWithMembers.getDeclaredMemberScope(): KtDeclaredMemberScope = scopeProvider.getDeclaredMemberScope(this) - - fun KtFileSymbol.getFileScope(): KtDeclarationScope = scopeProvider.getFileScope(this) - - fun KtPackageSymbol.getPackageScope(): KtPackageScope = scopeProvider.getPackageScope(this) - - fun List.asCompositeScope(): KtCompositeScope = scopeProvider.getCompositeScope(this) - - fun KtType.getTypeScope(): KtScope? = scopeProvider.getTypeScope(this) - - fun KtFile.getScopeContextForPosition(positionInFakeFile: KtElement): KtScopeContext = - scopeProvider.getScopeContextForPosition(this, positionInFakeFile) - - fun KtDeclaration.getSymbol(): KtSymbol = symbolProvider.getSymbol(this) - - fun KtParameter.getParameterSymbol(): KtParameterSymbol = symbolProvider.getParameterSymbol(this) - - fun KtNamedFunction.getFunctionSymbol(): KtFunctionSymbol = symbolProvider.getFunctionSymbol(this) - - fun KtConstructor<*>.getConstructorSymbol(): KtConstructorSymbol = symbolProvider.getConstructorSymbol(this) - - fun KtTypeParameter.getTypeParameterSymbol(): KtTypeParameterSymbol = symbolProvider.getTypeParameterSymbol(this) - - fun KtTypeAlias.getTypeAliasSymbol(): KtTypeAliasSymbol = symbolProvider.getTypeAliasSymbol(this) - - fun KtEnumEntry.getEnumEntrySymbol(): KtEnumEntrySymbol = symbolProvider.getEnumEntrySymbol(this) - - fun KtNamedFunction.getAnonymousFunctionSymbol(): KtAnonymousFunctionSymbol = symbolProvider.getAnonymousFunctionSymbol(this) - - fun KtLambdaExpression.getAnonymousFunctionSymbol(): KtAnonymousFunctionSymbol = symbolProvider.getAnonymousFunctionSymbol(this) - - fun KtProperty.getVariableSymbol(): KtVariableSymbol = symbolProvider.getVariableSymbol(this) - - fun KtObjectLiteralExpression.getAnonymousObjectSymbol(): KtAnonymousObjectSymbol = symbolProvider.getAnonymousObjectSymbol(this) - - fun KtClassOrObject.getClassOrObjectSymbol(): KtClassOrObjectSymbol = symbolProvider.getClassOrObjectSymbol(this) - - fun KtPropertyAccessor.getPropertyAccessorSymbol(): KtPropertyAccessorSymbol = symbolProvider.getPropertyAccessorSymbol(this) - - fun KtFile.getFileSymbol(): KtFileSymbol = symbolProvider.getFileSymbol(this) - - /** - * @return symbol with specified [this@getClassOrObjectSymbolByClassId] or `null` in case such symbol is not found - */ - fun ClassId.getCorrespondingToplevelClassOrObjectSymbol(): KtClassOrObjectSymbol? = symbolProvider.getClassOrObjectSymbolByClassId(this) - - fun FqName.getContainingCallableSymbolsWithName(name: Name): Sequence = symbolProvider.getTopLevelCallableSymbols(this, name) - - fun KtSymbolPointer.restoreSymbol(): S? = restoreSymbol(this@KtAnalysisSession) - - fun KtCallExpression.resolveCall(): KtCall? = callResolver.resolveCall(this) - - fun KtBinaryExpression.resolveCall(): KtCall? = callResolver.resolveCall(this) - - fun KtReference.resolveToSymbols(): Collection { - check(this is KtSymbolBasedReference) { "To get reference symbol the one should be KtSymbolBasedReference" } - return this@KtAnalysisSession.resolveToSymbols() - } - - fun KtSimpleReference<*>.resolveToSymbol(): KtSymbol? { - check(this is KtSymbolBasedReference) { "To get reference symbol the one should be KtSymbolBasedReference but was ${this::class}" } - return resolveToSymbols().singleOrNull() - } - - fun KtCallableSymbol.checkExtensionIsSuitable( - originalPsiFile: KtFile, - psiFakeCompletionExpression: KtSimpleNameExpression, - psiReceiverExpression: KtExpression?, - ): Boolean = completionCandidateChecker.checkExtensionFitsCandidate( - this, - originalPsiFile, - psiFakeCompletionExpression, - psiReceiverExpression - ) - - fun KtType.render(options: KtTypeRendererOptions = KtTypeRendererOptions.DEFAULT): String = - typeRenderer.render(this, options) - - fun KtReturnExpression.getReturnTargetSymbol(): KtCallableSymbol? = - expressionHandlingComponent.getReturnExpressionTargetSymbol(this) - - fun collectPossibleReferenceShortenings(file: KtFile, selection: TextRange): ShortenCommand = - referenceShortener.collectShortenings(file, selection) -} + internal val expressionInfoProvider: KtExpressionInfoProvider get() = expressionInfoProviderImpl + protected abstract val expressionInfoProviderImpl: KtExpressionInfoProvider +} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionComponent.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionComponent.kt index a326fa0786b..2f644f48a2d 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionComponent.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionComponent.kt @@ -6,9 +6,9 @@ package org.jetbrains.kotlin.idea.frontend.api.components import org.jetbrains.kotlin.idea.frontend.api.KtAnalysisSession -import org.jetbrains.kotlin.idea.frontend.api.ValidityToken import org.jetbrains.kotlin.idea.frontend.api.ValidityTokenOwner abstract class KtAnalysisSessionComponent : ValidityTokenOwner { protected abstract val analysisSession: KtAnalysisSession -} \ No newline at end of file +} + diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionMixIn.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionMixIn.kt new file mode 100644 index 00000000000..7ee3f0fbfff --- /dev/null +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtAnalysisSessionMixIn.kt @@ -0,0 +1,12 @@ +/* + * Copyright 2010-2021 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.frontend.api.components + +import org.jetbrains.kotlin.idea.frontend.api.KtAnalysisSession + +interface KtAnalysisSessionMixIn { + val analysisSession: KtAnalysisSession +} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCallResolver.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCallResolver.kt index cd213ab28fb..ee27e0b8d4e 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCallResolver.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCallResolver.kt @@ -12,4 +12,13 @@ import org.jetbrains.kotlin.psi.KtCallExpression abstract class KtCallResolver : KtAnalysisSessionComponent() { abstract fun resolveCall(call: KtCallExpression): KtCall? abstract fun resolveCall(call: KtBinaryExpression): KtCall? +} + +interface KtCallResolverMixIn : KtAnalysisSessionMixIn { + fun KtCallExpression.resolveCall(): KtCall? = + analysisSession.callResolver.resolveCall(this) + + fun KtBinaryExpression.resolveCall(): KtCall? = + analysisSession.callResolver.resolveCall(this) + } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCompletionCandidateChecker.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCompletionCandidateChecker.kt index ed147559dce..2d9d6ab0c6f 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCompletionCandidateChecker.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtCompletionCandidateChecker.kt @@ -5,7 +5,6 @@ package org.jetbrains.kotlin.idea.frontend.api.components -import com.intellij.psi.PsiElement import org.jetbrains.kotlin.idea.frontend.api.symbols.KtCallableSymbol import org.jetbrains.kotlin.psi.KtExpression import org.jetbrains.kotlin.psi.KtFile @@ -18,4 +17,18 @@ abstract class KtCompletionCandidateChecker : KtAnalysisSessionComponent() { nameExpression: KtSimpleNameExpression, possibleExplicitReceiver: KtExpression?, ): Boolean +} + +interface KtCompletionCandidateCheckerMixIn : KtAnalysisSessionMixIn { + fun KtCallableSymbol.checkExtensionIsSuitable( + originalPsiFile: KtFile, + psiFakeCompletionExpression: KtSimpleNameExpression, + psiReceiverExpression: KtExpression?, + ): Boolean = + analysisSession.completionCandidateChecker.checkExtensionFitsCandidate( + this, + originalPsiFile, + psiFakeCompletionExpression, + psiReceiverExpression + ) } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtDiagnosticProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtDiagnosticProvider.kt index 7964d4e3c17..4b7f58a581b 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtDiagnosticProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtDiagnosticProvider.kt @@ -5,6 +5,7 @@ package org.jetbrains.kotlin.idea.frontend.api.components +import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnostic import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnosticWithPsi import org.jetbrains.kotlin.psi.KtElement import org.jetbrains.kotlin.psi.KtFile @@ -14,6 +15,14 @@ abstract class KtDiagnosticProvider : KtAnalysisSessionComponent() { abstract fun collectDiagnosticsForFile(ktFile: KtFile, filter: KtDiagnosticCheckerFilter): Collection> } +interface KtDiagnosticProviderMixIn : KtAnalysisSessionMixIn { + fun KtElement.getDiagnostics(filter: KtDiagnosticCheckerFilter): Collection = + analysisSession.diagnosticProvider.getDiagnosticsForElement(this, filter) + + fun KtFile.collectDiagnosticsForFile(filter: KtDiagnosticCheckerFilter): Collection> = + analysisSession.diagnosticProvider.collectDiagnosticsForFile(this, filter) +} + enum class KtDiagnosticCheckerFilter { ONLY_COMMON_CHECKERS, ONLY_EXTENDED_CHECKERS, diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionHandlingComponent.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionHandlingComponent.kt deleted file mode 100644 index 74a5c7a46f1..00000000000 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionHandlingComponent.kt +++ /dev/null @@ -1,14 +0,0 @@ -/* - * Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors. - * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. - */ - -package org.jetbrains.kotlin.idea.frontend.api.components - -import org.jetbrains.kotlin.idea.frontend.api.symbols.KtCallableSymbol -import org.jetbrains.kotlin.idea.frontend.api.symbols.KtFunctionLikeSymbol -import org.jetbrains.kotlin.psi.KtReturnExpression - -abstract class KtExpressionHandlingComponent : KtAnalysisSessionComponent() { - abstract fun getReturnExpressionTargetSymbol(returnExpression: KtReturnExpression): KtCallableSymbol? -} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionInfoProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionInfoProvider.kt new file mode 100644 index 00000000000..d0a63e81235 --- /dev/null +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionInfoProvider.kt @@ -0,0 +1,18 @@ +/* + * Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.frontend.api.components + +import org.jetbrains.kotlin.idea.frontend.api.symbols.KtCallableSymbol +import org.jetbrains.kotlin.psi.KtReturnExpression + +abstract class KtExpressionInfoProvider : KtAnalysisSessionComponent() { + abstract fun getReturnExpressionTargetSymbol(returnExpression: KtReturnExpression): KtCallableSymbol? +} + +interface KtExpressionInfoProviderMixIn : KtAnalysisSessionMixIn { + fun KtReturnExpression.getReturnTargetSymbol(): KtCallableSymbol? = + analysisSession.expressionInfoProvider.getReturnExpressionTargetSymbol(this) +} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionTypeProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionTypeProvider.kt index 5a4de47792b..96b66e5a110 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionTypeProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtExpressionTypeProvider.kt @@ -17,3 +17,14 @@ abstract class KtExpressionTypeProvider : KtAnalysisSessionComponent() { abstract fun getExpectedType(expression: PsiElement): KtType? } + +interface KtExpressionTypeProviderMixIn : KtAnalysisSessionMixIn { + fun KtExpression.getKtType(): KtType = + analysisSession.expressionTypeProvider.getKtExpressionType(this) + + fun KtDeclaration.getReturnKtType(): KtType = + analysisSession.expressionTypeProvider.getReturnTypeForKtDeclaration(this) + + fun PsiElement.getExpectedType(): KtType? = + analysisSession.expressionTypeProvider.getExpectedType(this) +} diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceResolveMixIn.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceResolveMixIn.kt new file mode 100644 index 00000000000..84e8fc1d116 --- /dev/null +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceResolveMixIn.kt @@ -0,0 +1,24 @@ +/* + * Copyright 2010-2021 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.frontend.api.components + +import org.jetbrains.kotlin.idea.frontend.api.KtSymbolBasedReference +import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbol +import org.jetbrains.kotlin.idea.frontend.api.symbols.pointers.KtSymbolPointer +import org.jetbrains.kotlin.idea.references.KtReference +import org.jetbrains.kotlin.idea.references.KtSimpleReference + +interface KtReferenceResolveMixIn : KtAnalysisSessionMixIn { + fun KtReference.resolveToSymbols(): Collection { + check(this is KtSymbolBasedReference) { "To get reference symbol the one should be KtSymbolBasedReference" } + return analysisSession.resolveToSymbols() + } + + fun KtSimpleReference<*>.resolveToSymbol(): KtSymbol? { + check(this is KtSymbolBasedReference) { "To get reference symbol the one should be KtSymbolBasedReference but was ${this::class}" } + return resolveToSymbols().singleOrNull() + } +} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceShortener.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceShortener.kt index 311f50194c0..564bc27f00b 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceShortener.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtReferenceShortener.kt @@ -12,6 +12,11 @@ abstract class KtReferenceShortener : KtAnalysisSessionComponent() { abstract fun collectShortenings(file: KtFile, selection: TextRange): ShortenCommand } +interface KtReferenceShortenerMixIn : KtAnalysisSessionMixIn { + fun collectPossibleReferenceShortenings(file: KtFile, selection: TextRange): ShortenCommand = + analysisSession.referenceShortener.collectShortenings(file, selection) +} + interface ShortenCommand { fun invokeShortening() } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtScopeProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtScopeProvider.kt index 169fe140677..0cba32841d2 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtScopeProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtScopeProvider.kt @@ -29,4 +29,27 @@ abstract class KtScopeProvider : KtAnalysisSessionComponent() { ): KtScopeContext } +interface KtScopeProviderMixIn : KtAnalysisSessionMixIn { + fun KtSymbolWithMembers.getMemberScope(): KtMemberScope = + analysisSession.scopeProvider.getMemberScope(this) + + fun KtSymbolWithMembers.getDeclaredMemberScope(): KtDeclaredMemberScope = + analysisSession.scopeProvider.getDeclaredMemberScope(this) + + fun KtFileSymbol.getFileScope(): KtDeclarationScope = + analysisSession.scopeProvider.getFileScope(this) + + fun KtPackageSymbol.getPackageScope(): KtPackageScope = + analysisSession.scopeProvider.getPackageScope(this) + + fun List.asCompositeScope(): KtCompositeScope = + analysisSession.scopeProvider.getCompositeScope(this) + + fun KtType.getTypeScope(): KtScope? = + analysisSession.scopeProvider.getTypeScope(this) + + fun KtFile.getScopeContextForPosition(positionInFakeFile: KtElement): KtScopeContext = + analysisSession.scopeProvider.getScopeContextForPosition(this, positionInFakeFile) +} + data class KtScopeContext(val scopes: KtCompositeScope, val implicitReceiversTypes: List) diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSmartCastProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSmartCastProvider.kt index 415804c1af2..f1a1b604c41 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSmartCastProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSmartCastProvider.kt @@ -12,4 +12,12 @@ import org.jetbrains.kotlin.psi.KtExpression abstract class KtSmartCastProvider : KtAnalysisSessionComponent() { abstract fun getSmartCastedToType(expression: KtExpression): KtType? abstract fun getImplicitReceiverSmartCast(expression: KtExpression): Collection +} + +interface KtSmartCastProviderMixIn : KtAnalysisSessionMixIn { + fun KtExpression.getSmartCast(): KtType? = + analysisSession.smartCastProvider.getSmartCastedToType(this) + + fun KtExpression.getImplicitReceiverSmartCast(): Collection = + analysisSession.smartCastProvider.getImplicitReceiverSmartCast(this) } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSubtypingComponent.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSubtypingComponent.kt index 58c0e33ef24..3f412cdde6e 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSubtypingComponent.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSubtypingComponent.kt @@ -10,4 +10,15 @@ import org.jetbrains.kotlin.idea.frontend.api.types.KtType abstract class KtSubtypingComponent : KtAnalysisSessionComponent() { abstract fun isEqualTo(first: KtType, second: KtType): Boolean abstract fun isSubTypeOf(subType: KtType, superType: KtType): Boolean +} + +interface KtSubtypingComponentMixIn : KtAnalysisSessionMixIn { + infix fun KtType.isEqualTo(other: KtType): Boolean = + analysisSession.subtypingComponent.isEqualTo(this, other) + + infix fun KtType.isSubTypeOf(superType: KtType): Boolean = + analysisSession.subtypingComponent.isSubTypeOf(this, superType) + + infix fun KtType.isNotSubTypeOf(superType: KtType): Boolean = + !analysisSession.subtypingComponent.isSubTypeOf(this, superType) } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolContainingDeclarationProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolContainingDeclarationProvider.kt index eea4d4181f5..0ce5ac09520 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolContainingDeclarationProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolContainingDeclarationProvider.kt @@ -8,11 +8,16 @@ package org.jetbrains.kotlin.idea.frontend.api.components import org.jetbrains.kotlin.idea.frontend.api.symbols.markers.KtSymbolWithKind abstract class KtSymbolContainingDeclarationProvider : KtAnalysisSessionComponent() { + abstract fun getContainingDeclaration(symbol: KtSymbolWithKind): KtSymbolWithKind? +} + +interface KtSymbolContainingDeclarationProviderMixIn : KtAnalysisSessionMixIn { /** * Returns containing declaration for symbol: * for top-level declarations returns null * for class members returns containing class * for local declaration returns declaration it was declared it */ - abstract fun getContainingDeclaration(symbol: KtSymbolWithKind): KtSymbolWithKind? + fun KtSymbolWithKind.getContainingSymbol(): KtSymbolWithKind? = + analysisSession.containingDeclarationProvider.getContainingDeclaration(this) } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolDeclarationOverridesProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolDeclarationOverridesProvider.kt index e93c087fbac..f619768a90d 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolDeclarationOverridesProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolDeclarationOverridesProvider.kt @@ -10,24 +10,37 @@ import org.jetbrains.kotlin.idea.frontend.api.symbols.KtClassOrObjectSymbol import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbol abstract class KtSymbolDeclarationOverridesProvider : KtAnalysisSessionComponent() { - /** - * Returns symbols that are overridden by requested - */ - abstract fun getAllOverriddenSymbols( - callableSymbol: T, - ): List + abstract fun getAllOverriddenSymbols(callableSymbol: T): List + abstract fun getDirectlyOverriddenSymbols(callableSymbol: T): List - /** - * Returns symbols that are overridden by requested - */ - abstract fun getDirectlyOverriddenSymbols( - callableSymbol: T, - ): List - - - /** - * If [symbol] origin is [org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin.INTERSECTION_OVERRIDE] - * Then returns the symbols which [symbol] overrides, otherwise empty collection - */ abstract fun getIntersectionOverriddenSymbols(symbol: KtCallableSymbol): Collection +} + +interface KtSymbolDeclarationOverridesProviderMixIn : KtAnalysisSessionMixIn { + /** + * Return a list of **all** symbols which are overridden by symbol + * + * E.g, if we have `A.foo` overrides `B.foo` overrides `C.foo`, all two super declarations `B.foo`, `C.foo` will be returned + * + * Unwraps substituted overridden symbols (see [org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin.INTERSECTION_OVERRIDE]) + * + * @see getDirectlyOverriddenSymbols + */ + fun KtCallableSymbol.getAllOverriddenSymbols(): List = + analysisSession.symbolDeclarationOverridesProvider.getAllOverriddenSymbols(this) + + /** + * Return a list of symbols which are **directly** overridden by symbol + ** + * E.g, if we have `A.foo` overrides `B.foo` overrides `C.foo`, only declarations directly overriden `B.foo` will be returned + * + * Unwraps substituted overridden symbols (see [org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolOrigin.INTERSECTION_OVERRIDE]) + * + * @see getAllOverriddenSymbols + */ + fun KtCallableSymbol.getDirectlyOverriddenSymbols(): List = + analysisSession.symbolDeclarationOverridesProvider.getDirectlyOverriddenSymbols(this) + + fun KtCallableSymbol.getIntersectionOverriddenSymbols(): Collection = + analysisSession.symbolDeclarationOverridesProvider.getIntersectionOverriddenSymbols(this) } \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolsMixIn.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolsMixIn.kt new file mode 100644 index 00000000000..ec38c2908ce --- /dev/null +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtSymbolsMixIn.kt @@ -0,0 +1,14 @@ +/* + * Copyright 2010-2021 JetBrains s.r.o. and Kotlin Programming Language contributors. + * Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file. + */ + +package org.jetbrains.kotlin.idea.frontend.api.components + +import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbol +import org.jetbrains.kotlin.idea.frontend.api.symbols.pointers.KtSymbolPointer + +interface KtSymbolsMixIn : KtAnalysisSessionMixIn { + @Suppress("DEPRECATION") + fun KtSymbolPointer.restoreSymbol(): S? = restoreSymbol(analysisSession) +} \ No newline at end of file diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeProvider.kt index 1f69c3d56fb..f701df11bcd 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeProvider.kt @@ -5,7 +5,6 @@ package org.jetbrains.kotlin.idea.frontend.api.components -import org.jetbrains.kotlin.builtins.functions.FunctionClassKind import org.jetbrains.kotlin.idea.frontend.api.ValidityTokenOwner import org.jetbrains.kotlin.idea.frontend.api.symbols.KtClassOrObjectSymbol import org.jetbrains.kotlin.idea.frontend.api.types.KtType @@ -18,6 +17,23 @@ abstract class KtTypeProvider : KtAnalysisSessionComponent() { abstract fun buildSelfClassType(symbol: KtClassOrObjectSymbol): KtType } +interface KtTypeProviderMixIn : KtAnalysisSessionMixIn { + val builtinTypes: KtBuiltinTypes + get() = analysisSession.typeProvider.builtinTypes + + /** + * Approximates [KtType] with the a supertype which can be rendered in a source code + * + * Return `null` if the type do not need approximation and can be rendered as is + * Otherwise, for type `T` return type `S` such `T <: S` and `T` and every it type argument is [org.jetbrains.kotlin.idea.frontend.api.types.KtDenotableType]` + */ + fun KtType.approximateToSuperPublicDenotable(): KtType? = + analysisSession.typeProvider.approximateToSuperPublicDenotableType(this) + + fun KtClassOrObjectSymbol.buildSelfClassType(): KtType = + analysisSession.typeProvider.buildSelfClassType(this) + +} @Suppress("PropertyName") abstract class KtBuiltinTypes : ValidityTokenOwner { diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeRenderer.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeRenderer.kt index 3f9770b03ce..2aa371b0c6d 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeRenderer.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/components/KtTypeRenderer.kt @@ -14,6 +14,11 @@ abstract class KtTypeRenderer : KtAnalysisSessionComponent() { abstract fun render(type: KtType, options: KtTypeRendererOptions): String } +interface KtTypeRendererMixIn : KtAnalysisSessionMixIn { + fun KtType.render(options: KtTypeRendererOptions = KtTypeRendererOptions.DEFAULT): String = + analysisSession.typeRenderer.render(this, options) +} + data class KtTypeRendererOptions( val renderFqNames: Boolean, val renderFunctionTypes: Boolean diff --git a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/symbols/KtSymbolProvider.kt b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/symbols/KtSymbolProvider.kt index c4381a90d6e..6d15de3665c 100644 --- a/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/symbols/KtSymbolProvider.kt +++ b/idea/idea-frontend-api/src/org/jetbrains/kotlin/idea/frontend/api/symbols/KtSymbolProvider.kt @@ -6,6 +6,7 @@ package org.jetbrains.kotlin.idea.frontend.api.symbols import org.jetbrains.kotlin.idea.frontend.api.components.KtAnalysisSessionComponent +import org.jetbrains.kotlin.idea.frontend.api.components.KtAnalysisSessionMixIn import org.jetbrains.kotlin.name.ClassId import org.jetbrains.kotlin.name.FqName import org.jetbrains.kotlin.name.Name @@ -43,10 +44,61 @@ abstract class KtSymbolProvider : KtAnalysisSessionComponent() { abstract fun getClassOrObjectSymbol(psi: KtClassOrObject): KtClassOrObjectSymbol abstract fun getPropertyAccessorSymbol(psi: KtPropertyAccessor): KtPropertyAccessorSymbol - /** - * @return symbol with specified [classId] or `null` in case such symbol is not found - */ abstract fun getClassOrObjectSymbolByClassId(classId: ClassId): KtClassOrObjectSymbol? abstract fun getTopLevelCallableSymbols(packageFqName: FqName, name: Name): Sequence +} + +interface KtSymbolProviderMixIn : KtAnalysisSessionMixIn { + fun KtDeclaration.getSymbol(): KtSymbol = + analysisSession.symbolProvider.getSymbol(this) + + fun KtParameter.getParameterSymbol(): KtParameterSymbol = + analysisSession.symbolProvider.getParameterSymbol(this) + + fun KtNamedFunction.getFunctionSymbol(): KtFunctionSymbol = + analysisSession.symbolProvider.getFunctionSymbol(this) + + fun KtConstructor<*>.getConstructorSymbol(): KtConstructorSymbol = + analysisSession.symbolProvider.getConstructorSymbol(this) + + fun KtTypeParameter.getTypeParameterSymbol(): KtTypeParameterSymbol = + analysisSession.symbolProvider.getTypeParameterSymbol(this) + + fun KtTypeAlias.getTypeAliasSymbol(): KtTypeAliasSymbol = + analysisSession.symbolProvider.getTypeAliasSymbol(this) + + fun KtEnumEntry.getEnumEntrySymbol(): KtEnumEntrySymbol = + analysisSession.symbolProvider.getEnumEntrySymbol(this) + + fun KtNamedFunction.getAnonymousFunctionSymbol(): KtAnonymousFunctionSymbol = + analysisSession.symbolProvider.getAnonymousFunctionSymbol(this) + + fun KtLambdaExpression.getAnonymousFunctionSymbol(): KtAnonymousFunctionSymbol = + analysisSession.symbolProvider.getAnonymousFunctionSymbol(this) + + fun KtProperty.getVariableSymbol(): KtVariableSymbol = + analysisSession.symbolProvider.getVariableSymbol(this) + + fun KtObjectLiteralExpression.getAnonymousObjectSymbol(): KtAnonymousObjectSymbol = + analysisSession.symbolProvider.getAnonymousObjectSymbol(this) + + fun KtClassOrObject.getClassOrObjectSymbol(): KtClassOrObjectSymbol = + analysisSession.symbolProvider.getClassOrObjectSymbol(this) + + fun KtPropertyAccessor.getPropertyAccessorSymbol(): KtPropertyAccessorSymbol = + analysisSession.symbolProvider.getPropertyAccessorSymbol(this) + + fun KtFile.getFileSymbol(): KtFileSymbol = + analysisSession.symbolProvider.getFileSymbol(this) + + /** + * @return symbol with specified [this@getClassOrObjectSymbolByClassId] or `null` in case such symbol is not found + */ + fun ClassId.getCorrespondingToplevelClassOrObjectSymbol(): KtClassOrObjectSymbol? = + analysisSession.symbolProvider.getClassOrObjectSymbolByClassId(this) + + fun FqName.getContainingCallableSymbolsWithName(name: Name): Sequence = + analysisSession.symbolProvider.getTopLevelCallableSymbols(this, name) + } \ No newline at end of file diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/KtFirAnalysisSession.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/KtFirAnalysisSession.kt index 4a9a1f25955..dd9560b0c9a 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/KtFirAnalysisSession.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/KtFirAnalysisSession.kt @@ -16,13 +16,11 @@ import org.jetbrains.kotlin.idea.frontend.api.KtAnalysisSession import org.jetbrains.kotlin.idea.frontend.api.ReadActionConfinementValidityToken import org.jetbrains.kotlin.idea.frontend.api.ValidityToken import org.jetbrains.kotlin.idea.frontend.api.assertIsValidAndAccessible -import org.jetbrains.kotlin.idea.frontend.api.components.* import org.jetbrains.kotlin.idea.frontend.api.fir.components.* import org.jetbrains.kotlin.idea.frontend.api.fir.symbols.KtFirSymbolProvider import org.jetbrains.kotlin.idea.frontend.api.fir.utils.EnclosingDeclarationContext import org.jetbrains.kotlin.idea.frontend.api.fir.utils.recordCompletionContext import org.jetbrains.kotlin.idea.frontend.api.fir.utils.threadLocal -import org.jetbrains.kotlin.idea.frontend.api.symbols.KtSymbolProvider import org.jetbrains.kotlin.psi.KtElement import org.jetbrains.kotlin.psi.KtFile @@ -38,22 +36,33 @@ private constructor( assertIsValidAndAccessible() } - override val smartCastProvider: KtSmartCastProvider = KtFirSmartcastProvider(this, token) - override val expressionTypeProvider: KtExpressionTypeProvider = KtFirExpressionTypeProvider(this, token) - public override val diagnosticProvider: KtDiagnosticProvider = KtFirDiagnosticProvider(this, token) - override val containingDeclarationProvider = KtFirSymbolContainingDeclarationProvider(this, token) - override val callResolver: KtCallResolver = KtFirCallResolver(this, token) - override val scopeProvider by threadLocal { KtFirScopeProvider(this, firSymbolBuilder, project, firResolveState, token) } - override val symbolProvider: KtSymbolProvider = - KtFirSymbolProvider(this, firResolveState.rootModuleSession.symbolProvider, firResolveState, firSymbolBuilder, token) - override val completionCandidateChecker: KtCompletionCandidateChecker = KtFirCompletionCandidateChecker(this, token) - override val symbolDeclarationOverridesProvider: KtSymbolDeclarationOverridesProvider = - KtFirSymbolDeclarationOverridesProvider(this, token) - override val referenceShortener: KtReferenceShortener = KtFirReferenceShortener(this, token, firResolveState) + override val smartCastProviderImpl = KtFirSmartcastProvider(this, token) - override val expressionHandlingComponent: KtExpressionHandlingComponent = KtFirExpressionHandlingComponent(this, token) - override val typeProvider: KtTypeProvider = KtFirTypeProvider(this, token) - override val subtypingComponent: KtSubtypingComponent = KtFirSubtypingComponent(this, token) + override val expressionTypeProviderImpl = KtFirExpressionTypeProvider(this, token) + + override val diagnosticProviderImpl = KtFirDiagnosticProvider(this, token) + + override val containingDeclarationProviderImpl = KtFirSymbolContainingDeclarationProvider(this, token) + + override val callResolverImpl = KtFirCallResolver(this, token) + + override val scopeProviderImpl by threadLocal { KtFirScopeProvider(this, firSymbolBuilder, project, firResolveState, token) } + + override val symbolProviderImpl = + KtFirSymbolProvider(this, firResolveState.rootModuleSession.symbolProvider, firResolveState, firSymbolBuilder, token) + + override val completionCandidateCheckerImpl = KtFirCompletionCandidateChecker(this, token) + + override val symbolDeclarationOverridesProviderImpl = + KtFirSymbolDeclarationOverridesProvider(this, token) + + override val referenceShortenerImpl = KtFirReferenceShortener(this, token, firResolveState) + + override val expressionInfoProviderImpl = KtFirExpressionInfoProvider(this, token) + + override val typeProviderImpl = KtFirTypeProvider(this, token) + + override val subtypingComponentImpl = KtFirSubtypingComponent(this, token) override fun createContextDependentCopy(originalKtFile: KtFile, fakeKtElement: KtElement): KtAnalysisSession { check(context == KtFirAnalysisSessionContext.DefaultContext) { diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirAnalysisSessionComponent.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirAnalysisSessionComponent.kt index c3e8ab530e8..1c0b26ef2c7 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirAnalysisSessionComponent.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirAnalysisSessionComponent.kt @@ -7,29 +7,37 @@ package org.jetbrains.kotlin.idea.frontend.api.fir.components import org.jetbrains.kotlin.fir.FirSession import org.jetbrains.kotlin.fir.FirSourceElement +import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnostic import org.jetbrains.kotlin.fir.analysis.diagnostics.FirPsiDiagnostic +import org.jetbrains.kotlin.fir.analysis.diagnostics.toFirDiagnostic import org.jetbrains.kotlin.fir.diagnostics.ConeDiagnostic import org.jetbrains.kotlin.fir.typeContext import org.jetbrains.kotlin.fir.types.ConeKotlinType import org.jetbrains.kotlin.fir.types.ConeTypeCheckerContext +import org.jetbrains.kotlin.idea.frontend.api.ValidityTokenOwner +import org.jetbrains.kotlin.idea.frontend.api.components.KtAnalysisSessionComponent import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnostic import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnosticWithPsi import org.jetbrains.kotlin.idea.frontend.api.fir.KtFirAnalysisSession +import org.jetbrains.kotlin.idea.frontend.api.fir.diagnostics.KT_DIAGNOSTIC_CONVERTER internal interface KtFirAnalysisSessionComponent { val analysisSession: KtFirAnalysisSession val rootModuleSession: FirSession get() = analysisSession.firResolveState.rootModuleSession - val firSymbolBuilder get() = analysisSession.firSymbolBuilder val firResolveState get() = analysisSession.firResolveState + fun ConeKotlinType.asKtType() = analysisSession.firSymbolBuilder.buildKtType(this) fun FirPsiDiagnostic<*>.asKtDiagnostic(): KtDiagnosticWithPsi<*> = - (analysisSession.diagnosticProvider as KtFirDiagnosticProvider).firDiagnosticAsKtDiagnostic(this) + KT_DIAGNOSTIC_CONVERTER.convert(analysisSession, this as FirDiagnostic<*>) - fun ConeDiagnostic.asKtDiagnostic(source: FirSourceElement): KtDiagnostic? = - (analysisSession.diagnosticProvider as KtFirDiagnosticProvider).coneDiagnosticAsKtDiagnostic(this, source) + fun ConeDiagnostic.asKtDiagnostic(source: FirSourceElement): KtDiagnosticWithPsi<*>? { + val firDiagnostic = toFirDiagnostic(source) ?: return null + check(firDiagnostic is FirPsiDiagnostic<*>) + return firDiagnostic.asKtDiagnostic() + } fun createTypeCheckerContext() = ConeTypeCheckerContext( isErrorTypeEqualsToAnything = true, diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirDiagnosticProvider.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirDiagnosticProvider.kt index 68bdd683e01..d25456b908c 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirDiagnosticProvider.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirDiagnosticProvider.kt @@ -5,12 +5,6 @@ package org.jetbrains.kotlin.idea.frontend.api.fir.components -import com.intellij.psi.PsiElement -import org.jetbrains.kotlin.fir.FirSourceElement -import org.jetbrains.kotlin.fir.analysis.diagnostics.FirDiagnostic -import org.jetbrains.kotlin.fir.analysis.diagnostics.FirPsiDiagnostic -import org.jetbrains.kotlin.fir.analysis.diagnostics.toFirDiagnostic -import org.jetbrains.kotlin.fir.diagnostics.ConeDiagnostic import org.jetbrains.kotlin.idea.fir.low.level.api.api.DiagnosticCheckerFilter import org.jetbrains.kotlin.idea.fir.low.level.api.api.collectDiagnosticsForFile import org.jetbrains.kotlin.idea.fir.low.level.api.api.getDiagnostics @@ -19,7 +13,6 @@ import org.jetbrains.kotlin.idea.frontend.api.components.KtDiagnosticCheckerFilt import org.jetbrains.kotlin.idea.frontend.api.components.KtDiagnosticProvider import org.jetbrains.kotlin.idea.frontend.api.diagnostics.KtDiagnosticWithPsi import org.jetbrains.kotlin.idea.frontend.api.fir.KtFirAnalysisSession -import org.jetbrains.kotlin.idea.frontend.api.fir.diagnostics.KT_DIAGNOSTIC_CONVERTER import org.jetbrains.kotlin.idea.frontend.api.withValidityAssertion import org.jetbrains.kotlin.psi.KtElement import org.jetbrains.kotlin.psi.KtFile @@ -38,19 +31,10 @@ internal class KtFirDiagnosticProvider( override fun collectDiagnosticsForFile(ktFile: KtFile, filter: KtDiagnosticCheckerFilter): Collection> = ktFile.collectDiagnosticsForFile(firResolveState, filter.asLLFilter()).map { it.asKtDiagnostic() } - fun firDiagnosticAsKtDiagnostic(diagnostic: FirPsiDiagnostic<*>): KtDiagnosticWithPsi<*> { - return KT_DIAGNOSTIC_CONVERTER.convert(analysisSession, diagnostic as FirDiagnostic<*>) - } private fun KtDiagnosticCheckerFilter.asLLFilter() = when (this) { KtDiagnosticCheckerFilter.ONLY_COMMON_CHECKERS -> DiagnosticCheckerFilter.ONLY_COMMON_CHECKERS KtDiagnosticCheckerFilter.ONLY_EXTENDED_CHECKERS -> DiagnosticCheckerFilter.ONLY_EXTENDED_CHECKERS KtDiagnosticCheckerFilter.EXTENDED_AND_COMMON_CHECKERS -> DiagnosticCheckerFilter.EXTENDED_AND_COMMON_CHECKERS } - - fun coneDiagnosticAsKtDiagnostic(coneDiagnostic: ConeDiagnostic, source: FirSourceElement): KtDiagnosticWithPsi<*>? { - val firDiagnostic = coneDiagnostic.toFirDiagnostic(source) ?: return null - check(firDiagnostic is FirPsiDiagnostic<*>) - return firDiagnosticAsKtDiagnostic(firDiagnostic) - } } \ No newline at end of file diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionHandlingComponent.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionInfoProvider.kt similarity index 84% rename from idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionHandlingComponent.kt rename to idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionInfoProvider.kt index d8048dcb056..7fdb4052891 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionHandlingComponent.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirExpressionInfoProvider.kt @@ -8,16 +8,15 @@ package org.jetbrains.kotlin.idea.frontend.api.fir.components import org.jetbrains.kotlin.fir.expressions.FirReturnExpression import org.jetbrains.kotlin.idea.fir.low.level.api.api.getOrBuildFirSafe import org.jetbrains.kotlin.idea.frontend.api.ValidityToken -import org.jetbrains.kotlin.idea.frontend.api.components.KtExpressionHandlingComponent +import org.jetbrains.kotlin.idea.frontend.api.components.KtExpressionInfoProvider import org.jetbrains.kotlin.idea.frontend.api.fir.KtFirAnalysisSession import org.jetbrains.kotlin.idea.frontend.api.symbols.KtCallableSymbol -import org.jetbrains.kotlin.idea.frontend.api.symbols.KtFunctionLikeSymbol import org.jetbrains.kotlin.psi.KtReturnExpression -internal class KtFirExpressionHandlingComponent( +internal class KtFirExpressionInfoProvider( override val analysisSession: KtFirAnalysisSession, override val token: ValidityToken, -) : KtExpressionHandlingComponent(), KtFirAnalysisSessionComponent { +) : KtExpressionInfoProvider(), KtFirAnalysisSessionComponent { override fun getReturnExpressionTargetSymbol(returnExpression: KtReturnExpression): KtCallableSymbol? { val fir = returnExpression.getOrBuildFirSafe(firResolveState) ?: return null val firTargetSymbol = fir.target.labeledElement diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirSmartcastProvider.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirSmartcastProvider.kt index 25dc4adc57f..2b416a98c45 100644 --- a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirSmartcastProvider.kt +++ b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/components/KtFirSmartcastProvider.kt @@ -10,13 +10,10 @@ import org.jetbrains.kotlin.fir.expressions.FirQualifiedAccessExpression import org.jetbrains.kotlin.fir.types.ConeKotlinType import org.jetbrains.kotlin.fir.types.coneTypeSafe import org.jetbrains.kotlin.idea.fir.low.level.api.api.getOrBuildFirSafe -import org.jetbrains.kotlin.idea.frontend.api.ImplicitReceiverSmartCast -import org.jetbrains.kotlin.idea.frontend.api.ImplicitReceiverSmartcastKind -import org.jetbrains.kotlin.idea.frontend.api.ValidityToken +import org.jetbrains.kotlin.idea.frontend.api.* import org.jetbrains.kotlin.idea.frontend.api.components.KtSmartCastProvider import org.jetbrains.kotlin.idea.frontend.api.fir.KtFirAnalysisSession import org.jetbrains.kotlin.idea.frontend.api.types.KtType -import org.jetbrains.kotlin.idea.frontend.api.withValidityAssertion import org.jetbrains.kotlin.psi.KtExpression internal class KtFirSmartcastProvider( diff --git a/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/diagnostics/DiagnosticConverter.kt b/idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/diagnostics/KtDiagnosticConverter.kt similarity index 100% rename from idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/diagnostics/DiagnosticConverter.kt rename to idea/idea-frontend-fir/src/org/jetbrains/kotlin/idea/frontend/api/fir/diagnostics/KtDiagnosticConverter.kt