make JvmElementActionsFactory a regular EP instead of a language EP

This commit is contained in:
Daniil Ovchinnikov
2017-08-28 13:33:36 +03:00
parent e1a6c4eddf
commit 176be0e190
7 changed files with 82 additions and 58 deletions
@@ -16,11 +16,8 @@
package com.intellij.lang.jvm.actions
import com.intellij.codeInsight.intention.IntentionAction
import com.intellij.lang.Language
import com.intellij.lang.LanguageExtension
import com.intellij.lang.jvm.JvmClass
import com.intellij.lang.jvm.JvmModifiersOwner
import com.intellij.openapi.components.ServiceManager
import org.jetbrains.annotations.ApiStatus
/**
@@ -43,16 +40,4 @@ abstract class JvmElementActionsFactory {
open fun createAddMethodActions(targetClass: JvmClass, request: MemberRequest.Method): List<IntentionAction> = emptyList()
open fun createAddPropertyActions(targetClass: JvmClass, request: MemberRequest.Property): List<IntentionAction> = emptyList()
companion object : LanguageExtension<JvmElementActionsFactory>(
"com.intellij.lang.jvm.actions.jvmElementActionsFactory") {
@JvmStatic
override fun forLanguage(l: Language): JvmElementActionsFactory? =
super.forLanguage(l)
?: ServiceManager.getService(JvmElementActionsFactoryFallback::class.java).forLanguage(l)
}
}
@@ -0,0 +1,62 @@
/*
* Copyright 2000-2017 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.
*/
@file:JvmName("JvmElementActionFactories")
package com.intellij.lang.jvm.actions
import com.intellij.codeInsight.intention.IntentionAction
import com.intellij.lang.jvm.JvmClass
import com.intellij.lang.jvm.JvmModifiersOwner
import com.intellij.openapi.extensions.ExtensionPointName
private val EP_NAME = ExtensionPointName.create<JvmElementActionsFactory>("com.intellij.lang.jvm.actions.jvmElementActionsFactory")
private inline fun createActions(crossinline actions: (JvmElementActionsFactory) -> List<IntentionAction>): List<IntentionAction> {
return EP_NAME.extensions.flatMap {
actions(it)
}
}
fun createModifierActions(target: JvmModifiersOwner, request: MemberRequest.Modifier): List<IntentionAction> {
return createActions {
it.createChangeModifierActions(target, request)
}
}
fun createConstructorActions(target: JvmClass, request: MemberRequest.Constructor): List<IntentionAction> {
return createActions {
it.createAddConstructorActions(target, request)
}
}
fun createMethodAction(target: JvmClass, request: MemberRequest.Method): IntentionAction? {
for (factory in EP_NAME.extensions) {
return factory.createAddMethodActions(target, request).firstOrNull() ?: continue
}
return null
}
fun createMethodActions(target: JvmClass, request: MemberRequest.Method): List<IntentionAction> {
return createActions {
it.createAddMethodActions(target, request)
}
}
fun createPropertyActions(target: JvmClass, request: MemberRequest.Property): List<IntentionAction> {
return createActions {
it.createAddPropertyActions(target, request)
}
}
@@ -22,8 +22,8 @@ import com.intellij.codeInspection.*
import com.intellij.lang.jvm.JvmClass
import com.intellij.lang.jvm.JvmModifier
import com.intellij.lang.jvm.JvmModifiersOwner
import com.intellij.lang.jvm.actions.JvmElementActionsFactory
import com.intellij.lang.jvm.actions.MemberRequest
import com.intellij.lang.jvm.actions.createModifierActions
import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.diagnostic.Logger
import com.intellij.openapi.project.Project
@@ -61,13 +61,11 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
val smartPointerManager = SmartPointerManager.getInstance(aClass.project)
val actionsFactory = JvmElementActionsFactory.forLanguage(aClass.language)
for ((method, description) in methodsToOverride) {
if (method.isFinal || method.isStatic || method.hasModifierProperty(PsiModifier.PRIVATE)) {
methodsToAttachToClassFix?.add(smartPointerManager.createSmartPsiElementPointer(method, method.containingFile))
val methodFixes = createFixesIfApplicable(actionsFactory, method, method.name)
val methodFixes = createFixesIfApplicable(method, method.name)
problemTargets(method, methodHighlightableModifiersSet).forEach {
problems.add(manager.createProblemDescriptor(
it, description, isOnTheFly,
@@ -84,7 +82,7 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
problems.add(manager.createProblemDescriptor(
it, classReasonToBeSubclassed ?: InspectionsBundle.message("inspection.implicit.subclass.display.forClass", aClass.name),
isOnTheFly,
createFixesIfApplicable(actionsFactory, aClass, aClass.name ?: "class", methodsToAttachToClassFix ?: emptyList()),
createFixesIfApplicable(aClass, aClass.name ?: "class", methodsToAttachToClassFix ?: emptyList()),
ProblemHighlightType.GENERIC_ERROR_OR_WARNING)
)
}
@@ -94,12 +92,10 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
return problems.toTypedArray()
}
private fun createFixesIfApplicable(actionsFactory: JvmElementActionsFactory?,
aClass: UDeclaration,
private fun createFixesIfApplicable(aClass: UDeclaration,
hintTargetName: String,
methodsToAttachToClassFix: List<SmartPsiElementPointer<UDeclaration>> = emptyList()): Array<LocalQuickFix> {
if (actionsFactory == null) return emptyArray()
val fix = MakeExtendableFix(aClass, hintTargetName, actionsFactory, methodsToAttachToClassFix)
val fix = MakeExtendableFix(aClass, hintTargetName, methodsToAttachToClassFix)
if (!fix.hasActionsToPerform) return emptyArray()
return arrayOf(fix)
}
@@ -123,7 +119,6 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
private class MakeExtendableFix(uDeclaration: UDeclaration,
hintTargetName: String,
val actionsFactory: JvmElementActionsFactory,
val siblings: List<SmartPsiElementPointer<UDeclaration>> = emptyList())
: LocalQuickFixOnPsiElement(uDeclaration) {
@@ -133,8 +128,7 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
private val actionsToPerform = SmartList<IntentionAction>()
val hasActionsToPerform: Boolean
get() = actionsToPerform.isNotEmpty()
val hasActionsToPerform: Boolean get() = actionsToPerform.isNotEmpty()
init {
collectMakeExtendable(uDeclaration, actionsToPerform)
@@ -187,12 +181,9 @@ class ImplicitSubclassInspection : AbstractBaseUastLocalInspectionTool() {
modifier: JvmModifier,
shouldPresent: Boolean,
actionsList: SmartList<IntentionAction>) {
if (declaration.hasModifier(modifier) != shouldPresent) {
actionsFactory.createChangeModifierActions(declaration, MemberRequest.Modifier(modifier,
shouldPresent)).let {
actionsList.addAll(it)
}
}
if (declaration.hasModifier(modifier) == shouldPresent) return
val request = MemberRequest.Modifier(modifier, shouldPresent)
actionsList += createModifierActions(declaration, request)
}
private val MAX_MESSAGES_TO_COMBINE = 3
@@ -19,8 +19,8 @@ import com.intellij.codeInsight.intention.IntentionAction
import com.intellij.codeInspection.LocalQuickFixBase
import com.intellij.codeInspection.ProblemDescriptor
import com.intellij.lang.jvm.JvmModifier
import com.intellij.lang.jvm.actions.JvmElementActionsFactory
import com.intellij.lang.jvm.actions.MemberRequest
import com.intellij.lang.jvm.actions.createMethodAction
import com.intellij.openapi.module.ModuleUtilCore
import com.intellij.openapi.project.Project
import com.intellij.psi.*
@@ -59,10 +59,8 @@ class CreateMethodFix(containingClass: @JvmCommon PsiClass, private val createMe
methodName: String,
modifier: JvmModifier): CreateMethodFix? {
if (!ModuleUtilCore.projectContainsFile(psiClass.project, psiClass.containingFile.virtualFile, false)) return null
val actionsFactory = JvmElementActionsFactory.forLanguage(psiClass.language) ?: return null
val action = actionsFactory.createAddMethodActions(psiClass,
MemberRequest.simpleMethodRequest(methodName, modifier, PsiType.VOID, emptyList())
).firstOrNull() ?: return null
val request = MemberRequest.simpleMethodRequest(methodName, modifier, PsiType.VOID, emptyList())
val action = createMethodAction(psiClass, request) ?: return null
return CreateMethodFix(psiClass, action)
}
}
@@ -1,5 +1,5 @@
/*
* Copyright 2000-2014 JetBrains s.r.o.
* Copyright 2000-2017 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.
@@ -19,7 +19,6 @@ import com.intellij.codeInsight.intention.IntentionAction;
import com.intellij.codeInspection.IntentionWrapper;
import com.intellij.codeInspection.LocalQuickFix;
import com.intellij.lang.jvm.JvmModifier;
import com.intellij.lang.jvm.actions.JvmElementActionsFactory;
import com.intellij.lang.jvm.actions.MemberRequest;
import com.intellij.openapi.project.Project;
import com.intellij.psi.*;
@@ -28,6 +27,7 @@ import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import static com.intellij.lang.jvm.actions.JvmElementActionFactories.createPropertyActions;
import static com.intellij.psi.CommonClassNames.JAVA_LANG_STRING;
import static com.intellij.util.ArrayUtil.toObjectArray;
@@ -53,11 +53,7 @@ public class CreateBeanPropertyFixes {
if (aClass == null) return IntentionAction.EMPTY_ARRAY;
type = facade.getElementFactory().createType(aClass);
}
JvmElementActionsFactory factory = JvmElementActionsFactory.forLanguage(psiClass.getLanguage());
if (factory == null) return IntentionAction.EMPTY_ARRAY;
return toObjectArray(
factory.createAddPropertyActions(psiClass,
new MemberRequest.Property(propertyName, JvmModifier.PUBLIC, type, createSetter, !createSetter)),
IntentionAction.class);
MemberRequest.Property request = new MemberRequest.Property(propertyName, JvmModifier.PUBLIC, type, createSetter, !createSetter);
return toObjectArray(createPropertyActions(psiClass, request), IntentionAction.class);
}
}
@@ -17,7 +17,7 @@ package org.jetbrains.plugins.javaFX.fxml.refs;
import com.intellij.codeInsight.daemon.QuickFixActionRegistrar;
import com.intellij.codeInsight.quickfix.UnresolvedReferenceQuickFixProvider;
import com.intellij.lang.jvm.actions.JvmElementActionsFactory;
import com.intellij.lang.jvm.actions.JvmElementActionFactories;
import com.intellij.lang.jvm.actions.MemberRequest;
import com.intellij.openapi.project.Project;
import com.intellij.openapi.util.TextRange;
@@ -100,10 +100,6 @@ public class JavaFxEventHandlerReference extends PsiReferenceBase<XmlAttributeVa
@Override
public void registerFixes(@NotNull final JavaFxEventHandlerReference ref, @NotNull final QuickFixActionRegistrar registrar) {
if (ref.myController != null && ref.myEventHandler == null) {
JvmElementActionsFactory intentionActionsFactory =
JvmElementActionsFactory.forLanguage(ref.myController.getLanguage());
if (intentionActionsFactory == null) return;
String javaSignature = getHandlerSignature(ref);
PsiMethod javaMethod = JavaPsiFacade.getElementFactory(ref.myController.getProject())
.createMethodFromText(javaSignature, ref.myController);
@@ -114,7 +110,7 @@ public class JavaFxEventHandlerReference extends PsiReferenceBase<XmlAttributeVa
Arrays.asList(javaMethod.getModifiers()),
javaMethod.getReturnType(),
Arrays.asList(javaMethod.getParameterList().getParameters()));
intentionActionsFactory.createAddMethodActions(ref.myController, method).forEach(registrar::register);
JvmElementActionFactories.createMethodActions(ref.myController, method).forEach(registrar::register);
}
}
+2 -6
View File
@@ -329,10 +329,7 @@
<extensionPoint qualifiedName="com.intellij.codeInsight.intention.jvmCommonIntentionActionsFactory" beanClass="com.intellij.lang.LanguageExtensionPoint">
<with attribute="implementationClass" implements="com.intellij.codeInsight.intention.JvmCommonIntentionActionsFactory"/>
</extensionPoint>
<extensionPoint qualifiedName="com.intellij.lang.jvm.actions.jvmElementActionsFactory"
beanClass="com.intellij.lang.LanguageExtensionPoint">
<with attribute="implementationClass" implements="com.intellij.lang.jvm.actions.JvmElementActionsFactory"/>
</extensionPoint>
<extensionPoint name="lang.jvm.actions.jvmElementActionsFactory" interface="com.intellij.lang.jvm.actions.JvmElementActionsFactory"/>
<extensionPoint name="javaModuleSystem" interface="com.intellij.psi.JavaModuleSystem"/>
@@ -2023,8 +2020,7 @@
<projectService serviceInterface="org.jetbrains.uast.UastContext" serviceImplementation="org.jetbrains.uast.UastContext"/>
<metaLanguage implementation="com.intellij.uast.UastMetaLanguage"/>
<smartPointer.anchorProvider implementation="com.intellij.uast.UastElementAnchorProvider"/>
<lang.jvm.actions.jvmElementActionsFactory language="JAVA"
implementationClass="com.intellij.codeInsight.intention.impl.JavaElementActionsFactoryImpl"/>
<lang.jvm.actions.jvmElementActionsFactory implementation="com.intellij.codeInsight.intention.impl.JavaElementActionsFactoryImpl"/>
<deadCode implementation="com.intellij.codeInspection.java19modules.Java9ModuleEntryPoint"/>