diff --git a/src/functionalTest/groovy/com/autonomousapps/jvm/JavaToolchainSpec.groovy b/src/functionalTest/groovy/com/autonomousapps/jvm/JavaToolchainSpec.groovy new file mode 100644 index 000000000..fe67fa6f5 --- /dev/null +++ b/src/functionalTest/groovy/com/autonomousapps/jvm/JavaToolchainSpec.groovy @@ -0,0 +1,41 @@ +package com.autonomousapps.jvm + +import com.autonomousapps.jvm.projects.JavaToolchainProject + +import static com.autonomousapps.utils.Runner.build +import static com.google.common.truth.Truth.assertThat + +final class JavaToolchainSpec extends AbstractJvmSpec { + + def "does not fail with Java #javaToolchainVersion toolchain (#gradleVersion)"() { + given: "a Gradle project using Java toolchain version #javaToolchainVersion that has been built" + def project = new JavaToolchainProject(javaToolchainVersion) + gradleProject = project.gradleProject + build(gradleVersion, gradleProject.rootDir, 'build') + + when: 'running buildHealth' + def result = build(gradleVersion, gradleProject.rootDir, 'buildHealth') + + then: 'abiAnalysisMain and explodeByteCodeSourceMain tasks were ran' + // These two are the ones that were actually failing, sanity check that java library plugin is applied + assert result.tasks.any { (it.getPath() == ':proj:abiAnalysisMain') } + assert result.tasks.any { (it.getPath() == ':proj:explodeByteCodeSourceMain') } + + and: 'the report should be empty' + assertThat(project.actualBuildHealth()).containsExactlyElementsIn(project.expectedBuildHealth) + + where: + // Comment out all but the last for speed + // See https://docs.gradle.org/8.5/userguide/compatibility.html#java + gradleVersion | javaToolchainVersion +// GRADLE_7_5 | 18 +// GRADLE_7_5 | 19 +// GRADLE_7_6 | 18 + GRADLE_7_6 | 19 + // TODO(tsr): some errors running these two scenarios +// GRADLE_8_3 | 20 +// GRADLE_8_5 | 21 + + classFileMajorVersion = javaToolchainVersion + 44 // 19 + 44 = 63, is this safe? + } +} diff --git a/src/functionalTest/groovy/com/autonomousapps/jvm/projects/JavaToolchainProject.groovy b/src/functionalTest/groovy/com/autonomousapps/jvm/projects/JavaToolchainProject.groovy new file mode 100644 index 000000000..81087a1a9 --- /dev/null +++ b/src/functionalTest/groovy/com/autonomousapps/jvm/projects/JavaToolchainProject.groovy @@ -0,0 +1,84 @@ +package com.autonomousapps.jvm.projects + +import com.autonomousapps.AbstractProject +import com.autonomousapps.kit.GradleProject +import com.autonomousapps.kit.Source +import com.autonomousapps.kit.SourceType +import com.autonomousapps.kit.gradle.Plugin +import com.autonomousapps.model.ProjectAdvice + +import static com.autonomousapps.AdviceHelper.actualProjectAdvice +import static com.autonomousapps.AdviceHelper.emptyProjectAdviceFor +import static com.autonomousapps.kit.gradle.Dependency.annotationProcessor +import static com.autonomousapps.kit.gradle.Dependency.implementation + +final class JavaToolchainProject extends AbstractProject { + + final GradleProject gradleProject + + JavaToolchainProject(int javaToolchainVersion) { + this.gradleProject = build(javaToolchainVersion) + } + + private GradleProject build(int javaToolchainVersion) { + return newGradleProjectBuilder() + .withSubproject('proj') { s -> + s.sources = sources + s.withBuildScript { bs -> + bs.plugins(Plugin.javaLibrary) + bs.dependencies( + implementation('org.projectlombok:lombok:1.18.24'), + annotationProcessor('org.projectlombok:lombok:1.18.24'), + ) + bs.withGroovy("java { toolchain { languageVersion.set(JavaLanguageVersion.of(${javaToolchainVersion})) } }") + } + }.write() + } + + private List sources = [ + new Source( + SourceType.JAVA, "Country", "com/example", + """\ + package com.example; + + import lombok.AccessLevel; + import lombok.Getter; + import lombok.NoArgsConstructor; + + @Getter + @NoArgsConstructor(access = AccessLevel.PROTECTED) + public class Country { + private Long id; + private String alpha2; + private String alpha3; + private String name; + private boolean active; + + private Country(final String alpha2, final String alpha3, final String name) { + this.alpha2 = alpha2; + this.alpha3 = alpha3; + this.name = name; + this.active = Boolean.TRUE; + } + + public static Country of(final String alpha2, final String alpha3, final String name) { + return new Country(alpha2, alpha3, name); + } + + public void setActive(boolean active) { + this.active = active; + } + } + """.stripIndent() + ) + ] + + Set actualBuildHealth() { + return actualProjectAdvice(gradleProject) + } + + // In reality we merely hope for unsupported class file major version error + final Set expectedBuildHealth = [ + emptyProjectAdviceFor(':proj'), + ] +}