diff --git a/build.gradle.kts b/build.gradle.kts index 2c52711..f3dc994 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -4,6 +4,14 @@ import org.jetbrains.kotlin.gradle.tasks.KotlinCompile plugins { kotlin("jvm") version "2.2.20" + // KSP for moshi-kotlin-codegen — generates JsonAdapter classes at + // compile time so the shaded JAR doesn't have to ship kotlin-reflect. + // Reflection-based KotlinJsonAdapterFactory + ShadowJar's `relocate(kotlin)` + // produced corrupted paths inside the .kotlin_builtins resources + // (`gg/grounds/platform/shaded/kotlin/gg.grounds.platform.shaded.kotlin.…_builtins`) + // and crashed Moshi's adapter() at plugin onEnable. Codegen sidesteps the + // whole reflection path. + id("com.google.devtools.ksp") version "2.2.20-2.0.4" id("com.gradleup.shadow") version "9.4.1" id("com.diffplug.spotless") version "8.4.0" } @@ -32,7 +40,8 @@ dependencies { // we get back from forge. Avoids pulling in jackson / gson which // would inflate the shadow jar dramatically for two DTOs. implementation("com.squareup.moshi:moshi:1.15.2") - implementation("com.squareup.moshi:moshi-kotlin:1.15.2") + // moshi-kotlin (reflection) replaced with codegen — see plugins block. + ksp("com.squareup.moshi:moshi-kotlin-codegen:1.15.2") testImplementation("org.junit.jupiter:junit-jupiter:5.11.3") testRuntimeOnly("org.junit.platform:junit-platform-launcher") diff --git a/src/main/kotlin/gg/grounds/platform/whitelist/WhitelistApiClient.kt b/src/main/kotlin/gg/grounds/platform/whitelist/WhitelistApiClient.kt index 568f466..4e5da76 100644 --- a/src/main/kotlin/gg/grounds/platform/whitelist/WhitelistApiClient.kt +++ b/src/main/kotlin/gg/grounds/platform/whitelist/WhitelistApiClient.kt @@ -1,9 +1,8 @@ package gg.grounds.platform.whitelist import com.squareup.moshi.JsonAdapter +import com.squareup.moshi.JsonClass import com.squareup.moshi.Moshi -import com.squareup.moshi.Types -import com.squareup.moshi.kotlin.reflect.KotlinJsonAdapterFactory import java.net.URI import java.net.http.HttpClient import java.net.http.HttpRequest @@ -33,8 +32,12 @@ class WhitelistApiClient( HttpClient.newBuilder().connectTimeout(Duration.ofSeconds(5)).build(), ) { + // Codegen-backed adapter: KSP generates ListResponseJsonAdapter at + // compile time, no kotlin-reflect on the runtime classpath. Mandatory + // because shadowJar's `relocate(kotlin)` corrupts the .kotlin_builtins + // resources that the reflection-based adapter loads. private val adapter: JsonAdapter = - Moshi.Builder().add(KotlinJsonAdapterFactory()).build().adapter(ListResponse::class.java) + Moshi.Builder().build().adapter(ListResponse::class.java) /** * Fetches the current whitelist. Throws on any non-2xx — caller decides whether to surface or @@ -69,11 +72,9 @@ class WhitelistApiClient( return parsed.items.map { WhitelistEntry(mcUuid = it.mcUuid, mcUsername = it.mcUsername) } } - private data class ListResponse(val items: List) { + @JsonClass(generateAdapter = true) + internal data class ListResponse(val items: List) { + @JsonClass(generateAdapter = true) data class RawEntry(val mcUuid: String, val mcUsername: String) } - - @Suppress("unused") - private val typeRef = - Types.newParameterizedType(List::class.java, ListResponse.RawEntry::class.java) }