IJPL-227246 [RegExp]: fix NPE with Custom RegExp inspections

GitOrigin-RevId: 32b10d26dd2da9b53a9248cde36167300dff2d6a
This commit is contained in:
Bas Leijdekkers
2026-01-07 22:46:23 +00:00
committed by intellij-monorepo-bot
parent 1f3d3e9a67
commit 92dc711d19
2 changed files with 55 additions and 6 deletions
@@ -1,4 +1,4 @@
// Copyright 2000-2025 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
// Copyright 2000-2026 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.custom;
import com.intellij.codeInsight.daemon.HighlightDisplayKey;
@@ -34,6 +34,8 @@ import org.jetbrains.annotations.Nullable;
import java.util.List;
import java.util.function.Function;
import static com.intellij.codeInspection.ProblemHighlightType.GENERIC_ERROR_OR_WARNING;
/**
* @author Bas Leijdekkers
*/
@@ -77,7 +79,7 @@ public final class CustomRegExpInspection extends LocalInspectionTool implements
for (RegExpInspectionConfiguration configuration : myConfigurations) {
final String uuid = configuration.getUuid();
final ToolsImpl tools = profile.getToolsOrNull(uuid, project);
if (tools != null && !tools.isEnabled(file)) {
if (tools == null || !tools.isEnabled(file)) {
continue;
}
addInspectionToProfile(project, profile, configuration); // hack
@@ -85,7 +87,7 @@ public final class CustomRegExpInspection extends LocalInspectionTool implements
for (RegExpInspectionConfiguration.InspectionPattern pattern : configuration.getPatterns()) {
FileType fileType = pattern.fileType();
if (UnknownFileType.INSTANCE != fileType && file.getFileType() != fileType) continue;
if (fileType != null && fileType != UnknownFileType.INSTANCE && file.getFileType() != fileType) continue;
final FindModel model = new FindModel();
model.setRegularExpressions(true);
model.setRegExpFlags(pattern.flags);
@@ -108,9 +110,11 @@ public final class CustomRegExpInspection extends LocalInspectionTool implements
final int start = result.getStartOffset() - elementRange.getStartOffset();
final TextRange warningRange = new TextRange(start, result.getEndOffset() - result.getStartOffset() + start);
final String problemDescriptor = StringUtil.defaultIfEmpty(configuration.getProblemDescriptor(), configuration.getName());
final CustomRegExpQuickFix fix = replacement == null ? null : new CustomRegExpQuickFix(findManager, model, text, result);
final LocalQuickFix[] fix = replacement == null
? LocalQuickFix.EMPTY_ARRAY
: new LocalQuickFix[] {new CustomRegExpQuickFix(findManager, model, text, result)};
final ProblemDescriptor descriptor =
manager.createProblemDescriptor(element, warningRange, problemDescriptor, ProblemHighlightType.GENERIC_ERROR_OR_WARNING, isOnTheFly, fix);
manager.createProblemDescriptor(element, warningRange, problemDescriptor, GENERIC_ERROR_OR_WARNING, isOnTheFly, fix);
descriptors.add(new ProblemDescriptorWithReporterName((ProblemDescriptorBase)descriptor, uuid));
result = findManager.findString(text, result.getEndOffset(), model, vFile);
}
@@ -186,7 +190,9 @@ public final class CustomRegExpInspection extends LocalInspectionTool implements
return myConfigurations;
}
public @NotNull InspectionMetaDataDialog createMetaDataDialog(Project project, @NotNull String profileName, @Nullable RegExpInspectionConfiguration configuration) {
public @NotNull InspectionMetaDataDialog createMetaDataDialog(@NotNull Project project,
@NotNull String profileName,
@Nullable RegExpInspectionConfiguration configuration) {
Function<String, @Nullable @NlsContexts.DialogMessage String> nameValidator = name -> {
for (RegExpInspectionConfiguration current : myConfigurations) {
if ((configuration == null || !configuration.getUuid().equals(current.getUuid())) &&
@@ -0,0 +1,43 @@
// Copyright 2000-2026 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.custom;
import com.intellij.codeInspection.ex.InspectionProfileImpl;
import com.intellij.find.FindModel.SearchContext;
import com.intellij.openapi.project.Project;
import com.intellij.profile.codeInspection.InspectionProfileManager;
import com.intellij.testFramework.fixtures.BasePlatformTestCase;
/**
* @author Bas Leijdekkers
*/
public class CustomRegExpInspectionTest extends BasePlatformTestCase {
public void testMultipleCustomInspections() {
myFixture.enableInspections(new CustomRegExpInspection());
Project project = myFixture.getProject();
InspectionProfileImpl profile = InspectionProfileManager.getInstance(project).getCurrentProfile();
CustomRegExpInspection inspection = CustomRegExpInspection.getCustomRegExpInspection(profile);
RegExpInspectionConfiguration one = new RegExpInspectionConfiguration("one");
one.addPattern(new RegExpInspectionConfiguration.InspectionPattern("one", null, 0, SearchContext.ANY, null));
inspection.addConfiguration(one);
CustomRegExpInspection.addInspectionToProfile(project, profile, one);
RegExpInspectionConfiguration two = new RegExpInspectionConfiguration("two");
two.addPattern(new RegExpInspectionConfiguration.InspectionPattern("two", null, 0, SearchContext.ANY, null));
inspection.addConfiguration(two);
// configuration "two" is not yet added to the inspection profile
myFixture.configureByText("dummy.txt", """
<warning descr="one">one</warning>
two
three
""");
myFixture.testHighlighting(true, true, true);
CustomRegExpInspection.addInspectionToProfile(project, profile, two);
myFixture.configureByText("dummy.txt", """
<warning descr="one">one</warning>
<warning descr="two">two</warning>
three
""");
myFixture.testHighlighting(true, true, true);
}
}