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

Add Kotlin DSL template #23

Open
wants to merge 12 commits into
base: main
Choose a base branch
from
12 changes: 12 additions & 0 deletions scripts/src/lib/Template.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
let projectName = "Template Mod";
let packageName = "com.example";
let useKotlin = false;
let useKotlinGradle = false;
let dataGeneration = false;
let splitSources = true;

Expand Down Expand Up @@ -122,6 +123,7 @@
projectName,
packageName,
useKotlin,
useKotlinGradle,
dataGeneration: dataGeneration && supportsDataGen,
splitSources: splitSources && supportsSplitSources,
};
Expand Down Expand Up @@ -242,6 +244,16 @@
</p>
</div>

<div>
<div class="option-container">
<input id="kotlinGradle" type="checkbox" class="option-input" bind:checked={useKotlinGradle} />
<label for="kotlinGradle" class="option-label">Gradle Kotlin DSL</label>
</div>
<p class="option-body">
Use the <a href="https://docs.gradle.org/current/userguide/kotlin_dsl.html">Kotlin DSL</a> for the Gradle build script. This option is only reccomended for advanced users familar with Kotlin and Gradle. This may result in slower build peformance and compability issues with some IDEs.
KosmX marked this conversation as resolved.
Show resolved Hide resolved
</p>
</div>

