Skip to content

Commit 0267bed

Browse files
committed
Merge remote-tracking branch 'origin/main' into feature-maven-expand-wildcard-import
# Conflicts: # plugin-maven/src/main/java/com/diffplug/spotless/maven/AbstractSpotlessMojo.java # plugin-maven/src/main/java/com/diffplug/spotless/maven/FormatterConfig.java
2 parents 4bccda8 + 3b6401d commit 0267bed

22 files changed

Lines changed: 222 additions & 39 deletions

File tree

CHANGES.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,11 +11,15 @@ We adhere to the [keepachangelog](https://keepachangelog.com/en/1.0.0/) format (
1111

1212
## [Unreleased]
1313
### Added
14+
- `scalafmt()` now reads the version from the `version` field in the scalafmt config file when no version is explicitly set in the plugin config, falling back to the built-in default only if neither is available. ([#2922](https://github.com/diffplug/spotless/pull/2922))
1415
- Add `versionCatalog` step for formatting and sorting Gradle version catalog (`.toml`) files. ([#2916](https://github.com/diffplug/spotless/issues/2916))
1516
- Add `javaparserVersion` option to the Cleanthat step, allowing callers to override the JavaParser version pulled in transitively by Cleanthat. ([#2903](https://github.com/diffplug/spotless/pull/2903))
1617
### Fixed
18+
- Preserve case of JDBI named bind params that collide with SQL keywords (e.g. `:limit`, `:offset`) in the DBeaver SQL formatter. ([#2899](https://github.com/diffplug/spotless/pull/2899))
1719
- Fix non-idempotent formatting when `importOrder()` is combined with `greclipse()`: a single catch-all group no longer strips blank lines that `greclipse()` independently inserted between import groups. ([#2914](https://github.com/diffplug/spotless/pull/2914))
1820
### Changes
21+
- Fix `expandWildcardImports` failing on JDK XML types such as `org.xml.sax.InputSource`. ([#2921](https://github.com/diffplug/spotless/pull/2921))
22+
- Use Eclipse JDT's collator-based comparison when sorting Java members to better match Eclipse save actions. ([#2920](https://github.com/diffplug/spotless/pull/2920))
1923
- Bump default `cleanthat` version `2.24` -> `2.25`. ([#2903](https://github.com/diffplug/spotless/pull/2903))
2024
- Bump default `eclipse-jdt` version from `4.35` to `4.39`. ([#2912](https://github.com/diffplug/spotless/pull/2912))
2125

lib-extra/src/jdt/java/com/diffplug/spotless/extra/glue/jdt/DefaultJavaElementComparator.java

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2024-2025 DiffPlug
2+
* Copyright 2024-2026 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -15,6 +15,7 @@
1515
*/
1616
package com.diffplug.spotless.extra.glue.jdt;
1717

18+
import java.text.Collator;
1819
import java.util.Comparator;
1920
import java.util.List;
2021
import java.util.StringTokenizer;
@@ -61,6 +62,7 @@ class DefaultJavaElementComparator implements Comparator<BodyDeclaration> {
6162
private final int[] memberCategoryOffsets;
6263
private final boolean sortByVisibility;
6364
private final int[] visibilityOffsets;
65+
private final Collator collator;
6466

6567
static DefaultJavaElementComparator of(
6668
boolean doNotSortFields,
@@ -95,6 +97,7 @@ static DefaultJavaElementComparator of(
9597
this.memberCategoryOffsets = memberCategoryOffsets;
9698
this.sortByVisibility = sortByVisibility;
9799
this.visibilityOffsets = visibilityOffsets;
100+
this.collator = Collator.getInstance();
98101
}
99102

100103
@SuppressFBWarnings(value = "SF_SWITCH_NO_DEFAULT", justification = "we only accept valid tokens in the order string, otherwise we fall back to default value")
@@ -271,7 +274,7 @@ public int compare(BodyDeclaration bodyDeclaration1, BodyDeclaration bodyDeclara
271274
String name2 = method2.getName().getIdentifier();
272275

273276
// method declarations (constructors) are sorted by name
274-
int cmp = name1.compareTo(name2);
277+
int cmp = collator.compare(name1, name2);
275278
if (cmp != 0) {
276279
return cmp;
277280
}
@@ -286,7 +289,7 @@ public int compare(BodyDeclaration bodyDeclaration1, BodyDeclaration bodyDeclara
286289
for (int i = 0; i < len; i++) {
287290
SingleVariableDeclaration param1 = parameters1.get(i);
288291
SingleVariableDeclaration param2 = parameters2.get(i);
289-
cmp = buildSignature(param1.getType()).compareTo(buildSignature(param2.getType()));
292+
cmp = collator.compare(buildSignature(param1.getType()), buildSignature(param2.getType()));
290293
if (cmp != 0) {
291294
return cmp;
292295
}
@@ -377,7 +380,7 @@ private int preserveRelativeOrder(BodyDeclaration bodyDeclaration1, BodyDeclarat
377380
}
378381

379382
private int compareNames(BodyDeclaration bodyDeclaration1, BodyDeclaration bodyDeclaration2, String name1, String name2) {
380-
int cmp = name1.compareTo(name2);
383+
int cmp = collator.compare(name1, name2);
381384
if (cmp != 0) {
382385
return cmp;
383386
}

lib-extra/src/test/java/com/diffplug/spotless/extra/java/EclipseJdtFormatterStepSpecialCaseTest.java

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,4 +107,12 @@ void sort_members_local_enabled_true() {
107107
StepHarness.forStep(builder.build())
108108
.testResource("java/eclipse/SortExample.localEnabledTrue.test", "java/eclipse/SortExample.localEnabledTrue.clean");
109109
}
110+
111+
@Test
112+
void sort_members_uses_collator() {
113+
EclipseJdtFormatterStep.Builder builder = EclipseJdtFormatterStep.createBuilder(TestProvisioner.mavenCentral(), TestP2Provisioner.defaultProvisioner());
114+
builder.sortMembersEnabled(true);
115+
StepHarness.forStep(builder.build())
116+
.testResource("java/eclipse/SortExample.collator.test", "java/eclipse/SortExample.collator.clean");
117+
}
110118
}

lib/src/javaParser/java/com/diffplug/spotless/glue/javaparser/ExpandWildcardsFormatterFunc.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ public ExpandWildcardsFormatterFunc(Collection<File> typeSolverClasspath) throws
7070
this.parser = new JavaParser();
7171

7272
CombinedTypeSolver combinedTypeSolver = new CombinedTypeSolver();
73-
combinedTypeSolver.add(new ReflectionTypeSolver());
73+
combinedTypeSolver.add(new ReflectionTypeSolver(ReflectionTypeSolver.JCL_ONLY));
7474
for (File element : typeSolverClasspath) {
7575
if (element.isFile()) {
7676
combinedTypeSolver.add(new JarTypeSolver(element));

lib/src/main/java/com/diffplug/spotless/scala/ScalaFmtStep.java

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2016-2025 DiffPlug
2+
* Copyright 2016-2026 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -20,7 +20,9 @@
2020
import java.io.Serial;
2121
import java.io.Serializable;
2222
import java.lang.reflect.Constructor;
23+
import java.nio.file.Files;
2324
import java.util.Collections;
25+
import java.util.Optional;
2426
import java.util.Set;
2527

2628
import javax.annotation.Nullable;
@@ -54,15 +56,16 @@ public static FormatterStep create(Provisioner provisioner) {
5456
return create(defaultVersion(), defaultScalaMajorVersion(), provisioner, null);
5557
}
5658

57-
public static FormatterStep create(String version, Provisioner provisioner, @Nullable File configFile) {
59+
public static FormatterStep create(@Nullable String version, Provisioner provisioner, @Nullable File configFile) {
5860
return create(version, defaultScalaMajorVersion(), provisioner, configFile);
5961
}
6062

61-
public static FormatterStep create(String version, @Nullable String scalaMajorVersion, Provisioner provisioner, @Nullable File configFile) {
63+
public static FormatterStep create(@Nullable String version, @Nullable String scalaMajorVersion, Provisioner provisioner, @Nullable File configFile) {
64+
String finalVersion = version != null ? version : versionFromConfig(configFile).orElse(defaultVersion());
6265
String finalScalaMajorVersion = scalaMajorVersion == null ? DEFAULT_SCALA_MAJOR_VERSION : scalaMajorVersion;
6366

6467
return FormatterStep.create(NAME,
65-
new ScalaFmtStep(JarState.promise(() -> JarState.from(MAVEN_COORDINATE + finalScalaMajorVersion + ":" + version, provisioner)), configFile),
68+
new ScalaFmtStep(JarState.promise(() -> JarState.from(MAVEN_COORDINATE + finalScalaMajorVersion + ":" + finalVersion, provisioner)), configFile),
6669
ScalaFmtStep::equalityState,
6770
State::createFormat);
6871
}
@@ -75,6 +78,22 @@ public static String defaultScalaMajorVersion() {
7578
return DEFAULT_SCALA_MAJOR_VERSION;
7679
}
7780

81+
private static Optional<String> versionFromConfig(@Nullable File configFile) {
82+
try {
83+
return configFile == null || !configFile.exists() ? Optional.empty()
84+
: Files.readAllLines(configFile.toPath())
85+
.stream()
86+
.filter(line -> line.trim().startsWith("version"))
87+
.findFirst()
88+
.flatMap(line -> {
89+
var parts = line.replaceAll("\\s", "").split("=");
90+
return parts.length < 2 ? Optional.empty() : Optional.of(parts[1]);
91+
});
92+
} catch (IOException e) {
93+
return Optional.empty();
94+
}
95+
}
96+
7897
private State equalityState() throws IOException {
7998
return new State(jarState.get(), configFile);
8099
}

lib/src/main/java/com/diffplug/spotless/sql/dbeaver/SQLTokenizedFormatter.java

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2016-2025 DiffPlug
2+
* Copyright 2016-2026 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -95,9 +95,13 @@ private List<FormatterToken> format(final List<FormatterToken> argList) {
9595
}
9696

9797
final KeywordCase keywordCase = formatterCfg.getKeywordCase();
98-
for (FormatterToken anArgList : argList) {
99-
token = anArgList;
98+
for (int index = 0; index < argList.size(); index++) {
99+
token = argList.get(index);
100100
if (token.getType() == TokenType.KEYWORD) {
101+
// Do not transform case for JDBI named bind params (e.g. :limit, :offset)
102+
if (index > 0 && isEmbeddedToken(argList.get(index - 1))) {
103+
continue;
104+
}
101105
token.setString(keywordCase.transform(token.getString()));
102106
}
103107
}
@@ -323,8 +327,10 @@ private List<FormatterToken> format(final List<FormatterToken> argList) {
323327
continue;
324328
}
325329
if (token.getType() == TokenType.SYMBOL && isEmbeddedToken(token)
330+
&& (!":".equals(token.getString()) || prev.getType() == TokenType.SYMBOL)
326331
|| prev.getType() == TokenType.SYMBOL && isEmbeddedToken(prev)) {
327-
// Do not insert spaces around colons
332+
// Do not insert spaces around embedded tokens (colons, dots),
333+
// except before JDBI named bind params (e.g. :limit) preceded by a keyword or name
328334
continue;
329335
}
330336
if (token.getType() == TokenType.SYMBOL && prev.getType() == TokenType.SYMBOL) {

plugin-gradle/CHANGES.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,14 +4,18 @@ We adhere to the [keepachangelog](https://keepachangelog.com/en/1.0.0/) format (
44

55
## [Unreleased]
66
### Added
7+
- `scalafmt()` now reads the version from the `version` field in the scalafmt config file when no version is explicitly set in the plugin config, falling back to the built-in default only if neither is available. ([#2922](https://github.com/diffplug/spotless/pull/2922))
78
- Add `toml` format type with `versionCatalog()` step for formatting and sorting Gradle version catalog files. ([#2916](https://github.com/diffplug/spotless/issues/2916))
89
- Add `withIndentStyle` and `withIndentSize` configuration to `tableTestFormatter` for setting the fallback indent when no `.editorconfig` is found. ([#2893](https://github.com/diffplug/spotless/pull/2893))
910
- Add `javaparserVersion(...)` to `cleanthat`, allowing users to override the JavaParser version pulled in transitively by Cleanthat. ([#2903](https://github.com/diffplug/spotless/pull/2903))
1011
### Fixed
1112
- Fix `tableTestFormatter` editorconfig cache not honoring `.editorconfig` changes across Gradle daemon runs due to a shared static `EditorConfigProvider`. ([#2893](https://github.com/diffplug/spotless/pull/2893))
13+
- Preserve case of JDBI named bind params that collide with SQL keywords (e.g. `:limit`, `:offset`) in the DBeaver SQL formatter. ([#2899](https://github.com/diffplug/spotless/pull/2899))
1214
- Fix non-idempotent formatting when `importOrder()` is combined with `greclipse()`: a single catch-all group no longer strips blank lines that `greclipse()` independently inserted between import groups. ([#2914](https://github.com/diffplug/spotless/pull/2914))
1315
- Fix `predeclareDepsFromBuildscript()` on Gradle 9 by avoiding mutation of the root buildscript configuration container. ([#2929](https://github.com/diffplug/spotless/pull/2929), fixes [#2599](https://github.com/diffplug/spotless/issues/2599))
1416
### Changes
17+
- Fix `expandWildcardImports` failing on JDK XML types such as `org.xml.sax.InputSource`. ([#2921](https://github.com/diffplug/spotless/pull/2921))
18+
- Use Eclipse JDT's collator-based comparison when sorting Java members to better match Eclipse save actions. ([#2920](https://github.com/diffplug/spotless/pull/2920))
1519
- Bump default `cleanthat` version `2.24` -> `2.25`. ([#2903](https://github.com/diffplug/spotless/pull/2903))
1620
- Bump default `eclipse-jdt` version from `4.35` to `4.39`. ([#2912](https://github.com/diffplug/spotless/pull/2912))
1721
- Make `spotlessPredeclare` visible to Gradle Kotlin DSL type-safe accessors. ([#2925](https://github.com/diffplug/spotless/pull/2925))

plugin-gradle/src/main/java/com/diffplug/gradle/spotless/ScalaExtension.java

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2016-2023 DiffPlug
2+
* Copyright 2016-2026 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -35,22 +35,20 @@ public ScalaExtension(SpotlessExtension spotless) {
3535
}
3636

3737
public ScalaFmtConfig scalafmt() {
38-
return scalafmt(ScalaFmtStep.defaultVersion());
38+
return new ScalaFmtConfig(null);
3939
}
4040

4141
public ScalaFmtConfig scalafmt(String version) {
42-
return new ScalaFmtConfig(version);
42+
return new ScalaFmtConfig(Objects.requireNonNull(version));
4343
}
4444

4545
public class ScalaFmtConfig {
46-
final String version;
47-
@Nullable
48-
String scalaMajorVersion;
49-
@Nullable
50-
Object configFile;
46+
@Nullable final String version;
47+
@Nullable String scalaMajorVersion;
48+
@Nullable Object configFile;
5149

52-
ScalaFmtConfig(String version) {
53-
this.version = Objects.requireNonNull(version);
50+
ScalaFmtConfig(@Nullable String version) {
51+
this.version = version;
5452
addStep(createStep());
5553
}
5654

plugin-gradle/src/test/java/com/diffplug/gradle/spotless/ScalaExtensionTest.java

Lines changed: 20 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2016-2021 DiffPlug
2+
* Copyright 2016-2026 DiffPlug
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -20,6 +20,25 @@
2020
import org.junit.jupiter.api.Test;
2121

2222
class ScalaExtensionTest extends GradleIntegrationHarness {
23+
@Test
24+
void versionFromConfig() throws IOException {
25+
setFile("build.gradle").toLines(
26+
"plugins {",
27+
" id 'com.diffplug.spotless'",
28+
"}",
29+
"repositories { mavenCentral() }",
30+
"apply plugin: 'scala'",
31+
"spotless {",
32+
" scala {",
33+
" scalafmt().configFile('scalafmt.conf')",
34+
" }",
35+
"}");
36+
setFile("scalafmt.conf").toResource("scala/scalafmt/scalafmt_newer.conf");
37+
setFile("src/main/scala/basic.scala").toResource("scala/scalafmt/basic.dirty");
38+
gradleRunner().withArguments("spotlessApply").build();
39+
assertFile("src/main/scala/basic.scala").sameAsResource("scala/scalafmt/basic.cleanWithCustomConf_3.0.0");
40+
}
41+
2342
@Test
2443
void integration() throws IOException {
2544
setFile("build.gradle").toLines(

plugin-maven/CHANGES.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,17 @@ We adhere to the [keepachangelog](https://keepachangelog.com/en/1.0.0/) format (
44

55
## [Unreleased]
66
### Added
7+
- `<scalafmt>` now reads the version from the `version` field in the scalafmt config file when no `<version>` is explicitly set, falling back to the built-in default only if neither is available. ([#2922](https://github.com/diffplug/spotless/pull/2922))
78
- Add `<toml>` format type with `<versionCatalog>` step for formatting and sorting Gradle version catalog files. ([#2916](https://github.com/diffplug/spotless/issues/2916))
89
- Add `<javaparserVersion>` option to `<cleanthat>`, allowing users to override the JavaParser version pulled in transitively by Cleanthat. ([#2903](https://github.com/diffplug/spotless/pull/2903))
910
- Add a `expandWildcardImports` API for java ([#2829](https://github.com/diffplug/spotless/pull/2930))
1011
### Fixed
12+
- Preserve case of JDBI named bind params that collide with SQL keywords (e.g. `:limit`, `:offset`) in the DBeaver SQL formatter. ([#2899](https://github.com/diffplug/spotless/pull/2899))
13+
- The `-Dspotless.ratchetFrom=...` user property now takes priority over `<ratchetFrom>` configured in the plugin or in individual formatters, instead of being overridden by them. ([#2896](https://github.com/diffplug/spotless/pull/2896), fixes [#2842](https://github.com/diffplug/spotless/issues/2842))
1114
- Fix non-idempotent formatting when `importOrder()` is combined with `greclipse()`: a single catch-all group no longer strips blank lines that `greclipse()` independently inserted between import groups. ([#2914](https://github.com/diffplug/spotless/pull/2914))
1215
### Changes
16+
- Fix `expandWildcardImports` failing on JDK XML types such as `org.xml.sax.InputSource`. ([#2921](https://github.com/diffplug/spotless/pull/2921))
17+
- Use Eclipse JDT's collator-based comparison when sorting Java members to better match Eclipse save actions. ([#2920](https://github.com/diffplug/spotless/pull/2920))
1318
- Bump default `cleanthat` version `2.24` -> `2.25`. ([#2903](https://github.com/diffplug/spotless/pull/2903))
1419
- Bump default `eclipse-jdt` version from `4.35` to `4.39`. ([#2912](https://github.com/diffplug/spotless/pull/2912))
1520

0 commit comments

Comments
 (0)