I’m trying to get a Kotlin Ktor project running. I can build a jar with my gradle script but trying to run the jar errors out with a ClassNotFoundException
for the class that contains my main
method. Indeed, when looking at the MANIFEST.MF
file there is no classpath defined so no wonder the entry point isn’t found.
However, I can’t figure out how to fix this. I’ve cobbled together my gradle script from various examples on the internet but none of them seem to set the classpath explicitly to anything.
Googling led me to try to set the classpath manually with the following:
jar {
manifest {
attributes(
'Main-Class': application.mainClass, // defined earlier
'Class-Path': configurations.compile.collect { it.getName() }.join(' '))
}
}
but compile
is deprecated and I’m not sure what to substitute it with.
Here’s a Build Scan for good measure although the build itself works perfectly fine: Build Scan™ | Gradle Cloud Services
And here’s my build.gradle
since I don’t think its contents are included in the Build Scan:
plugins {
id 'application'
id 'org.jetbrains.kotlin.jvm' version '1.7.10'
id 'org.jetbrains.kotlin.plugin.serialization' version '1.7.10'
}
group = 'la.sakuer'
version = '0.0.1'
final String devmode = hasProperty('devmode') && getProperty('devmode') == 'true' ? 'true' : 'false'
final String ktor_version = '2.0.3'
application {
mainClass = 'la.sakuer.bilebandi.ApplicationKt'
applicationDefaultJvmArgs = [ "-Dio.ktor.development=$devmode" ]
}
repositories {
mavenCentral()
}
sourceSets {
main.kotlin.srcDirs = [ 'src/main' ]
main.resources.srcDirs = [ 'src/main/resources' ]
test.kotlin.srcDirs = [ 'src/test' ]
}
kotlin {
sourceSets {
main {
dependencies {
implementation "io.ktor:ktor-server-core-jvm:$ktor_version"
implementation "io.ktor:ktor-server-tomcat-jvm:$ktor_version"
implementation "io.ktor:ktor-server-html-builder:$ktor_version"
implementation "io.ktor:ktor-server-content-negotiation:$ktor_version"
implementation "io.ktor:ktor-serialization-kotlinx-json:$ktor_version"
implementation 'org.jetbrains.kotlinx:kotlinx-serialization-json:1.4.0-RC'
implementation 'com.google.cloud:google-cloud-firestore:3.3.0'
implementation 'ch.qos.logback:logback-classic:1.2.11'
}
}
test {
dependencies {
implementation "io.ktor:ktor-server-tests-jvm:$ktor_version"
implementation 'org.jetbrains.kotlin:kotlin-test-junit'
}
}
}
}
compileKotlin {
kotlinOptions.jvmTarget = '17'
}
tasks.register('postBuild') {
doFirst {
println 'Built with development mode: ' + devmode
}
}
tasks.named('build') { finalizedBy('postBuild') }
jar {
manifest {
attributes 'Main-Class': application.mainClass
}
from {
configurations.runtimeClasspath.collect {
it.isDirectory() ? it : zipTree(it)
}
}
// works around a bug, perhaps not optimal but no one seems to have a fix
duplicatesStrategy = DuplicatesStrategy.INCLUDE
}
The entry point is at src/main/Application.kt
, in package la.sakuer.bilebandi
. Gradle version is 7.5.
So, what would be the proper way to include the entry point in the classpath?