From 90c2e9dc98cc6f687d528dfef064a7c213ed2219 Mon Sep 17 00:00:00 2001 From: Bartek Pacia Date: Tue, 8 Jul 2025 17:43:48 +0200 Subject: [PATCH] [java-inspections] IDEA-374865 ClassCanBeRecord: fix edge case with calls to super methods Now quick-fix is not shown when, in the class constructor, a method from superclass/superinterface is called before the class is ready for that. Basically, respect javac behavior. In response to IJ-CR-167896 GitOrigin-RevId: 421fc995c478ec20e39292ed02a32cb249b6398b --- .../ConstructorBodyProcessor.java | 13 ++++++++---- .../beforeDelegating_8.java | 21 +++++++++++++++++++ 2 files changed, 30 insertions(+), 4 deletions(-) create mode 100644 java/java-tests/testData/inspection/classCanBeRecord/flexibleConstructorBodies/beforeDelegating_8.java diff --git a/java/java-impl-inspections/src/com/intellij/codeInspection/classCanBeRecord/ConstructorBodyProcessor.java b/java/java-impl-inspections/src/com/intellij/codeInspection/classCanBeRecord/ConstructorBodyProcessor.java index 6a9bdfffe360..c55f021effae 100644 --- a/java/java-impl-inspections/src/com/intellij/codeInspection/classCanBeRecord/ConstructorBodyProcessor.java +++ b/java/java-impl-inspections/src/com/intellij/codeInspection/classCanBeRecord/ConstructorBodyProcessor.java @@ -265,10 +265,15 @@ final class ConstructorBodyProcessor { if (resolved instanceof PsiField field && !field.hasModifierProperty(STATIC) && field.getContainingClass() == containingClass) { hasReferenceToClassUnderConstruction.set(true); } - else if (resolved instanceof PsiMethod method && - !method.hasModifierProperty(STATIC) && - method.getContainingClass() == containingClass) { - hasReferenceToClassUnderConstruction.set(true); + else if (resolved instanceof PsiMethod method) { + if (method.hasModifierProperty(STATIC)) return; + if (method.getContainingClass() == containingClass) { + hasReferenceToClassUnderConstruction.set(true); + return; + } + if (containingClass.findMethodBySignature(method, true) != null) { + hasReferenceToClassUnderConstruction.set(true); + } } } }); diff --git a/java/java-tests/testData/inspection/classCanBeRecord/flexibleConstructorBodies/beforeDelegating_8.java b/java/java-tests/testData/inspection/classCanBeRecord/flexibleConstructorBodies/beforeDelegating_8.java new file mode 100644 index 000000000000..8d4e0c7aa190 --- /dev/null +++ b/java/java-tests/testData/inspection/classCanBeRecord/flexibleConstructorBodies/beforeDelegating_8.java @@ -0,0 +1,21 @@ +// "Convert to record class" "false" +interface LivingAndBreathing { + default void performBackflip() { + System.out.println("Watch out, I'm gonna do a backflip"); + } +} + +class Person implements LivingAndBreathing { + final String name; + final int age; + + Person(String name, int age) { + this.name = name; + this.age = age; + } + + Person(String name) { + performBackflip(); // javac error: "cannot reference performBackflip() before supertype constructor has been called" + this(name, 0); + } +} \ No newline at end of file