Skip to content

Predeclared dependencies (opt-in feature/restriction) #984

Description

@nedtwigg

We have a strange feature in the Spotless gradle plugin: googleJavaFormat('1.8') The exact chain by which that 1.8 becomes a dependency that gets declared to Gradle is this:

the stacktrace

privateFormatterStepcreateStep() {
returnGoogleJavaFormatStep.create(
groupArtifact,
version,

State(StringstepName, StringgroupArtifact, Stringversion, Stringstyle, Provisionerprovisioner, booleanreflowLongStrings) throwsException {
JVM_SUPPORT.assertFormatterSupported(version);
this.jarState = JarState.from(groupArtifact + ":" + version, provisioner);

privatestaticJarStateprovisionWithTransitives(booleanwithTransitives, Collection<String> mavenCoordinates, Provisionerprovisioner) throwsIOException {
Objects.requireNonNull(mavenCoordinates, "mavenCoordinates");
Objects.requireNonNull(provisioner, "provisioner");
Set<File> jars = provisioner.provisionWithTransitives(withTransitives, mavenCoordinates);

staticProvisionerforProject(Projectproject) {
Objects.requireNonNull(project);
return (withTransitives, mavenCoords) -> {
try {
Configurationconfig = project.getConfigurations().create("spotless"
+ newRequest(withTransitives, mavenCoords).hashCode());
mavenCoords.stream()
.map(project.getDependencies()::create)
.forEach(config.getDependencies()::add);
config.setDescription(mavenCoords.toString());
config.setTransitive(withTransitives);
returnconfig.resolve();

FormatterFunccreateFormat() throwsException {
ClassLoaderclassLoader = jarState.getClassLoader();

* The lifetime of the underlying cacheloader is controlled by {@link SpotlessCache}.
*/
publicClassLoadergetClassLoader() {
returnSpotlessCache.instance().classloader(this);
}

synchronizedClassLoaderclassloader(Serializablekey, JarStatestate) {
SerializedKeyserializedKey = newSerializedKey(key);
returncache
.computeIfAbsent(serializedKey, k -> newFeatureClassLoader(state.jarUrls(), this.getClass().getClassLoader()));

In every Spotless before 6.0, we resolved all formatter dependencies against the buildscript repositories in the root project. That changed in 6.0 because of these two PRs:

If you want the old behavior back, we're happy to take a PR which adds it as a feature like so.

// build.gradle (root project only)spotless {
predeclareDeps()
// predeclareDepsFromBuildscript() to get pre-6.0 behavior
}
spotlessPredeclare {
// now you have to declare every formatter (including version) that you plan to use// you don't need to set the target, that part doesn't matter
java { googleJavaFormat('1.4') }
}
// works/build.gradlespotless {
java { googleJavaFormat('1.4') } // ok
}
// error/build.gradlespotless {
java { googleJavaFormat('1.3') } // throws error at configuration time
}

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions