Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve behavior of target and targetExclude for gradle plugin #457

Merged
merged 4 commits into from
Sep 24, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 3 additions & 2 deletions plugin-gradle/CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,14 @@
* Fixes [#410](https://github.com/diffplug/spotless/issues/410) AccessDeniedException in MinGW/GitBash.
* Also fixes occasional [hang on NFS due to filesystem timers](https://github.com/diffplug/spotless/pull/407#issuecomment-514824364).
* Eclipse-based formatters used to leave temporary files around ([#447](https://github.com/diffplug/spotless/issues/447)). This is now fixed, but only for eclipse 4.12+, no back-port to older Eclipse formatter versions is planned. ([#451](https://github.com/diffplug/spotless/issues/451))
* Fixed a bad but simple bug in `paddedCell()` (https://github.com/diffplug/spotless/pull/455)
* Fixed a bad but simple bug in `paddedCell()` ([#455](https://github.com/diffplug/spotless/pull/455))
- if a formatter was behaving correctly on a given file (was idempotent)
- but the file was not properly formatted
- `spotlessCheck` would improperly say "all good" even though `spotlessApply` would properly change them
- combined with up-to-date checking, could lead to even more confusing results,
(https://github.com/diffplug/spotless/issues/338)
([#338](https://github.com/diffplug/spotless/issues/338))
- Fixed now!
* When you specify `targetExclude()`, spotless no longer silently removes `build` directories from the exclusion ([#457](https://github.com/diffplug/spotless/pull/457)).

### Version 3.24.2 - August 19th 2019 ([javadoc](https://diffplug.github.io/spotless/javadoc/spotless-plugin-gradle/3.24.1/), [jcenter](https://bintray.com/diffplug/opensource/spotless-plugin-gradle/3.24.1))

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
import org.gradle.api.GradleException;
import org.gradle.api.Project;
import org.gradle.api.file.FileCollection;
import org.gradle.api.tasks.util.PatternFilterable;

import com.diffplug.spotless.FormatExceptionPolicyStrict;
import com.diffplug.spotless.FormatterFunc;
Expand Down Expand Up @@ -134,9 +135,12 @@ public void encoding(String charset) {
* Strings are treated as the 'include' arg to fileTree, with project.rootDir as the dir.
* List<String> are treated as the 'includes' arg to fileTree, with project.rootDir as the dir.
* Anything else gets passed to getProject().files().
*
* If you pass any strings that start with "**\/*", this method will automatically filter out
* "build", ".gradle", and ".git" folders.
*/
public void target(Object... targets) {
this.target = parseTargets(targets);
this.target = parseTargetsIsExclude(targets, false);
}

/**
Expand All @@ -150,22 +154,22 @@ public void target(Object... targets) {
* Anything else gets passed to getProject().files().
*/
public void targetExclude(Object... targets) {
this.targetExclude = parseTargets(targets);
this.targetExclude = parseTargetsIsExclude(targets, true);
}

private FileCollection parseTargets(Object[] targets) {
private FileCollection parseTargetsIsExclude(Object[] targets, boolean isExclude) {
requireElementsNonNull(targets);
if (targets.length == 0) {
return getProject().files();
} else if (targets.length == 1) {
return parseTarget(targets[0]);
return parseTargetIsExclude(targets[0], isExclude);
} else {
if (Stream.of(targets).allMatch(o -> o instanceof String)) {
return parseTarget(Arrays.asList(targets));
return parseTargetIsExclude(Arrays.asList(targets), isExclude);
} else {
FileCollection union = getProject().files();
for (Object target : targets) {
union = union.plus(parseTarget(target));
union = union.plus(parseTargetIsExclude(target, isExclude));
}
return union;
}
Expand All @@ -178,33 +182,52 @@ private FileCollection parseTargets(Object[] targets) {
* List<String> are treated as the 'includes' arg to fileTree, with project.rootDir as the dir.
* Anything else gets passed to getProject().files().
*/
@SuppressWarnings("unchecked")
protected FileCollection parseTarget(Object target) {
protected final FileCollection parseTarget(Object target) {
return parseTargetIsExclude(target, false);
}

private final FileCollection parseTargetIsExclude(Object target, boolean isExclude) {
if (target instanceof FileCollection) {
return (FileCollection) target;
} else if (target instanceof String ||
(target instanceof List && ((List<?>) target).stream().allMatch(o -> o instanceof String))) {
// since people are likely to do '**/*.md', we want to make sure to exclude folders
// they don't want to format which will slow down the operation greatly
File dir = getProject().getProjectDir();
List<String> excludes = new ArrayList<>();
// no git
excludes.add(".git");
// no .gradle
if (getProject() == getProject().getRootProject()) {
excludes.add(".gradle");
}
// no build folders (flatInclude means that subproject might not be subfolders, see https://github.com/diffplug/spotless/issues/121)
relativizeIfSubdir(excludes, dir, getProject().getBuildDir());
for (Project subproject : getProject().getSubprojects()) {
relativizeIfSubdir(excludes, dir, subproject.getBuildDir());
}
PatternFilterable userExact; // exactly the collection that the user specified
if (target instanceof String) {
return (FileCollection) getProject().fileTree(dir).include((String) target).exclude(excludes);
userExact = getProject().fileTree(dir).include((String) target);
} else {
// target can only be a List<String> at this point
return (FileCollection) getProject().fileTree(dir).include((List<String>) target).exclude(excludes);
@SuppressWarnings("unchecked")
List<String> targetList = (List<String>) target;
userExact = getProject().fileTree(dir).include(targetList);
}
boolean filterOutGitAndGradle;
// since people are likely to do '**/*.md', we want to make sure to exclude folders
// they don't want to format which will slow down the operation greatly
// but we only want to do that if they are *including* - if they are specifying
// what they want to exclude, we shouldn't filter at all
if (target instanceof String && !isExclude) {
String str = (String) target;
filterOutGitAndGradle = str.startsWith("**/*") || str.startsWith("**\\*");
} else {
filterOutGitAndGradle = false;
}
if (filterOutGitAndGradle) {
List<String> excludes = new ArrayList<>();
// no git
excludes.add(".git");
// no .gradle
if (getProject() == getProject().getRootProject()) {
excludes.add(".gradle");
}
// no build folders (flatInclude means that subproject might not be subfolders, see https://github.com/diffplug/spotless/issues/121)
relativizeIfSubdir(excludes, dir, getProject().getBuildDir());
for (Project subproject : getProject().getSubprojects()) {
relativizeIfSubdir(excludes, dir, subproject.getBuildDir());
}
userExact = userExact.exclude(excludes);
}
return (FileCollection) userExact;
} else {
return getProject().files(target);
}
Expand Down