Fix false positive "Unused import directive" for imports under several alias
#KT-30949 Fixed
This commit is contained in:
@@ -175,7 +175,7 @@ open class KtFile(viewProvider: FileViewProvider, val isCompiled: Boolean) :
|
|||||||
importDirectives.firstOrNull { name == it.aliasName }
|
importDirectives.firstOrNull { name == it.aliasName }
|
||||||
|
|
||||||
fun findAliasByFqName(fqName: FqName): KtImportAlias? = importDirectives.firstOrNull {
|
fun findAliasByFqName(fqName: FqName): KtImportAlias? = importDirectives.firstOrNull {
|
||||||
fqName == it.importedFqName
|
it.alias != null && fqName == it.importedFqName
|
||||||
}?.alias
|
}?.alias
|
||||||
|
|
||||||
@Deprecated("") // getPackageFqName should be used instead
|
@Deprecated("") // getPackageFqName should be used instead
|
||||||
|
|||||||
@@ -42,7 +42,6 @@ import org.jetbrains.kotlin.resolve.ImportPath
|
|||||||
import org.jetbrains.kotlin.resolve.descriptorUtil.getImportableDescriptor
|
import org.jetbrains.kotlin.resolve.descriptorUtil.getImportableDescriptor
|
||||||
import org.jetbrains.kotlin.resolve.scopes.HierarchicalScope
|
import org.jetbrains.kotlin.resolve.scopes.HierarchicalScope
|
||||||
import org.jetbrains.kotlin.resolve.scopes.utils.*
|
import org.jetbrains.kotlin.resolve.scopes.utils.*
|
||||||
import java.util.*
|
|
||||||
|
|
||||||
class KotlinImportOptimizer : ImportOptimizer {
|
class KotlinImportOptimizer : ImportOptimizer {
|
||||||
override fun supports(file: PsiFile?) = file is KtFile
|
override fun supports(file: PsiFile?) = file is KtFile
|
||||||
@@ -74,6 +73,12 @@ class KotlinImportOptimizer : ImportOptimizer {
|
|||||||
|
|
||||||
private class CollectUsedDescriptorsVisitor(file: KtFile) : KtVisitorVoid() {
|
private class CollectUsedDescriptorsVisitor(file: KtFile) : KtVisitorVoid() {
|
||||||
private val currentPackageName = file.packageFqName
|
private val currentPackageName = file.packageFqName
|
||||||
|
private val withAlias: Set<FqName> = file.importDirectives
|
||||||
|
.asSequence()
|
||||||
|
.filter { it.alias != null && it.aliasName != it.importPath?.fqName?.shortName()?.asString() }
|
||||||
|
.mapNotNull(KtImportDirective::importedFqName)
|
||||||
|
.toSet()
|
||||||
|
|
||||||
private val descriptorsToImport = HashSet<DeclarationDescriptor>()
|
private val descriptorsToImport = HashSet<DeclarationDescriptor>()
|
||||||
private val abstractRefs = ArrayList<OptimizedImportsBuilder.AbstractReference>()
|
private val abstractRefs = ArrayList<OptimizedImportsBuilder.AbstractReference>()
|
||||||
|
|
||||||
@@ -107,7 +112,7 @@ class KotlinImportOptimizer : ImportOptimizer {
|
|||||||
val importableFqName = target.importableFqName ?: continue
|
val importableFqName = target.importableFqName ?: continue
|
||||||
val parentFqName = importableFqName.parent()
|
val parentFqName = importableFqName.parent()
|
||||||
if (target is PackageViewDescriptor && parentFqName == FqName.ROOT) continue // no need to import top-level packages
|
if (target is PackageViewDescriptor && parentFqName == FqName.ROOT) continue // no need to import top-level packages
|
||||||
if (target !is PackageViewDescriptor && parentFqName == currentPackageName) continue
|
if (target !is PackageViewDescriptor && parentFqName == currentPackageName && importableFqName !in withAlias) continue
|
||||||
|
|
||||||
if (!reference.canBeResolvedViaImport(target, bindingContext)) continue
|
if (!reference.canBeResolvedViaImport(target, bindingContext)) continue
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1 @@
|
|||||||
|
const val name = 42
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
import name
|
||||||
|
import name as names
|
||||||
|
|
||||||
|
val a = name
|
||||||
@@ -0,0 +1,4 @@
|
|||||||
|
import name
|
||||||
|
import name as names
|
||||||
|
|
||||||
|
val a = name
|
||||||
@@ -0,0 +1,5 @@
|
|||||||
|
package duration
|
||||||
|
|
||||||
|
val Int.hours: Int get() = TODO()
|
||||||
|
val Int.minutes: Int get() = TODO()
|
||||||
|
val Int.seconds: Int get() = TODO()
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
import duration.*
|
||||||
|
import duration.hours as hour
|
||||||
|
import duration.minutes as minute
|
||||||
|
import duration.minutes as minutes
|
||||||
|
import duration.seconds as second
|
||||||
|
import duration.seconds as seconds
|
||||||
|
|
||||||
|
fun main() {
|
||||||
|
val totalDuration = 1.hour - 30.minutes + 1.second
|
||||||
|
println(totalDuration)
|
||||||
|
}
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
import duration.minutes
|
||||||
|
import duration.hours as hour
|
||||||
|
import duration.seconds as second
|
||||||
|
|
||||||
|
fun main() {
|
||||||
|
val totalDuration = 1.hour - 30.minutes + 1.second
|
||||||
|
println(totalDuration)
|
||||||
|
}
|
||||||
@@ -0,0 +1,13 @@
|
|||||||
|
Additional checking of reference Getter: hour
|
||||||
|
Additional checking of reference KtSimpleNameReference: hour
|
||||||
|
Changed resolve of KtSimpleNameReference: hour
|
||||||
|
Additional checking of reference Getter: second
|
||||||
|
Additional checking of reference KtSimpleNameReference: second
|
||||||
|
Changed resolve of KtSimpleNameReference: second
|
||||||
|
Trying to build import list again with import rules: +duration.hours as hour, +duration.seconds as second
|
||||||
|
Additional checking of reference Getter: hour
|
||||||
|
Additional checking of reference KtSimpleNameReference: hour
|
||||||
|
Changed resolve of KtSimpleNameReference: hour
|
||||||
|
Additional checking of reference Getter: second
|
||||||
|
Additional checking of reference KtSimpleNameReference: second
|
||||||
|
Changed resolve of KtSimpleNameReference: second
|
||||||
+1
@@ -0,0 +1 @@
|
|||||||
|
const val name = 42
|
||||||
+4
@@ -0,0 +1,4 @@
|
|||||||
|
import name
|
||||||
|
import name as names
|
||||||
|
|
||||||
|
val a = name
|
||||||
+10
@@ -64,6 +64,16 @@ public class JsOptimizeImportsTestGenerated extends AbstractJsOptimizeImportsTes
|
|||||||
runTest("idea/testData/editor/optimizeImports/common/ComponentFunction.kt");
|
runTest("idea/testData/editor/optimizeImports/common/ComponentFunction.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("ConflictWithAlias.kt")
|
||||||
|
public void testConflictWithAlias() throws Exception {
|
||||||
|
runTest("idea/testData/editor/optimizeImports/common/ConflictWithAlias.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("ConflictWithAlias2.kt")
|
||||||
|
public void testConflictWithAlias2() throws Exception {
|
||||||
|
runTest("idea/testData/editor/optimizeImports/common/ConflictWithAlias2.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("CurrentPackage.kt")
|
@TestMetadata("CurrentPackage.kt")
|
||||||
public void testCurrentPackage() throws Exception {
|
public void testCurrentPackage() throws Exception {
|
||||||
runTest("idea/testData/editor/optimizeImports/common/CurrentPackage.kt");
|
runTest("idea/testData/editor/optimizeImports/common/CurrentPackage.kt");
|
||||||
|
|||||||
+10
@@ -257,6 +257,16 @@ public class JvmOptimizeImportsTestGenerated extends AbstractJvmOptimizeImportsT
|
|||||||
runTest("idea/testData/editor/optimizeImports/common/ComponentFunction.kt");
|
runTest("idea/testData/editor/optimizeImports/common/ComponentFunction.kt");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@TestMetadata("ConflictWithAlias.kt")
|
||||||
|
public void testConflictWithAlias() throws Exception {
|
||||||
|
runTest("idea/testData/editor/optimizeImports/common/ConflictWithAlias.kt");
|
||||||
|
}
|
||||||
|
|
||||||
|
@TestMetadata("ConflictWithAlias2.kt")
|
||||||
|
public void testConflictWithAlias2() throws Exception {
|
||||||
|
runTest("idea/testData/editor/optimizeImports/common/ConflictWithAlias2.kt");
|
||||||
|
}
|
||||||
|
|
||||||
@TestMetadata("CurrentPackage.kt")
|
@TestMetadata("CurrentPackage.kt")
|
||||||
public void testCurrentPackage() throws Exception {
|
public void testCurrentPackage() throws Exception {
|
||||||
runTest("idea/testData/editor/optimizeImports/common/CurrentPackage.kt");
|
runTest("idea/testData/editor/optimizeImports/common/CurrentPackage.kt");
|
||||||
|
|||||||
Reference in New Issue
Block a user