Skip to content

Commit 809fb4b

Browse files
committed
Make GIT_ATTRIBUTES_FAST_ALLSAME faster.
1 parent 54c0af2 commit 809fb4b

File tree

2 files changed

+47
-44
lines changed

2 files changed

+47
-44
lines changed

lib-extra/src/main/java/com/diffplug/spotless/extra/GitAttributesLineEndings.java

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,41 @@ public final class GitAttributesLineEndings {
6868
// prevent direct instantiation
6969
private GitAttributesLineEndings() {}
7070

71+
/**
72+
* Creates a line-endings policy which matches {@link #create(File, Supplier)},
73+
* which is much faster at the cost that every file under the policy
74+
* is assumed to have the same line endings as the first file.
75+
*/
76+
public static LineEnding.Policy createFastAllSame(File projectDir, Supplier<Iterable<File>> toFormat) {
77+
return new LazyAllTheSame(projectDir, toFormat);
78+
}
79+
80+
static class LazyAllTheSame extends LazyForwardingEquality<String> implements LineEnding.Policy {
81+
transient File projectDir;
82+
transient Supplier<Iterable<File>> toFormat;
83+
84+
public LazyAllTheSame(File projectDir, Supplier<Iterable<File>> toFormat) {
85+
this.projectDir = projectDir;
86+
this.toFormat = toFormat;
87+
}
88+
89+
@Override
90+
protected String calculateState() throws Exception {
91+
var files = toFormat.get().iterator();
92+
if (files.hasNext()) {
93+
Runtime runtime = new RuntimeInit(projectDir).atRuntime();
94+
return runtime.getEndingFor(files.next());
95+
} else {
96+
return LineEnding.UNIX.str();
97+
}
98+
}
99+
100+
@Override
101+
public String getEndingFor(File file) {
102+
return state();
103+
}
104+
}
105+
71106
/**
72107
* Creates a line-endings policy whose serialized state is relativized against projectDir,
73108
* at the cost of eagerly evaluating the line-ending state of every target file when the

lib/src/main/java/com/diffplug/spotless/LineEnding.java

Lines changed: 12 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -59,52 +59,20 @@ public Policy createPolicy() {
5959
public Policy createPolicy(File projectDir, Supplier<Iterable<File>> toFormat) {
6060
Objects.requireNonNull(projectDir, "projectDir");
6161
Objects.requireNonNull(toFormat, "toFormat");
62-
if (this != GIT_ATTRIBUTES && this != GIT_ATTRIBUTES_FAST_ALLSAME) {
63-
return createPolicy();
62+
String gitAttributesMethod;
63+
if (this == GIT_ATTRIBUTES) {
64+
gitAttributesMethod = "create";
65+
} else if (this == GIT_ATTRIBUTES_FAST_ALLSAME) {
66+
gitAttributesMethod = "createFastAllSame";
6467
} else {
65-
if (gitAttributesPolicyCreator == null) {
66-
try {
67-
Class<?> clazz = Class.forName("com.diffplug.spotless.extra.GitAttributesLineEndings");
68-
Method method = clazz.getMethod("create", File.class, Supplier.class);
69-
gitAttributesPolicyCreator = (proj, target) -> ThrowingEx.get(() -> (Policy) method.invoke(null, proj, target));
70-
} catch (ClassNotFoundException | NoSuchMethodException | SecurityException e) {
71-
throw new IllegalStateException("LineEnding.GIT_ATTRIBUTES requires the spotless-lib-extra library, but it is not on the classpath", e);
72-
}
73-
}
74-
// gitAttributesPolicyCreator will always be nonnull at this point
75-
Policy policy = gitAttributesPolicyCreator.apply(projectDir, toFormat);
76-
if (this == GIT_ATTRIBUTES) {
77-
return policy;
78-
} else if (this == GIT_ATTRIBUTES_FAST_ALLSAME) {
79-
return new LazyAllTheSame(policy, toFormat);
80-
} else {
81-
throw new IllegalArgumentException("Unknown " + this);
82-
}
83-
}
84-
}
85-
86-
static class LazyAllTheSame extends LazyForwardingEquality<String> implements Policy {
87-
private transient Policy policy;
88-
private transient Supplier<Iterable<File>> toFormat;
89-
90-
public LazyAllTheSame(Policy policy, Supplier<Iterable<File>> toFormat) {
91-
this.policy = policy;
92-
this.toFormat = toFormat;
93-
}
94-
95-
@Override
96-
protected String calculateState() throws Exception {
97-
var files = toFormat.get().iterator();
98-
if (files.hasNext()) {
99-
return policy.getEndingFor(files.next());
100-
} else {
101-
return LineEnding.UNIX.str();
102-
}
68+
return createPolicy();
10369
}
104-
105-
@Override
106-
public String getEndingFor(File file) {
107-
return state();
70+
try {
71+
Class<?> clazz = Class.forName("com.diffplug.spotless.extra.GitAttributesLineEndings");
72+
Method method = clazz.getMethod(gitAttributesMethod, File.class, Supplier.class);
73+
return ThrowingEx.get(() -> (Policy) method.invoke(null, projectDir, toFormat));
74+
} catch (ClassNotFoundException | NoSuchMethodException | SecurityException e) {
75+
throw new IllegalStateException("LineEnding.GIT_ATTRIBUTES requires the spotless-lib-extra library, but it is not on the classpath", e);
10876
}
10977
}
11078

0 commit comments

Comments
 (0)