mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
IDEA-199839 Support deprecation in xsd schemas
This commit is contained in:
@@ -172,6 +172,7 @@ xml.inspections.unused.schema.remove=Remove unused namespace declaration
|
||||
|
||||
xml.inspections.path.resolve=File path resolving in XML
|
||||
xml.inspections.default.attribute.value=Redundant default attribute value assignment
|
||||
xml.inspections.deprecated=Deprecated elements
|
||||
|
||||
xml.inspections.global=XML highlighting
|
||||
|
||||
|
||||
@@ -438,6 +438,10 @@
|
||||
bundle="messages.XmlBundle" key="xml.inspections.default.attribute.value"
|
||||
groupBundle="messages.XmlBundle" groupKey="xml.inspections.group.name"
|
||||
implementationClass="com.intellij.codeInsight.daemon.impl.analysis.XmlDefaultAttributeValueInspection"/>
|
||||
<localInspection language="XML" enabledByDefault="true" level="WARNING"
|
||||
bundle="messages.XmlBundle" key="xml.inspections.deprecated"
|
||||
groupBundle="messages.XmlBundle" groupKey="xml.inspections.group.name"
|
||||
implementationClass="com.intellij.codeInsight.daemon.impl.analysis.XmlDeprecatedElementInspection"/>
|
||||
|
||||
<localInspection language="XML" shortName="CheckEmptyScriptTag" enabledByDefault="true" level="WARNING"
|
||||
bundle="messages.XmlBundle" key="html.inspections.check.empty.tag"
|
||||
|
||||
@@ -92,7 +92,7 @@ public class XmlDocumentationProvider implements DocumentationProvider {
|
||||
@Override
|
||||
public String generateDoc(PsiElement element, final PsiElement originalElement) {
|
||||
if (element instanceof XmlElementDecl) {
|
||||
PsiElement curElement = findPreviousComment(element);
|
||||
PsiElement curElement = XmlUtil.findPreviousComment(element);
|
||||
|
||||
if (curElement!=null) {
|
||||
return formatDocFromComment(curElement, ((XmlElementDecl)element).getNameElement().getText());
|
||||
@@ -138,7 +138,7 @@ public class XmlDocumentationProvider implements DocumentationProvider {
|
||||
}
|
||||
}
|
||||
if (processor.result == null) {
|
||||
final PsiElement comment = findPreviousComment(element);
|
||||
final PsiElement comment = XmlUtil.findPreviousComment(element);
|
||||
if (comment != null) {
|
||||
return formatDocFromComment(comment, ((XmlTag)element).getName());
|
||||
}
|
||||
@@ -153,7 +153,7 @@ public class XmlDocumentationProvider implements DocumentationProvider {
|
||||
} else if (element instanceof XmlAttributeDecl) {
|
||||
// Check for comment before attlist, it should not be right after previous declaration
|
||||
final PsiElement parent = element.getParent();
|
||||
final PsiElement previousComment = findPreviousComment(parent);
|
||||
final PsiElement previousComment = XmlUtil.findPreviousComment(parent);
|
||||
final String referenceName = ((XmlAttributeDecl)element).getNameElement().getText();
|
||||
|
||||
if (previousComment instanceof PsiComment) {
|
||||
@@ -249,26 +249,6 @@ public class XmlDocumentationProvider implements DocumentationProvider {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static PsiElement findPreviousComment(final PsiElement element) {
|
||||
PsiElement curElement = element;
|
||||
|
||||
while(curElement!=null && !(curElement instanceof XmlComment)) {
|
||||
curElement = curElement.getPrevSibling();
|
||||
if (curElement instanceof XmlText && StringUtil.isEmptyOrSpaces(curElement.getText())) {
|
||||
continue;
|
||||
}
|
||||
if (!(curElement instanceof PsiWhiteSpace) &&
|
||||
!(curElement instanceof XmlProlog) &&
|
||||
!(curElement instanceof XmlComment)
|
||||
) {
|
||||
curElement = null; // finding comment fails, we found another similar declaration
|
||||
break;
|
||||
}
|
||||
}
|
||||
return curElement;
|
||||
}
|
||||
|
||||
private String formatDocFromComment(final PsiElement curElement, final String name) {
|
||||
String text = curElement.getText();
|
||||
text = text.substring("<!--".length(),text.length()-"-->".length()).trim();
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
package com.intellij.codeInsight.daemon;
|
||||
|
||||
import com.intellij.codeInsight.daemon.impl.analysis.XmlDefaultAttributeValueInspection;
|
||||
import com.intellij.codeInsight.daemon.impl.analysis.XmlDeprecatedElementInspection;
|
||||
import com.intellij.codeInsight.intention.IntentionAction;
|
||||
import com.intellij.ide.highlighter.HtmlFileType;
|
||||
import com.intellij.ide.highlighter.XmlFileType;
|
||||
@@ -72,6 +73,11 @@ public class XmlInspectionsTest extends LightPlatformCodeInsightFixtureTestCase
|
||||
myFixture.testHighlighting("def.xml", "def.xsd");
|
||||
}
|
||||
|
||||
public void testDeprecations() {
|
||||
myFixture.enableInspections(new XmlDeprecatedElementInspection());
|
||||
myFixture.testHighlighting("deprecated.xml", "deprecated.xsd");
|
||||
}
|
||||
|
||||
@Override
|
||||
protected String getTestDataPath() {
|
||||
return PlatformTestUtil.getCommunityPath().replace(File.separatorChar, '/') + "/xml/tests/testData/xml";
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
<root xmlns="test.deprecated" <warning descr="The attribute is marked as deprecated">deprecated</warning>="">
|
||||
<<warning descr="The tag is marked as deprecated">deprecated</warning>/>
|
||||
</root>
|
||||
@@ -0,0 +1,12 @@
|
||||
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="test.deprecated" elementFormDefault="qualified">
|
||||
<element name="root">
|
||||
<complexType>
|
||||
<sequence>
|
||||
<!-- deprecated -->
|
||||
<element name="deprecated"/>
|
||||
</sequence>
|
||||
<!-- deprecated -->
|
||||
<attribute name="deprecated"/>
|
||||
</complexType>
|
||||
</element>
|
||||
</schema>
|
||||
@@ -0,0 +1,6 @@
|
||||
<html>
|
||||
<body>
|
||||
This inspection checks for deprecated XML elements.
|
||||
<p>The elements can be marked by XML comment or documentation tag with text "deprecated".
|
||||
</body>
|
||||
</html>
|
||||
+54
@@ -0,0 +1,54 @@
|
||||
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
|
||||
package com.intellij.codeInsight.daemon.impl.analysis;
|
||||
|
||||
import com.intellij.codeInspection.ProblemHighlightType;
|
||||
import com.intellij.codeInspection.ProblemsHolder;
|
||||
import com.intellij.codeInspection.XmlSuppressableInspectionTool;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiElementVisitor;
|
||||
import com.intellij.psi.XmlElementVisitor;
|
||||
import com.intellij.psi.meta.PsiMetaData;
|
||||
import com.intellij.psi.xml.XmlAttribute;
|
||||
import com.intellij.psi.xml.XmlChildRole;
|
||||
import com.intellij.psi.xml.XmlTag;
|
||||
import com.intellij.xml.util.XmlUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Locale;
|
||||
|
||||
public class XmlDeprecatedElementInspection extends XmlSuppressableInspectionTool {
|
||||
@NotNull
|
||||
@Override
|
||||
public PsiElementVisitor buildVisitor(@NotNull ProblemsHolder holder, boolean isOnTheFly) {
|
||||
return new XmlElementVisitor() {
|
||||
@Override
|
||||
public void visitXmlTag(XmlTag tag) {
|
||||
if (checkDeprecated(tag.getDescriptor())) {
|
||||
ASTNode nameNode = XmlChildRole.START_TAG_NAME_FINDER.findChild(tag.getNode());
|
||||
if (nameNode != null) {
|
||||
holder.registerProblem(nameNode.getPsi(), "The tag is marked as deprecated", ProblemHighlightType.LIKE_DEPRECATED);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void visitXmlAttribute(XmlAttribute attribute) {
|
||||
if (checkDeprecated(attribute.getDescriptor())) {
|
||||
holder.registerProblem(attribute.getNameElement(), "The attribute is marked as deprecated", ProblemHighlightType.LIKE_DEPRECATED);
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private static boolean checkDeprecated(@Nullable PsiMetaData metaData) {
|
||||
if (metaData == null) return false;
|
||||
PsiElement declaration = metaData.getDeclaration();
|
||||
if (declaration == null) return false;
|
||||
PsiElement comment = XmlUtil.findPreviousComment(declaration);
|
||||
if (comment == null) return false;
|
||||
return StringUtil.trimStart(comment.getText(), "<!--").toLowerCase(Locale.ENGLISH).trim().startsWith("deprecated");
|
||||
}
|
||||
}
|
||||
@@ -1413,6 +1413,26 @@ public class XmlUtil {
|
||||
return descriptor != null && !(descriptor instanceof AnyXmlElementDescriptor);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static PsiElement findPreviousComment(final PsiElement element) {
|
||||
PsiElement curElement = element;
|
||||
|
||||
while(curElement!=null && !(curElement instanceof XmlComment)) {
|
||||
curElement = curElement.getPrevSibling();
|
||||
if (curElement instanceof XmlText && StringUtil.isEmptyOrSpaces(curElement.getText())) {
|
||||
continue;
|
||||
}
|
||||
if (!(curElement instanceof PsiWhiteSpace) &&
|
||||
!(curElement instanceof XmlProlog) &&
|
||||
!(curElement instanceof XmlComment)
|
||||
) {
|
||||
curElement = null; // finding comment fails, we found another similar declaration
|
||||
break;
|
||||
}
|
||||
}
|
||||
return curElement;
|
||||
}
|
||||
|
||||
public interface DuplicationInfoProvider<T extends PsiElement> {
|
||||
@Nullable
|
||||
String getName(@NotNull T t);
|
||||
|
||||
Reference in New Issue
Block a user