I’m trying to make a plugin, which include other three plugin java
, scala
, kotlin-jvm
. And I hope that users can configure it in the build.gradle.kts
, to determine whether to enable scala
or kotlin-jvm
. Here is my code.
public class JvmAIOPlugin implements Plugin<Project> {
@Override
public void apply(Project project) {
JvmParameters parameters = project.getExtensions().create("jvmAio", JvmParameters.class);
if (parameters.getJavaVersion().isPresent()) {
configureJava(project, parameters);
}
if (parameters.getKotlinVersion().isPresent() && parameters.getScalaVersion().isPresent()) {
throw new IllegalArgumentException("do not configure kotlin and scala same time");
} else if (parameters.getKotlinVersion().isPresent()) {
configureKotlin(project, parameters);
} else if (parameters.getScalaVersion().isPresent()) {
configureScala(project, parameters);
}
}
private void configureJava(Project project, JvmParameters parameters) {
project.getPluginManager().apply(JavaPlugin.class);
// configure javaCompile and jacoco, test tasks
TaskContainer tasks = project.getTasks();
tasks.withType(JavaCompile.class, javaCompile -> {
JavaVersion javaVersion = parameters.getJavaVersion().get();
javaCompile.setSourceCompatibility(javaVersion.name());
javaCompile.setTargetCompatibility(javaVersion.name());
CompileOptions options = javaCompile.getOptions();
options.setEncoding("UTF-8");
options.setFork(true);
options.setIncremental(true);
ForkOptions forkOptions = options.getForkOptions();
forkOptions.setMemoryMaximumSize("2g");
forkOptions.setJvmArgs(Collections.singletonList("-XX:MaxMetaspaceSize=1g"));
});
tasks.withType(Test.class, test -> {
tasks.withType(JacocoReport.class, test::finalizedBy);
test.useJUnitPlatform();
});
tasks.withType(JacocoReport.class, report -> {
tasks.withType(Test.class, it -> it.dependsOn(report));
JacocoReportsContainer reports = report.getReports();
Path buildDirectory = project.getBuildDir().toPath();
reports.getXml().getOutputLocation().fileValue(buildDirectory.resolve("jacocoXml.xml").toFile());
reports.getHtml().getOutputLocation().fileValue(buildDirectory.resolve("jacocoHtml").toFile());
reports.getCsv().getOutputLocation().fileValue(buildDirectory.resolve("jacocoCsv.csv").toFile());
});
}
private void configureKotlin(Project project, JvmParameters parameters) {
KotlinVersion kotlinVersion = parameters.getKotlinVersion().get();
project.getPluginManager().apply("org.jetbrains.kotlin.jvm");
if (kotlinVersion.isUseJpa()) project.getPluginManager().apply("org.jetbrains.kotlin.plugin.jpa");
if (kotlinVersion.isUseSpring()) project.getPluginManager().apply("org.jetbrains.kotlin.plugin.spring");
// configure kotlin tasks
project.getTasks().withType(KotlinJvmCompile.class, kotlinCompile -> {
KotlinJvmOptions kotlinOptions = kotlinCompile.getKotlinOptions();
JavaVersion javaVersion = parameters.getJavaVersion().get();
kotlinOptions.setJvmTarget(javaVersion.getMajorVersion());
kotlinOptions.setApiVersion(kotlinVersion.majorMinor());
kotlinOptions.setFreeCompilerArgs(Collections.singletonList("-Xjsr305=stric"));
if (kotlinVersion.isUseK2()) kotlinOptions.setLanguageVersion("2.0");
KotlinJvmCompilerOptions options = kotlinOptions.getOptions();
options.getOptIn().add("kotlin.RequiresOptIn");
});
// configure kotlin dependency
String library = "org.jetbrains.kotlin:kotlin-stdlib-jdk8:" + kotlinVersion;
String reflect = "org.jetbrains.kotlin:kotlin-reflect:" + kotlinVersion;
DependencyHandler dependencies = project.getDependencies();
dependencies.add("implementation", library);
dependencies.add("implementation", reflect);
}
private void configureScala(Project project, JvmParameters parameters) {
project.getPluginManager().apply(ScalaPlugin.class);
// configure scala tasks
ScalaVersion scalaVersion = parameters.getScalaVersion().get();
project.getTasks().withType(ScalaCompile.class, scalaCompile -> {
JavaVersion javaVersion = parameters.getJavaVersion().get();
scalaCompile.setSourceCompatibility(javaVersion.name());
scalaCompile.setTargetCompatibility(javaVersion.name());
ScalaCompileOptions options = scalaCompile.getScalaCompileOptions();
options.setEncoding("UTF-8");
ScalaForkOptions forkOptions = options.getForkOptions();
forkOptions.setMemoryMaximumSize("2g");
forkOptions.setJvmArgs(Collections.singletonList("-XX:MaxMetaspaceSize=1g"));
});
// configure scala dependency
String library = "org.scala-lang:scala-library:" + scalaVersion;
String reflect = "org.scala-lang:scala-reflect:" + scalaVersion;
DependencyHandler dependencies = project.getDependencies();
dependencies.add("implementation", library);
if (scalaVersion.getMajor() == 2) dependencies.add("implementation", reflect);
// configure scala source set
if (scalaVersion.isUseScalaOnly()) {
project.getLogger().info(project.getName() + " use scala only, adjusting source set");
SourceSetContainer sourceSets = project.getExtensions().getByType(SourceSetContainer.class);
configureScalaSourceDirs(sourceSets.getByName("main"));
configureScalaSourceDirs(sourceSets.getByName("test"));
}
}
private static void configureScalaSourceDirs(SourceSet main) {
SourceDirectorySet java = main.getJava();
ScalaSourceDirectorySet scala = main.getExtensions().getByType(ScalaSourceDirectorySet.class);
java.getSrcDirs().forEach(scala::srcDir);
java.setSrcDirs(Collections.emptySet());
}
}
And I used this plugin in allprojects
like
jvmAio {
useJava11()
when {
name.endsWith("-kotlin") -> useKotlin {
isUseJpa = true
isUseSpring = true
}
name.endsWith("-scala") -> useScala {
scalaVersion = ScalaVersion.V2_13
isUseScalaOnly = true
}
}
}
tasks {
test {
exclude("**/*IT.*")
}
}
But it says "test" not found
, which implies that the java
plugin never applied.
I copied this code pluginsManagers.apply()
from Gradle
’s ScalaBasePlugin
.
“Maybe I am using another wrong way” I thought