2023-03-15 21:52:13 +00:00
|
|
|
// SPDX-FileCopyrightText: 2022 The CC: Tweaked Developers
|
|
|
|
//
|
|
|
|
// SPDX-License-Identifier: MPL-2.0
|
|
|
|
|
2022-11-09 23:58:56 +00:00
|
|
|
import cc.tweaked.gradle.*
|
|
|
|
import net.minecraftforge.gradle.common.util.RunConfig
|
|
|
|
|
|
|
|
plugins {
|
|
|
|
id("cc-tweaked.forge")
|
|
|
|
id("cc-tweaked.gametest")
|
2023-03-15 23:20:07 +00:00
|
|
|
id("cc-tweaked.mod-publishing")
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
val modVersion: String by extra
|
|
|
|
|
|
|
|
val allProjects = listOf(":core-api", ":core", ":forge-api").map { evaluationDependsOn(it) }
|
|
|
|
cct {
|
|
|
|
inlineProject(":common")
|
|
|
|
allProjects.forEach { externalSources(it) }
|
|
|
|
}
|
|
|
|
|
|
|
|
sourceSets {
|
|
|
|
main {
|
|
|
|
resources.srcDir("src/generated/resources")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
minecraft {
|
|
|
|
runs {
|
|
|
|
// configureEach would be better, but we need to eagerly configure configs or otherwise the run task doesn't
|
|
|
|
// get set up properly.
|
|
|
|
all {
|
|
|
|
property("forge.logging.markers", "REGISTRIES")
|
|
|
|
property("forge.logging.console.level", "debug")
|
|
|
|
|
|
|
|
mods.register("computercraft") {
|
|
|
|
cct.sourceDirectories.get().forEach {
|
|
|
|
if (it.classes) sources(it.sourceSet)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
val client by registering {
|
|
|
|
workingDirectory(file("run"))
|
|
|
|
}
|
|
|
|
|
|
|
|
val server by registering {
|
|
|
|
workingDirectory(file("run/server"))
|
|
|
|
arg("--nogui")
|
|
|
|
}
|
|
|
|
|
|
|
|
val data by registering {
|
|
|
|
workingDirectory(file("run"))
|
|
|
|
args(
|
|
|
|
"--mod", "computercraft", "--all",
|
|
|
|
"--output", file("src/generated/resources/"),
|
|
|
|
"--existing", project(":common").file("src/main/resources/"),
|
|
|
|
"--existing", file("src/main/resources/"),
|
|
|
|
)
|
|
|
|
}
|
|
|
|
|
|
|
|
fun RunConfig.configureForGameTest() {
|
2022-11-17 09:26:57 +00:00
|
|
|
val old = lazyTokens["minecraft_classpath"]
|
2022-11-09 23:58:56 +00:00
|
|
|
lazyToken("minecraft_classpath") {
|
2024-01-31 19:47:03 +00:00
|
|
|
// Add all files in testMinecraftLibrary to the classpath.
|
|
|
|
val allFiles = mutableSetOf<String>()
|
2022-11-17 09:26:57 +00:00
|
|
|
|
|
|
|
val oldVal = old?.get()
|
2024-01-31 19:47:03 +00:00
|
|
|
if (!oldVal.isNullOrEmpty()) allFiles.addAll(oldVal.split(File.pathSeparatorChar))
|
|
|
|
|
|
|
|
for (file in configurations["testMinecraftLibrary"].resolve()) allFiles.add(file.absolutePath)
|
|
|
|
|
|
|
|
allFiles.joinToString(File.pathSeparator)
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
property("cctest.sources", project(":common").file("src/testMod/resources/data/cctest").absolutePath)
|
|
|
|
|
|
|
|
arg("--mixin.config=computercraft-gametest.mixins.json")
|
|
|
|
|
|
|
|
mods.register("cctest") {
|
|
|
|
source(sourceSets["testMod"])
|
|
|
|
source(sourceSets["testFixtures"])
|
2024-01-31 19:47:03 +00:00
|
|
|
source(project(":core").sourceSets["testFixtures"])
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
val testClient by registering {
|
|
|
|
workingDirectory(file("run/testClient"))
|
|
|
|
parent(client.get())
|
|
|
|
configureForGameTest()
|
2022-11-18 23:57:25 +00:00
|
|
|
|
|
|
|
property("cctest.tags", "client,common")
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
val gameTestServer by registering {
|
|
|
|
workingDirectory(file("run/testServer"))
|
|
|
|
configureForGameTest()
|
|
|
|
|
|
|
|
property("forge.logging.console.level", "info")
|
Ensure the terminal exists when creating a monitor peripheral
Previously we had the invariant that if we had a server monitor, we also
had a terminal. When a monitor shrank into a place, we deleted the
monitor, and then recreated it when a peripheral was requested.
As of ab785a090698e6972caac95691393428c6f8370b this has changed
slightly, and we now just delete the terminal (keeping the ServerMonitor
around). However, we didn't adjust the peripheral code accordingly,
meaning we didn't recreate the /terminal/ when a peripheral was
requested.
The fix for this is very simple - most of the rest of this commit is
some additional code for ensuring monitor invariants hold, so we can
write tests with a little more confidence.
I'm not 100% sold on this approach. It's tricky having a double layer of
nullable state (ServerMonitor, and then the terminal). However, I think
this is reasonable - the ServerMonitor is a reference to the multiblock,
and the Terminal is part of the multiblock's state.
Even after all the refactors, monitor code is still nastier than I'd
like :/.
Fixes #1608
2023-10-09 21:03:43 +00:00
|
|
|
jvmArg("-ea")
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
configurations {
|
2023-03-29 21:58:45 +00:00
|
|
|
minecraftLibrary { extendsFrom(minecraftEmbed.get()) }
|
2024-01-31 19:47:03 +00:00
|
|
|
|
|
|
|
val testMinecraftLibrary by registering {
|
|
|
|
isCanBeResolved = true
|
|
|
|
isCanBeConsumed = false
|
|
|
|
// Prevent ending up with multiple versions of libraries on the classpath.
|
|
|
|
shouldResolveConsistentlyWith(minecraftLibrary.get())
|
|
|
|
}
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
dependencies {
|
|
|
|
compileOnly(libs.jetbrainsAnnotations)
|
|
|
|
annotationProcessorEverywhere(libs.autoService)
|
|
|
|
|
2023-07-10 19:31:06 +00:00
|
|
|
clientCompileOnly(variantOf(libs.emi) { classifier("api") })
|
2022-11-09 23:58:56 +00:00
|
|
|
libs.bundles.externalMods.forge.compile.get().map { compileOnly(fg.deobf(it)) }
|
|
|
|
libs.bundles.externalMods.forge.runtime.get().map { runtimeOnly(fg.deobf(it)) }
|
|
|
|
|
2023-03-29 08:30:29 +00:00
|
|
|
// Depend on our other projects.
|
2023-12-16 22:35:11 +00:00
|
|
|
api(commonClasses(project(":forge-api"))) { cct.exclude(this) }
|
|
|
|
clientApi(clientClasses(project(":forge-api"))) { cct.exclude(this) }
|
|
|
|
implementation(project(":core")) { cct.exclude(this) }
|
2022-11-17 09:26:57 +00:00
|
|
|
|
2023-03-29 08:30:29 +00:00
|
|
|
minecraftEmbed(libs.cobalt) {
|
2023-12-19 18:12:21 +00:00
|
|
|
val version = libs.versions.cobalt.get()
|
|
|
|
jarJar.ranged(this, "[$version,${getNextVersion(version)})")
|
2023-03-29 08:30:29 +00:00
|
|
|
}
|
|
|
|
minecraftEmbed(libs.jzlib) {
|
|
|
|
jarJar.ranged(this, "[${libs.versions.jzlib.get()},)")
|
|
|
|
}
|
|
|
|
minecraftEmbed(libs.netty.http) {
|
|
|
|
jarJar.ranged(this, "[${libs.versions.netty.get()},)")
|
|
|
|
isTransitive = false
|
|
|
|
}
|
2023-06-06 18:58:24 +00:00
|
|
|
minecraftEmbed(libs.netty.socks) {
|
|
|
|
jarJar.ranged(this, "[${libs.versions.netty.get()},)")
|
|
|
|
isTransitive = false
|
|
|
|
}
|
|
|
|
minecraftEmbed(libs.netty.proxy) {
|
|
|
|
jarJar.ranged(this, "[${libs.versions.netty.get()},)")
|
|
|
|
isTransitive = false
|
|
|
|
}
|
2022-11-09 23:58:56 +00:00
|
|
|
|
|
|
|
testFixturesApi(libs.bundles.test)
|
|
|
|
testFixturesApi(libs.bundles.kotlin)
|
|
|
|
|
|
|
|
testImplementation(testFixtures(project(":core")))
|
|
|
|
testImplementation(libs.bundles.test)
|
|
|
|
testRuntimeOnly(libs.bundles.testRuntime)
|
|
|
|
|
|
|
|
testModImplementation(testFixtures(project(":core")))
|
2022-11-10 15:48:26 +00:00
|
|
|
testModImplementation(testFixtures(project(":forge")))
|
2022-11-09 23:58:56 +00:00
|
|
|
|
2024-01-31 19:47:03 +00:00
|
|
|
// Ensure our test fixture dependencies are on the classpath
|
|
|
|
"testMinecraftLibrary"(libs.bundles.kotlin)
|
|
|
|
"testMinecraftLibrary"(libs.bundles.test)
|
|
|
|
|
2023-10-08 14:21:33 +00:00
|
|
|
testFixturesImplementation(testFixtures(project(":core")))
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Compile tasks
|
|
|
|
|
|
|
|
tasks.processResources {
|
|
|
|
inputs.property("modVersion", modVersion)
|
|
|
|
inputs.property("forgeVersion", libs.versions.forge.get())
|
|
|
|
|
|
|
|
filesMatching("META-INF/mods.toml") {
|
|
|
|
expand(mapOf("forgeVersion" to libs.versions.forge.get(), "file" to mapOf("jarVersion" to modVersion)))
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
tasks.jar {
|
|
|
|
finalizedBy("reobfJar")
|
|
|
|
archiveClassifier.set("slim")
|
|
|
|
|
2022-11-17 09:26:57 +00:00
|
|
|
for (source in cct.sourceDirectories.get()) {
|
|
|
|
if (source.classes && source.external) from(source.sourceSet.output)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
tasks.sourcesJar {
|
|
|
|
for (source in cct.sourceDirectories.get()) from(source.sourceSet.allSource)
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
2023-03-29 08:30:29 +00:00
|
|
|
tasks.jarJar {
|
|
|
|
finalizedBy("reobfJarJar")
|
2022-11-09 23:58:56 +00:00
|
|
|
archiveClassifier.set("")
|
|
|
|
|
2023-03-29 08:30:29 +00:00
|
|
|
for (source in cct.sourceDirectories.get()) {
|
|
|
|
if (source.classes) from(source.sourceSet.output)
|
2022-11-17 09:26:57 +00:00
|
|
|
}
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
2023-03-29 08:30:29 +00:00
|
|
|
tasks.assemble { dependsOn("jarJar") }
|
2022-11-09 23:58:56 +00:00
|
|
|
|
|
|
|
// Check tasks
|
|
|
|
|
|
|
|
tasks.test {
|
2023-10-19 17:28:15 +00:00
|
|
|
systemProperty("cct.test-files", layout.buildDirectory.dir("tmp/testFiles").getAbsolutePath())
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
val runGametest by tasks.registering(JavaExec::class) {
|
|
|
|
group = LifecycleBasePlugin.VERIFICATION_GROUP
|
|
|
|
description = "Runs tests on a temporary Minecraft instance."
|
|
|
|
dependsOn("cleanRunGametest")
|
2022-11-18 23:57:25 +00:00
|
|
|
usesService(MinecraftRunnerService.get(gradle))
|
2022-11-09 23:58:56 +00:00
|
|
|
|
2023-06-29 19:10:17 +00:00
|
|
|
setRunConfig(minecraft.runs["gameTestServer"])
|
2022-11-09 23:58:56 +00:00
|
|
|
|
2023-10-19 17:28:15 +00:00
|
|
|
systemProperty("cctest.gametest-report", layout.buildDirectory.dir("test-results/$name.xml").getAbsolutePath())
|
2022-11-18 23:57:25 +00:00
|
|
|
}
|
2022-11-09 23:58:56 +00:00
|
|
|
cct.jacoco(runGametest)
|
|
|
|
tasks.check { dependsOn(runGametest) }
|
|
|
|
|
2022-11-18 23:57:25 +00:00
|
|
|
val runGametestClient by tasks.registering(ClientJavaExec::class) {
|
|
|
|
description = "Runs client-side gametests with no mods"
|
2023-06-29 19:10:17 +00:00
|
|
|
setRunConfig(minecraft.runs["testClient"])
|
2022-11-18 23:57:25 +00:00
|
|
|
tags("client")
|
|
|
|
}
|
|
|
|
cct.jacoco(runGametestClient)
|
|
|
|
|
|
|
|
tasks.register("checkClient") {
|
|
|
|
group = LifecycleBasePlugin.VERIFICATION_GROUP
|
|
|
|
description = "Runs all client-only checks."
|
|
|
|
dependsOn(runGametestClient)
|
|
|
|
}
|
|
|
|
|
2022-11-09 23:58:56 +00:00
|
|
|
// Upload tasks
|
|
|
|
|
2023-03-15 23:20:07 +00:00
|
|
|
modPublishing {
|
2023-03-29 08:30:29 +00:00
|
|
|
output.set(tasks.jarJar)
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// Don't publish the slim jar
|
|
|
|
for (cfg in listOf(configurations.apiElements, configurations.runtimeElements)) {
|
|
|
|
cfg.configure { artifacts.removeIf { it.classifier == "slim" } }
|
|
|
|
}
|
|
|
|
|
|
|
|
publishing {
|
|
|
|
publications {
|
|
|
|
named("maven", MavenPublication::class) {
|
|
|
|
fg.component(this)
|
2023-03-29 08:30:29 +00:00
|
|
|
// jarJar.component is broken (https://github.com/MinecraftForge/ForgeGradle/issues/914), so declare the
|
|
|
|
// artifact explicitly.
|
|
|
|
artifact(tasks.jarJar)
|
|
|
|
|
2022-11-17 09:26:57 +00:00
|
|
|
mavenDependencies {
|
2023-12-16 22:35:11 +00:00
|
|
|
cct.configureExcludes(this)
|
2022-11-17 09:26:57 +00:00
|
|
|
exclude(libs.jei.forge.get())
|
2022-11-09 23:58:56 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|