mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
IDEA-292945 New Inspection: \d is redundant with \w in the same class (\D with \W)
GitOrigin-RevId: 7c2e57a4e3bf8a61e08bf326460576766f851a98
This commit is contained in:
committed by
intellij-monorepo-bot
parent
7e8c6b7725
commit
677bd7e889
@@ -80,5 +80,8 @@
|
||||
<localInspection language="RegExp" shortName="RegExpSimplifiable" enabledByDefault="true" level="WEAK WARNING"
|
||||
bundle="messages.RegExpBundle" groupKey="inspection.group.name.regexp" key="inspection.name.simplifiable.expression"
|
||||
implementationClass="org.intellij.lang.regexp.inspection.RegExpSimplifiableInspection"/>
|
||||
<localInspection language="RegExp" shortName="RegExpRedundantClassElement" enabledByDefault="true" level="WEAK WARNING"
|
||||
bundle="messages.RegExpBundle" groupKey="inspection.group.name.regexp" key="inspection.name.redundant.digit.class.element"
|
||||
implementationClass="org.intellij.lang.regexp.inspection.RegExpRedundantClassElementInspection"/>
|
||||
</extensions>
|
||||
</idea-plugin>
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
<html>
|
||||
<body>
|
||||
Reports redundant <code>\d</code> or <code>[:digit:]</code> that are used in one class with <code>\w</code> or <code>[:word:]</code>
|
||||
(<code>\D</code> with <code>\W</code>) and can be removed.
|
||||
<p><b>Example:</b></p>
|
||||
<pre><code>
|
||||
[\w\d]
|
||||
</code></pre>
|
||||
<p>After the quick-fix is applied:</p>
|
||||
<pre><code>
|
||||
[\w]
|
||||
</code></pre>
|
||||
<!-- tooltip end -->
|
||||
<p><small>New in 2022.2</small>
|
||||
</body>
|
||||
</html>
|
||||
@@ -78,6 +78,7 @@ inspection.name.simplifiable.expression=Regular expression can be simplified
|
||||
inspection.name.single.character.alternation=Single character alternation
|
||||
inspection.name.suspicious.backref=Suspicious back reference
|
||||
inspection.name.unnecessary.non.capturing.group=Unnecessary non-capturing group
|
||||
inspection.name.redundant.digit.class.element=Redundant '\\d', '[:digit:]', or '\\D' class elements
|
||||
inspection.option.ignore.escaped.closing.brackets=Ignore escaped closing brackets '}' and ']'
|
||||
inspection.quick.fix.remove.duplicate.0.from.character.class=Remove duplicate ''{0}'' from character class
|
||||
inspection.quick.fix.remove.duplicate.branch=Remove duplicate branch
|
||||
@@ -85,6 +86,8 @@ inspection.quick.fix.remove.duplicate.element.from.character.class=Remove duplic
|
||||
inspection.quick.fix.remove.empty.branch=Remove empty branch
|
||||
inspection.quick.fix.remove.redundant.escape=Remove redundant escape
|
||||
inspection.quick.fix.remove.unnecessary.non.capturing.group=Unwrap unnecessary non-capturing group
|
||||
inspection.quick.fix.remove.redundant.0.class.element=Remove redundant ''{0}''
|
||||
inspection.quick.fix.remove.redundant.class.element=Remove redundant class element
|
||||
inspection.quick.fix.replace.alternation.with.character.class=Replace alternation with character class
|
||||
inspection.quick.fix.replace.redundant.character.class.with.contents=Replace redundant character class with contents
|
||||
inspection.quick.fix.replace.with.character.inside.class=Replace with character inside class
|
||||
@@ -105,6 +108,7 @@ inspection.warning.octal.escape.code.ref.code.in.regexp=Octal escape <code>#ref<
|
||||
inspection.warning.potential.exponential.backtracking=Potential exponential backtracking
|
||||
inspection.warning.redundant.character.escape.0.in.regexp=Redundant character escape <code>{0}</code> in RegExp
|
||||
inspection.warning.redundant.nested.character.class=Redundant nested character class
|
||||
inspection.warning.redundant.class.element=Redundant ''{0}'' in RegExp
|
||||
inspection.warning.single.character.alternation.in.regexp=Single character alternation in RegExp
|
||||
inspection.warning.unnecessary.non.capturing.group=Unnecessary non-capturing group <code>{0}</code>
|
||||
intention.name.check.regexp=Check RegExp
|
||||
|
||||
+83
@@ -0,0 +1,83 @@
|
||||
// Copyright 2000-2022 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
|
||||
package org.intellij.lang.regexp.inspection;
|
||||
|
||||
import com.intellij.codeInspection.LocalInspectionTool;
|
||||
import com.intellij.codeInspection.LocalQuickFix;
|
||||
import com.intellij.codeInspection.ProblemDescriptor;
|
||||
import com.intellij.codeInspection.ProblemsHolder;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.psi.PsiElement;
|
||||
import com.intellij.psi.PsiElementVisitor;
|
||||
import com.intellij.util.ObjectUtils;
|
||||
import com.intellij.util.containers.ContainerUtil;
|
||||
import org.intellij.lang.regexp.RegExpBundle;
|
||||
import org.intellij.lang.regexp.psi.*;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import static org.intellij.lang.regexp.psi.RegExpSimpleClass.Kind.*;
|
||||
import static org.intellij.lang.regexp.psi.RegExpSimpleClass.Kind.NON_WORD;
|
||||
|
||||
public class RegExpRedundantClassElementInspection extends LocalInspectionTool {
|
||||
@Override
|
||||
public @NotNull PsiElementVisitor buildVisitor(@NotNull ProblemsHolder holder, boolean isOnTheFly) {
|
||||
return new RegExpElementVisitor() {
|
||||
@Override
|
||||
public void visitRegExpClass(RegExpClass regExpClass) {
|
||||
RegExpClass regExp = ObjectUtils.tryCast(regExpClass, RegExpClass.class);
|
||||
if (regExp == null) return;
|
||||
RegExpClassElement[] classElements = regExp.getElements();
|
||||
boolean containsNonWordCharacterClass =
|
||||
ContainerUtil.exists(classElements, RegExpRedundantClassElementInspection::isAnyNonWordCharacter);
|
||||
boolean containsWordCharacterClass =
|
||||
ContainerUtil.exists(classElements, RegExpRedundantClassElementInspection::isAnyWordCharacter);
|
||||
for (RegExpClassElement element : classElements) {
|
||||
if (containsWordCharacterClass && isAnyDigit(element) || containsNonWordCharacterClass && isAnyNonDigit(element)) {
|
||||
String elementText = element.getText();
|
||||
holder.registerProblem(element, RegExpBundle.message("inspection.warning.redundant.class.element", elementText), new RemoveRedundantClassElement(elementText));
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private static boolean isAnyDigit(RegExpClassElement classElement) {
|
||||
return classElement instanceof RegExpSimpleClass && ((RegExpSimpleClass)classElement).getKind().equals(DIGIT) ||
|
||||
classElement instanceof RegExpPosixBracketExpression && ((RegExpPosixBracketExpression)classElement).getClassName().equals("digit");
|
||||
}
|
||||
|
||||
private static boolean isAnyNonDigit(RegExpClassElement classElement) {
|
||||
return classElement instanceof RegExpSimpleClass && ((RegExpSimpleClass)classElement).getKind().equals(NON_DIGIT);
|
||||
}
|
||||
|
||||
private static boolean isAnyWordCharacter(RegExpClassElement classElement) {
|
||||
return classElement instanceof RegExpSimpleClass && ((RegExpSimpleClass)classElement).getKind().equals(WORD) ||
|
||||
classElement instanceof RegExpPosixBracketExpression && ((RegExpPosixBracketExpression)classElement).getClassName().equals("word");
|
||||
}
|
||||
|
||||
private static boolean isAnyNonWordCharacter(RegExpClassElement classElement) {
|
||||
return classElement instanceof RegExpSimpleClass && ((RegExpSimpleClass)classElement).getKind().equals(NON_WORD);
|
||||
}
|
||||
|
||||
private static class RemoveRedundantClassElement implements LocalQuickFix {
|
||||
private final String myClassElementText;
|
||||
|
||||
private RemoveRedundantClassElement(String text) { myClassElementText = text; }
|
||||
|
||||
@Override
|
||||
public @NotNull String getFamilyName() {
|
||||
return RegExpBundle.message("inspection.quick.fix.remove.redundant.class.element");
|
||||
}
|
||||
|
||||
@Override
|
||||
public @NotNull String getName() {
|
||||
return RegExpBundle.message("inspection.quick.fix.remove.redundant.0.class.element", myClassElementText);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void applyFix(@NotNull Project project, @NotNull ProblemDescriptor descriptor) {
|
||||
PsiElement element = descriptor.getPsiElement();
|
||||
if (element == null) return;
|
||||
element.delete();
|
||||
}
|
||||
}
|
||||
}
|
||||
+27
@@ -0,0 +1,27 @@
|
||||
// Copyright 2000-2022 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
|
||||
package org.intellij.lang.regexp.inspection;
|
||||
|
||||
import com.intellij.codeInspection.LocalInspectionTool;
|
||||
import org.intellij.lang.regexp.RegExpBundle;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class RegExpRedundantClassElementInspectionTest extends RegExpInspectionTestCase {
|
||||
@Override
|
||||
protected @NotNull LocalInspectionTool getInspection() {
|
||||
return new RegExpRedundantClassElementInspection();
|
||||
}
|
||||
|
||||
public void testAnyDigit() {
|
||||
quickfixTest("[\\w.<weak_warning descr=\"Redundant '\\d' in RegExp\"><caret>\\d</weak_warning>]",
|
||||
"[\\w.]", RegExpBundle.message("inspection.quick.fix.remove.redundant.0.class.element", "\\d"));
|
||||
}
|
||||
|
||||
public void testAnyNonDigit() {
|
||||
quickfixTest("^[\\W.<weak_warning descr=\"Redundant '\\D' in RegExp\"><caret>\\D</weak_warning>]",
|
||||
"^[\\W.]", RegExpBundle.message("inspection.quick.fix.remove.redundant.0.class.element", "\\D"));
|
||||
}
|
||||
|
||||
public void testNoHighlighting() {
|
||||
highlightTest("\\w{2}[.,]?[\\d\\W]");
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user