{#if supportsDataGen}
<div>
<div class="option-container">
Expand Down
13 changes: 13 additions & 0 deletions scripts/src/lib/template/gradlekotlin.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import type { ComputedConfiguration, TemplateWriter } from './template';
import { renderTemplate } from './eta';

import gradlePropertiesTemplate from './templates/gradle/groovy/gradle.properties.eta?raw';
import buildGradleTemplate from './templates/gradle/kotlin/build.gradle.kts.eta?raw';
import settingsGradle from './templates/gradle/kotlin/settings.gradle.kts?raw';
import { getJavaVersion } from './java';

export async function addKotlinGradle(writer: TemplateWriter, config: ComputedConfiguration) {
await writer.write('gradle.properties', renderTemplate(gradlePropertiesTemplate, config));
await writer.write('build.gradle.kts', renderTemplate(buildGradleTemplate, {...config, java: getJavaVersion(config.minecraftVersion)}));
await writer.write('settings.gradle.kts', settingsGradle);
}
8 changes: 7 additions & 1 deletion scripts/src/lib/template/template.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { addGradleWrapper } from './gradlewrapper';
import { addGroovyGradle } from './gradlegroovy';
import { addKotlinGradle } from './gradlekotlin';
import { getApiVersionForMinecraft, getKotlinAdapterVersions, getLoaderVersions, getMinecraftYarnVersions } from '../Api';
import { addModJson } from './modjson';
import { addGitFiles } from './git';
Expand All @@ -23,6 +24,7 @@ export interface Configuration {
projectName: string,
packageName: string,
useKotlin: boolean,
useKotlinGradle: boolean,
dataGeneration: boolean,
splitSources: boolean,
}
Expand Down Expand Up @@ -53,7 +55,11 @@ export async function generateTemplate(options: Options) {
const computedConfig = await computeConfig(options.config);

await addGradleWrapper(options);
await addGroovyGradle(options.writer, computedConfig);
if (options.config.useKotlinGradle) {
await addKotlinGradle(options.writer, computedConfig);
} else {
await addGroovyGradle(options.writer, computedConfig);
}
await addModJson(options.writer, computedConfig);
await addGitFiles(options.writer, computedConfig);
}
Expand Down
113 changes: 113 additions & 0 deletions scripts/src/lib/template/templates/gradle/kotlin/build.gradle.kts.eta
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
plugins {
id("fabric-loom") version "1.2-SNAPSHOT"
id("maven-publish")<% if (it.kotlin) { %>
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
id("maven-publish")<% if (it.kotlin) { %>
`maven-publish`<% if (it.kotlin) { %>

The standard Gradle plugins have extension properties that avoid the use of id. See Gradle's own example:

Copy link
Author

@KosmX KosmX Jan 4, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True, but I personally like id("maven-publish") more. There are no ` characters and more consistent.
Maybe vote?

kotlin("jvm") version "<%= it.kotlin.kotlinVersion %>"<% } %>
}

KosmX marked this conversation as resolved.
Show resolved Hide resolved
java.sourceCompatibility = JavaVersion.<%= it.java.compatibility %>
java.targetCompatibility = JavaVersion.<%= it.java.compatibility %>

base.archivesName.set(project.property("archives_base_name") as String)
version = project.property("mod_version") as String
group = project.property("maven_group") as String

repositories {
// Add repositories to retrieve artifacts from in here.
// You should only use this when depending on other mods because
// Loom adds the essential maven repositories to download Minecraft and libraries from automatically.
// See https://docs.gradle.org/current/userguide/declaring_repositories.html
// for more information about repositories.
}
<% if (it.dataGeneration || it.splitSources) { %>
loom {
<% if (it.splitSources) { %> splitEnvironmentSourceSets()

mods {
create("<%= it.modid %>") {
sourceSet(sourceSets["main"])
sourceSet(sourceSets["client"])
}
}
<% } %><% if (it.dataGeneration) { %> runs {
create("datagen") {
inherit(runConfigs["server"])
name("Data Generation")
vmArg("-Dfabric-api.datagen")
vmArg("-Dfabric-api.datagen.output-dir=${file("src/main/generated")}")
vmArg("-Dfabric-api.datagen.modid=<%= it.modid %>")

runDir("build/datagen")
}
}<% } %>
}
<% } %><% if (it.dataGeneration) { %>
sourceSets {
main {
resources {
srcDirs += file("src/main/generated")
}
}
}<% } %>

dependencies {
// To change the versions see the gradle.properties file
minecraft("com.mojang:minecraft:${project.property("minecraft_version")}")
mappings("net.fabricmc:yarn:${project.property("yarn_mappings")}:v2")
modImplementation("net.fabricmc:fabric-loader:${project.property("loader_version")}")

// Fabric API. This is technically optional, but you probably want it anyway.
modImplementation("net.fabricmc.fabric-api:fabric-api:${project.property("fabric_version")}")
<% if (it.kotlin) { %> modImplementation("net.fabricmc:fabric-language-kotlin:${project.property("fabric_kotlin_version")}")<% } %>
// Uncomment the following line to enable the deprecated Fabric API modules.
// These are included in the Fabric API production distribution and allow you to update your mod to the latest modules at a later more convenient time.

// modImplementation("net.fabricmc.fabric-api:fabric-api-deprecated:${project.property("fabric_version")}")
}

<% if (it.kotlin) { %>
kotlin {
jvmToolchain(java.targetCompatibility.majorVersion.toInt())
}
<% } %>
tasks {
processResources {
inputs.property("version", project.version)

filesMatching("fabric.mod.json") {
expand("version" to project.version)
}
}

withType<JavaCompile> {
options.release.set(java.targetCompatibility.majorVersion.toInt())
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't this be <%= it.java.release %> like in the groovy template?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wouldn't create more constants, This PR is about Kotlin DSL, but I think, it should be changed in groovy to reuse the targetCompatibility constant

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IMO the best solution would be to use top-level constants in both Kotlin and Groovy buildscripts (val/def respectively) for these constants.

Since "this PR is about Kotlin DSL", shouldn't it follow the existing pattern?

}
java {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
java {
java {

// Loom will automatically attach sourcesJar to a RemapSourcesJar task and to the "build" task
// if it is present.
// If you remove this line, sources will not be generated.
withSourcesJar()
}

jar {
from("LICENSE") {
rename { "${it}_${base.archivesName.get()}" }
}
}
}

// configure the maven publication
publishing {
publications {
create<MavenPublication>("mavenJava") {
from(components["java"])
}
}

// See https://docs.gradle.org/current/userguide/publishing_maven.html for information on how to set up publishing.
repositories {
// Add repositories to publish to here.
// Notice: This block does NOT have the same function as the block in the top level.
// The repositories here will be used for publishing your artifact, not for
// retrieving dependencies.
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
pluginManagement {
repositories {
maven("https://maven.fabricmc.net/") {
name = "Fabric"
}
mavenCentral()
gradlePluginPortal()
}
}