From 5f47ccc0d657495c4da0c8e0be43193b0d051e7f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?No=C3=A9mie=20B=C3=A9nard?= Date: Thu, 16 Apr 2026 16:10:49 +0200 Subject: [PATCH 1/5] modify S1451 to accept empty headerFormat --- .../src/main/java/checks/FileHeaderCheck/Class4.java | 7 +++++++ .../src/main/java/checks/FileHeaderCheck/Class5.java | 5 +++++ .../java/org/sonar/java/checks/FileHeaderCheck.java | 4 +++- .../org/sonar/java/checks/FileHeaderCheckTest.java | 12 ++++++++++++ 4 files changed, 27 insertions(+), 1 deletion(-) create mode 100644 java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java create mode 100644 java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class5.java diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java new file mode 100644 index 00000000000..c0be3fcf550 --- /dev/null +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java @@ -0,0 +1,7 @@ + +package checks.FileHeaderCheck; + +public class Class4 { +} +// Noncompliant {{Add or update the header of this file.}} + diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class5.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class5.java new file mode 100644 index 00000000000..33df8514723 --- /dev/null +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class5.java @@ -0,0 +1,5 @@ +package checks.FileHeaderCheck; + +public class Class5 { +} +// Compliant diff --git a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java index a9bd6d7ec8b..18243cbc2bd 100644 --- a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java +++ b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java @@ -67,7 +67,9 @@ public void setContext(JavaFileScannerContext context) { } } } else { - expectedLines = headerFormat.split("(?:\r)?\n|\r"); + if (headerFormat.isEmpty()) { + expectedLines = new String[]{}; + } else {expectedLines = headerFormat.split("(?:\r)?\n|\r");} } visitFile(); } diff --git a/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java b/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java index 33036f91e98..f23022f312d 100644 --- a/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java +++ b/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java @@ -98,6 +98,18 @@ void test() { .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Class3.java")) .withCheck(check) .verifyNoIssues(); + + check = new FileHeaderCheck(); + CheckVerifier.newVerifier() + .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Class4.java")) + .withCheck(check) + .verifyNoIssues(); + + check = new FileHeaderCheck(); + CheckVerifier.newVerifier() + .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Class5.java")) + .withCheck(check) + .verifyNoIssues(); } @Test From 5c9bbebfec3fdf8fefc1f14e18ab7a7b56190e72 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?No=C3=A9mie=20B=C3=A9nard?= Date: Fri, 17 Apr 2026 08:51:00 +0200 Subject: [PATCH 2/5] fix incorrect test --- .../default/src/main/java/checks/FileHeaderCheck/Class4.java | 2 +- .../default/src/main/java/checks/FileHeaderCheck/Regex5.java | 4 ++++ .../default/src/main/java/checks/FileHeaderCheck/Regex6.java | 4 ++++ 3 files changed, 9 insertions(+), 1 deletion(-) create mode 100644 java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java create mode 100644 java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java index c0be3fcf550..ccc88d466cc 100644 --- a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Class4.java @@ -3,5 +3,5 @@ public class Class4 { } -// Noncompliant {{Add or update the header of this file.}} +// Compliant diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java new file mode 100644 index 00000000000..ef1f89c8c91 --- /dev/null +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java @@ -0,0 +1,4 @@ +package checks.FileHeaderCheck; + +public class Regex5 { +} diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java new file mode 100644 index 00000000000..4b65833236f --- /dev/null +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java @@ -0,0 +1,4 @@ +package checks.FileHeaderCheck; + +public class Regex6 { +} From c0f685877588dda346e8bbec1b2e57cc193f3462 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?No=C3=A9mie=20B=C3=A9nard?= Date: Fri, 17 Apr 2026 08:51:53 +0200 Subject: [PATCH 3/5] add tests for regex --- .../default/src/main/java/checks/FileHeaderCheck/Regex5.java | 2 ++ .../default/src/main/java/checks/FileHeaderCheck/Regex6.java | 1 + 2 files changed, 3 insertions(+) diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java index ef1f89c8c91..470b095a858 100644 --- a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex5.java @@ -1,4 +1,6 @@ + package checks.FileHeaderCheck; public class Regex5 { } +// Compliant diff --git a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java index 4b65833236f..e61c9a45031 100644 --- a/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java +++ b/java-checks-test-sources/default/src/main/java/checks/FileHeaderCheck/Regex6.java @@ -2,3 +2,4 @@ public class Regex6 { } +// Compliant From 0874843fc8b17154bb871d80fdd94ae3cbca9d86 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?No=C3=A9mie=20B=C3=A9nard?= Date: Fri, 17 Apr 2026 08:53:09 +0200 Subject: [PATCH 4/5] modify check so that it accepts an empty header in both cases (regex or not) --- .../sonar/java/checks/FileHeaderCheck.java | 25 +++++++++++-------- .../java/checks/FileHeaderCheckTest.java | 14 +++++++++++ 2 files changed, 28 insertions(+), 11 deletions(-) diff --git a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java index 18243cbc2bd..f85434a3009 100644 --- a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java +++ b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java @@ -16,6 +16,7 @@ */ package org.sonar.java.checks; +import java.util.Arrays; import org.sonar.check.Rule; import org.sonar.check.RuleProperty; import org.sonar.plugins.java.api.IssuableSubscriptionVisitor; @@ -58,18 +59,21 @@ public List nodesToVisit() { @Override public void setContext(JavaFileScannerContext context) { super.context = context; - if (isRegularExpression) { - if (searchPattern == null) { - try { - searchPattern = Pattern.compile(getHeaderFormat(), Pattern.DOTALL); - } catch (IllegalArgumentException e) { - throw new IllegalArgumentException("[" + getClass().getSimpleName() + "] Unable to compile the regular expression: " + headerFormat, e); + if (headerFormat.isEmpty()) { + expectedLines = new String[]{}; + isRegularExpression = false; + } else { + if (isRegularExpression) { + if (searchPattern == null) { + try { + searchPattern = Pattern.compile(getHeaderFormat(), Pattern.DOTALL); + } catch (IllegalArgumentException e) { + throw new IllegalArgumentException("[" + getClass().getSimpleName() + "] Unable to compile the regular expression: " + headerFormat, e); + } } + } else { + expectedLines = headerFormat.split("(?:\r)?\n|\r"); } - } else { - if (headerFormat.isEmpty()) { - expectedLines = new String[]{}; - } else {expectedLines = headerFormat.split("(?:\r)?\n|\r");} } visitFile(); } @@ -116,7 +120,6 @@ private static boolean matches(String[] expectedLines, List lines) { } else { result = false; } - return result; } diff --git a/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java b/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java index f23022f312d..ea34652c6fd 100644 --- a/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java +++ b/java-checks/src/test/java/org/sonar/java/checks/FileHeaderCheckTest.java @@ -151,6 +151,20 @@ void regex() { .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Regex4.java")) .withCheck(check) .verifyIssues(); + + check = new FileHeaderCheck(); + check.isRegularExpression = true; + CheckVerifier.newVerifier() + .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Regex5.java")) + .withCheck(check) + .verifyNoIssues(); + + check = new FileHeaderCheck(); + check.isRegularExpression = true; + CheckVerifier.newVerifier() + .onFile(mainCodeSourcesPath("checks/FileHeaderCheck/Regex6.java")) + .withCheck(check) + .verifyNoIssues(); } @Test From ce696137967d6c49a8f97defa8f4caf0b7939099 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?No=C3=A9mie=20B=C3=A9nard?= Date: Fri, 17 Apr 2026 08:55:35 +0200 Subject: [PATCH 5/5] remove unused import --- .../src/main/java/org/sonar/java/checks/FileHeaderCheck.java | 1 - 1 file changed, 1 deletion(-) diff --git a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java index f85434a3009..49d6062803a 100644 --- a/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java +++ b/java-checks/src/main/java/org/sonar/java/checks/FileHeaderCheck.java @@ -16,7 +16,6 @@ */ package org.sonar.java.checks; -import java.util.Arrays; import org.sonar.check.Rule; import org.sonar.check.RuleProperty; import org.sonar.plugins.java.api.IssuableSubscriptionVisitor;