Tweak light classes to avoid computing stubs on certain api calls

Should speed up completion from java for certain cases
This commit is contained in:
Pavel V. Talanov
2015-10-16 15:19:23 +03:00
parent 8d88109c00
commit d74a989d93
5 changed files with 69 additions and 17 deletions
@@ -0,0 +1,58 @@
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
/*
* Copyright 2010-2015 JetBrains s.r.o.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jetbrains.kotlin.asJava
import com.intellij.openapi.vfs.VirtualFile
import com.intellij.psi.ClassFileViewProvider
import com.intellij.psi.PsiClass
import com.intellij.psi.PsiElement
import com.intellij.psi.PsiManager
import com.intellij.psi.impl.compiled.ClsFileImpl
import com.intellij.psi.stubs.PsiClassHolderFileStub
import org.jetbrains.kotlin.name.FqName
open class FakeFileForLightClass(
private val packageFqName: FqName,
virtualFile: VirtualFile,
psiManager: PsiManager,
private val lightClass: KotlinLightClass,
private val stub: () -> PsiClassHolderFileStub<*>
) : ClsFileImpl(ClassFileViewProvider(psiManager, virtualFile)) {
override fun getPackageName() = packageFqName.asString()
override fun getStub() = stub()
override fun getClasses() = arrayOf(lightClass)
override fun getNavigationElement() = this
}
@@ -465,7 +465,7 @@ public class KotlinJavaFileStubProvider<T extends WithFileStubAndExtraDiagnostic
} }
@NotNull @NotNull
public static ClsFileImpl createFakeClsFile( private static ClsFileImpl createFakeClsFile(
@NotNull Project project, @NotNull Project project,
@NotNull final FqName packageFqName, @NotNull final FqName packageFqName,
@NotNull Collection<JetFile> files, @NotNull Collection<JetFile> files,
@@ -19,14 +19,12 @@ package org.jetbrains.kotlin.asJava
import com.intellij.openapi.util.Comparing import com.intellij.openapi.util.Comparing
import com.intellij.openapi.util.Key import com.intellij.openapi.util.Key
import com.intellij.psi.* import com.intellij.psi.*
import com.intellij.psi.impl.compiled.ClsFileImpl
import com.intellij.psi.impl.java.stubs.PsiJavaFileStub import com.intellij.psi.impl.java.stubs.PsiJavaFileStub
import com.intellij.psi.impl.light.LightClass import com.intellij.psi.impl.light.LightClass
import com.intellij.psi.impl.light.LightMethod import com.intellij.psi.impl.light.LightMethod
import com.intellij.psi.scope.PsiScopeProcessor import com.intellij.psi.scope.PsiScopeProcessor
import com.intellij.psi.search.SearchScope import com.intellij.psi.search.SearchScope
import com.intellij.psi.stubs.IStubElementType import com.intellij.psi.stubs.IStubElementType
import com.intellij.psi.stubs.PsiClassHolderFileStub
import com.intellij.psi.stubs.StubElement import com.intellij.psi.stubs.StubElement
import com.intellij.psi.util.CachedValue import com.intellij.psi.util.CachedValue
import com.intellij.psi.util.CachedValuesManager import com.intellij.psi.util.CachedValuesManager
@@ -185,13 +183,7 @@ public open class KotlinLightClassForExplicitDeclaration(
val virtualFile = classOrObject.containingFile.virtualFile val virtualFile = classOrObject.containingFile.virtualFile
assert(virtualFile != null) { "No virtual file for " + classOrObject.text } assert(virtualFile != null) { "No virtual file for " + classOrObject.text }
object : ClsFileImpl(ClassFileViewProvider(getManager(), virtualFile)) { object : FakeFileForLightClass(classOrObject.getContainingJetFile().packageFqName, virtualFile, myManager, this, { getJavaFileStub() }) {
override fun getPackageName(): String {
return classOrObject.getContainingJetFile().packageFqName.asString()
}
override fun getStub(): PsiClassHolderFileStub<PsiJavaFile> = getJavaFileStub()
override fun processDeclarations( override fun processDeclarations(
processor: PsiScopeProcessor, processor: PsiScopeProcessor,
state: ResolveState, state: ResolveState,
@@ -244,8 +236,6 @@ public open class KotlinLightClassForExplicitDeclaration(
override fun getParent(): PsiElement? = _parent override fun getParent(): PsiElement? = _parent
override fun getContext(): PsiElement? = getParent()
private val _typeParameterList: PsiTypeParameterList by lazy { private val _typeParameterList: PsiTypeParameterList by lazy {
LightClassUtil.buildLightTypeParameterList(this, classOrObject) LightClassUtil.buildLightTypeParameterList(this, classOrObject)
} }
@@ -20,7 +20,6 @@ import com.intellij.openapi.components.ServiceManager
import com.intellij.openapi.project.Project import com.intellij.openapi.project.Project
import com.intellij.openapi.util.Comparing import com.intellij.openapi.util.Comparing
import com.intellij.psi.* import com.intellij.psi.*
import com.intellij.psi.impl.compiled.ClsFileImpl
import com.intellij.psi.impl.light.LightEmptyImplementsList import com.intellij.psi.impl.light.LightEmptyImplementsList
import com.intellij.psi.impl.light.LightModifierList import com.intellij.psi.impl.light.LightModifierList
import com.intellij.psi.search.GlobalSearchScope import com.intellij.psi.search.GlobalSearchScope
@@ -116,8 +115,8 @@ public class KotlinLightClassForFacade private constructor(
private val implementsList: LightEmptyImplementsList = private val implementsList: LightEmptyImplementsList =
LightEmptyImplementsList(manager) LightEmptyImplementsList(manager)
private val packageClsFile: ClsFileImpl = KotlinJavaFileStubProvider.createFakeClsFile(manager.getProject(), packageFqName, files) { private val packageClsFile = FakeFileForLightClass(packageFqName, files.first().virtualFile!!, myManager, this) {
(getDelegate().getContainingFile() as ClsFileImpl).getStub() lightClassDataCache.value.javaFileStub
} }
override fun getOrigin(): JetClassOrObject? = null override fun getOrigin(): JetClassOrObject? = null
@@ -190,8 +189,8 @@ public class KotlinLightClassForFacade private constructor(
override fun copy() = KotlinLightClassForFacade(getManager(), facadeClassFqName, searchScope, lightClassDataCache, files, deprecated) override fun copy() = KotlinLightClassForFacade(getManager(), facadeClassFqName, searchScope, lightClassDataCache, files, deprecated)
override fun getDelegate(): PsiClass { override fun getDelegate(): PsiClass {
val psiClass = LightClassUtil.findClass(facadeClassFqName, lightClassDataCache.getValue().javaFileStub) val psiClass = LightClassUtil.findClass(facadeClassFqName, lightClassDataCache.value.javaFileStub)
?: throw IllegalStateException("Facade class $facadeClassFqName not found") ?: throw IllegalStateException("Facade class $facadeClassFqName not found")
return psiClass return psiClass
} }
@@ -211,4 +211,9 @@ public abstract class KotlinWrappingLightClass extends AbstractLightClass implem
@Override @Override
public abstract int hashCode(); public abstract int hashCode();
@Override
public PsiElement getContext() {
return getParent();
}
} }