[Analysis API] Fix 'getContainingDeclaration()' for code fragments
^KT-65075 Fixed
This commit is contained in:
+16
-5
@@ -153,8 +153,8 @@ internal class KtFirSymbolContainingDeclarationProvider(
|
||||
}
|
||||
}
|
||||
|
||||
fun getContainingDeclarationByPsi(symbol: KtSymbol): KtDeclarationSymbol {
|
||||
val containingDeclaration = getContainingPsi(symbol)
|
||||
fun getContainingDeclarationByPsi(symbol: KtSymbol): KtDeclarationSymbol? {
|
||||
val containingDeclaration = getContainingPsi(symbol) ?: return null
|
||||
return with(analysisSession) { containingDeclaration.getSymbol() }
|
||||
}
|
||||
|
||||
@@ -221,7 +221,7 @@ internal class KtFirSymbolContainingDeclarationProvider(
|
||||
return symbol.getContainingKtModule(analysisSession.firResolveSession)
|
||||
}
|
||||
|
||||
private fun getContainingPsi(symbol: KtSymbol): KtDeclaration {
|
||||
private fun getContainingPsi(symbol: KtSymbol): KtDeclaration? {
|
||||
val source = symbol.firSymbol.source
|
||||
?: errorWithAttachment("PSI should present for declaration built by Kotlin code") {
|
||||
withSymbolAttachment("symbolForContainingPsi", symbol, analysisSession)
|
||||
@@ -245,10 +245,21 @@ internal class KtFirSymbolContainingDeclarationProvider(
|
||||
}
|
||||
|
||||
if (isOrdinarySymbolWithSource(symbol)) {
|
||||
return psi.getContainingKtDeclaration()
|
||||
?: errorWithAttachment("Containing declaration should present for nested declaration ${psi::class}") {
|
||||
val result = psi.getContainingPsiDeclaration()
|
||||
|
||||
if (result == null) {
|
||||
val containingFile = psi.containingFile
|
||||
if (containingFile is KtCodeFragment) {
|
||||
// All content inside a code fragment is implicitly local, but there is no non-local parent
|
||||
return null
|
||||
}
|
||||
|
||||
errorWithAttachment("Containing declaration should present for nested declaration ${psi::class}") {
|
||||
withSymbolAttachment("symbolForContainingPsi", symbol, analysisSession)
|
||||
}
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
errorWithAttachment("Unsupported declaration origin ${symbol.origin} ${psi::class}") {
|
||||
|
||||
+6
@@ -52,6 +52,12 @@ public class FirIdeDependentAnalysisSourceModuleContainingDeclarationProviderByP
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/classes.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("codeFragments.kt")
|
||||
public void testCodeFragments() throws Exception {
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/codeFragments.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("deeplyNestedCode.kt")
|
||||
public void testDeeplyNestedCode() throws Exception {
|
||||
|
||||
+6
@@ -52,6 +52,12 @@ public class FirIdeNormalAnalysisSourceModuleContainingDeclarationProviderByPsiT
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/classes.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("codeFragments.kt")
|
||||
public void testCodeFragments() throws Exception {
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/codeFragments.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("deeplyNestedCode.kt")
|
||||
public void testDeeplyNestedCode() throws Exception {
|
||||
|
||||
+1
-1
@@ -20,7 +20,7 @@ abstract class AbstractContainingDeclarationProviderByPsiTest : AbstractAnalysis
|
||||
override fun doTestByMainFile(mainFile: KtFile, mainModule: TestModule, testServices: TestServices) {
|
||||
val currentPath = mutableListOf<KtDeclaration>()
|
||||
val ktClasses = mutableListOf<KtClassOrObject>()
|
||||
analyseForTest(mainFile.declarations.first()) {
|
||||
analyseForTest(mainFile) {
|
||||
val expectedFileSymbol = mainFile.getFileSymbol()
|
||||
mainFile.accept(object : KtVisitorVoid() {
|
||||
override fun visitElement(element: PsiElement) {
|
||||
|
||||
+6
@@ -52,6 +52,12 @@ public class FirStandaloneNormalAnalysisSourceModuleContainingDeclarationProvide
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/classes.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("codeFragments.kt")
|
||||
public void testCodeFragments() throws Exception {
|
||||
runTest("analysis/analysis-api/testData/components/containingDeclarationProvider/containingDeclarationByPsi/codeFragments.kt");
|
||||
}
|
||||
|
||||
@Test
|
||||
@TestMetadata("deeplyNestedCode.kt")
|
||||
public void testDeeplyNestedCode() throws Exception {
|
||||
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
// MODULE: context
|
||||
|
||||
// FILE: context.kt
|
||||
fun test() {
|
||||
<caret_context>Unit
|
||||
}
|
||||
|
||||
fun foo() {}
|
||||
|
||||
|
||||
// MODULE: main
|
||||
// MODULE_KIND: CodeFragment
|
||||
|
||||
// FILE: main.kt
|
||||
// CODE_FRAGMENT_KIND: EXPRESSION
|
||||
object {
|
||||
fun foo() {}
|
||||
|
||||
fun bar() {
|
||||
foo()
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user