java.lang.NoSuchMethodError when installing plugin in ktor - ktor

I am trying to add Resources plugin into my ktor client using the following code:
...
import io.ktor.client.*
import io.ktor.client.call.*
import io.ktor.client.engine.java.*
import io.ktor.client.plugins.*
import io.ktor.client.plugins.resources.*
import io.ktor.client.request.*
...
...
val HTTP_CLIENT = HttpClient(Java) {
install(Resources)
}
...
And here's part of my build.gradle.kts:
val ktor_version: String by project
plugins {
val kotlinVersion = "1.6.10"
kotlin("jvm") version kotlinVersion
kotlin("plugin.serialization") version kotlinVersion
}
dependencies {
implementation("org.jetbrains.kotlinx:kotlinx-serialization-json:1.3.2")
implementation("io.ktor:ktor-client-core:$ktor_version")
implementation("io.ktor:ktor-client-java:$ktor_version")
implementation("io.ktor:ktor-client-resources:$ktor_version")
}
The compile is successful, but when running I got following error:
java.lang.NoSuchMethodError: 'void io.ktor.client.HttpClientConfig.install$default(io.ktor.client.HttpClientConfig, io.ktor.client.plugins.HttpClientPlugin, kotlin.jvm.functions.Function1, int, java.lang.Object)'
2022-04-16 13:28:45 W/stderr: at NMEBoot-1.1.mirai.jar//NoMathExpectation.NMEBoot.wolframAlpha.Conversation$Companion$HTTP_CLIENT$1.invoke(Conversation.kt:20)
2022-04-16 13:28:45 W/stderr: at NMEBoot-1.1.mirai.jar//NoMathExpectation.NMEBoot.wolframAlpha.Conversation$Companion$HTTP_CLIENT$1.invoke(Conversation.kt:19)
2022-04-16 13:28:45 W/stderr: at io.ktor.client.HttpClientKt.HttpClient(HttpClient.kt:41)
2022-04-16 13:28:45 W/stderr: at NMEBoot-1.1.mirai.jar//NoMathExpectation.NMEBoot.wolframAlpha.Conversation.<clinit>(Conversation.kt:19)
I checked the jar and the source code and they both did have install method, but their signature was different from the signature described in the error.
I don't know if it is my fault or something else. Could someone help me solve this problem?
Edit: Here's a simplified project: KtorInstallTest

This is a bug on the Mirai side.
Mirai Console uses Kotlin 1.6.0 and for some reasons forces all plugins to use the same version of Kotlin, causing this problem. We plan to update to 1.6.20 by Mirai 2.11.0.

Related

Unable to use plugin in gradle.kts file

i´m trying to get a plugin to have the current version in a gradle kts file. I´m not able to get the apply for some reason, this is my code ->
buildscript {
repositories {
mavenLocal()
mavenCentral()
}
dependencies {
classpath("com.google.code.gson:gson:${rootProject.extra["gson_version"]}")
}
}
plugins {
id("me.tadej.versioning") version "0.2.0"
}
But i´m getting this error ->
"The plugins {} block must not be used here. If you need to apply a plugin imperatively, please use apply() or apply(plugin = "id") instead."
What i´m doing wrong here ?
Thanks!
EDIT:
I tried to write this as:
import com.google.gson.Gson
import java.io.BufferedReader
import java.io.BufferedWriter
import java.io.InputStreamReader
import java.io.OutputStreamWriter
import java.net.HttpURLConnection
import java.net.URL
plugins {
id("me.tadej.versioning") version "0.2.0"
}
repositories {
mavenLocal()
mavenCentral()
}
dependencies {
classpath("com.google.code.gson:gson:${rootProject.extra["gson_version"]}")
}
And got this error message:
ScriptCompilationException(errors=[ScriptCompilationError(message=Unresolved reference: gson, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (1:19)), ScriptCompilationError(message=Unresolved reference: classpath, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (17:5)), ScriptCompilationError(message=Unresolved reference: Gson, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (50:21)), ScriptCompilationError(message=Unresolved reference: Gson, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (100:16)), ScriptCompilationError(message=Unresolved reference: it, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (101:26)), ScriptCompilationError(message=Unresolved reference: it, location=/Users/develop/.gradle/.tmp/gradle-kotlin-dsl-14359683498958959271.tmp/jira.gradle.kts (101:40))])
at org.gradle.kotlin.dsl.support.KotlinCompilerKt.compileKotlinScriptModuleTo(KotlinCompiler.kt:187)
at org.gradle.kotlin.dsl.support.KotlinCompilerKt.compileKotlinScriptToDirectory(KotlinCompiler.kt:148)
at org.gradle.kotlin.dsl.execution.ResidualProgramCompiler$compileScript$1.invoke(ResidualProgramCompiler.kt:708)
at org.gradle.kotlin.dsl.execution.ResidualProgramCompiler$compileScript$1.invoke(ResidualProgramCompiler.kt:85)
at org.gradle.kotlin.dsl.provider.StandardKotlinScriptEvaluator$InterpreterHost$runCompileBuildOperation$1.call(KotlinScriptEvaluator.kt:162)...

Compose gradle community plugins requiring a version in a binary plugin

I'm writing a binary plugin that's pushed as an artifact to a remote repository to be re-used. One of the things I want to accomplish with this plugin is to compose a set of additional plugins that should always be present. When composing official gradle plugins like the java plugin, that works fine. But I can't find the strategy for composing a community plugin requiring a version that would use this syntax in a build.gradle.kts file:
plugins {
id("com.diffplug.spotless") version "6.1.0"
}
All of the APIs I'm discovering in the gradle plugin library makes no reference of specifying a version, which makes me think I need to configure it elsewhere, like how a build can specify defaults in the pluginManagement block in settings.gradle.
This is a distilled version of how I'm trying to apply this.
import org.gradle.api.Plugin
import org.gradle.api.Project
class MyPlugin : Plugin<Project> {
override fun apply(target: Project) {
// This works OK
target.plugins.apply("java")
// This is a community plugin, so it requires a version be set and fails
target.plugins.apply("com.diffplug.spotless")
}
}
Is there an API I'm missing? Or am I approaching this from the wrong direction?
Solved this by following aSemy's advice in a comment. I stopped trying to declare community plugins by ID and switched to applying the class of the plugin, after adding it to my plugin's classpath.
build.gradle.kts
dependencies {
api("com.diffplug.spotless:spotless-plugin-gradle:6.3.0")
}
Plugin class:
import com.diffplug.gradle.spotless.SpotlessPlugin
import org.gradle.api.Plugin
import org.gradle.api.Project
class MyPlugin : Plugin<Project> {
override fun apply(target: Project) {
target.plugins.apply("java")
target.plugins.apply(SpotlessPlugin::class.java)
}
}

'JacocoTaskExtension' does not exist with jdk11 , AGP 7.0.+ and ,Gradle 7.0.+

jacoco works like charm with AGP 4.0.1, gradle 6.+ , jdk1.8 but throw error "JacocoTaskExtension" not found with upgraded gradle version which is below.
Gradle 7.0.2
------------------------------------------------------------
Build time: 2021-05-14 12:02:31 UTC
Revision: 1ef1b260d39daacbf9357f9d8594a8a743e2152e
Kotlin: 1.4.31
Groovy: 3.0.7
Ant: Apache Ant(TM) version 1.10.9 compiled on September 27 2020
JVM: 11.0.12 (Oracle Corporation 11.0.12+8-LTS-237)
OS: Mac OS X 11.5 x86_64
Steps to reproduce :
I am not able to import JacocoTaskExtension in below kotlin class CodeCoveragePlugin
It's working fine with jkd 1.8 but not with jdk11
why am i using jdk11 ?
jdk11 is mandatory for agp 7.+ and gradle 7.+
My final goal : make it functional with agp7.+
package com.jitendra.sdk.android.gradle.quality.coverage
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.api.plugins.JavaPlugin
import org.gradle.api.plugins.JavaPluginConvention
import org.gradle.api.tasks.testing.Test
import org.gradle.kotlin.dsl.*
import org.gradle.testing.jacoco.plugins.JacocoPluginExtension
import org.gradle.testing.jacoco.plugins.JacocoTaskExtension
#Suppress("UnstableApiUsage")
class CodeCoveragePlugin : Plugin<Project> {
override fun apply(project: Project) = project.run {
val extension = extensions.create("codeCoverage", CodeCoverageExtension::class)
apply(plugin = "jacoco")
jacoco {
toolVersion = 0.8.7
}
java { createJavaTasks(sourceSets["main"], extension) }
setupAndroidTasks(extension)
}
private fun Project.java(run: JavaPlugin.() -> Unit) = plugins.withType(JavaPlugin::class, run)
private val Project.sourceSets get() = convention.getPlugin(JavaPluginConvention::class).sourceSets
private fun Project.jacoco(run: JacocoPluginExtension.() -> Unit) = configure(run)
}
I have had a similar issue. Could you please check the listed stack trace from the console?
If it contains:
Unexpected SMAP line: *S KotlinDebug"
Then it's clear that you haven't used the correct version 0.8.7 of Jacoco, as discussed here. In my case, I still need to add the following configuration:
configurations.all {
resolutionStrategy.eachDependency {
if (requested.group == "org.jacoco") {
useVersion("0.8.7")
}
}
}
You can put it inside your project.run closure. Hope it works. If not, please share your stack trace as part of your question.

IntelliJ missing reference to slf4j in new Ktor project

I started a new Ktor project through their IntelliJ plugin and everything is compiling and running fine with Gradle. However in IntelliJ everything that references the slf4j logger is having a Unresolved reference: ... error.
My import and setting log leve looks like this (sorry my reputation is not high enough to post images):
The project is generated with the following dependencies
// gradle.properties
ktor_version=1.4.0
logback_version=1.2.1
// build.gradle.kts
dependencies {
implementation("org.jetbrains.kotlin:kotlin-stdlib-jdk8:$kotlin_version")
implementation("io.ktor:ktor-server-netty:$ktor_version")
implementation("ch.qos.logback:logback-classic:$logback_version")
implementation("io.ktor:ktor-server-core:$ktor_version")
implementation("io.ktor:ktor-auth:$ktor_version")
implementation("io.ktor:ktor-auth-jwt:$ktor_version")
implementation("io.ktor:ktor-jackson:$ktor_version")
testImplementation("io.ktor:ktor-server-tests:$ktor_version")
}
I have tried to add org.slf4j:slf4j-nop:1.7.30 to my dependencies without any luck.
So my questions is, has anyone seen this error before and know if there is a dependency or setting i could change? It is annoying to not have any code completion and errors scattered around the IDE even though it compiles and run fine.
The full application code generated with the Ktor plugin is below if needed:
package com.example
import io.ktor.application.*
import io.ktor.response.*
import io.ktor.request.*
import io.ktor.features.*
import org.slf4j.event.*
import io.ktor.routing.*
import io.ktor.http.*
import io.ktor.auth.*
import com.fasterxml.jackson.databind.*
import io.ktor.jackson.*
fun main(args: Array<String>): Unit = io.ktor.server.netty.EngineMain.main(args)
#Suppress("unused") // Referenced in application.conf
#kotlin.jvm.JvmOverloads
fun Application.module(testing: Boolean = false) {
install(CallLogging) {
level = Level.INFO
filter { call -> call.request.path().startsWith("/") }
}
install(Authentication) {
}
install(ContentNegotiation) {
jackson {
enable(SerializationFeature.INDENT_OUTPUT)
}
}
routing {
get("/") {
call.respondText("HELLO WORLD!", contentType = ContentType.Text.Plain)
}
get("/json/jackson") {
call.respond(mapOf("hello" to "world"))
}
}
}
This was a caching issue with Gradle and IntelliJ, probably caused from other project dependencies. To IntelliJ the slf4j-api library was empty. Removing the global Gradle cache with rm -rf ~/.gradle/caches and re-download the dependencies solved the issue for me.

Unresolved reference: KotlinCompilerVersion in build.gradle.kts

In build.gradle.kts file, I include this code on the top line. Then I use KotlinCompilerVesion.VERSION below.
import org.jetbrains.kotlin.config.KotlinCompilerVersion
Some code works fine, but some code failed:
It seems like only plugins block can not enable this import.
Here works fine:
dependencies {
Implementation(kotlin("stdlib-jdk7", KotlinCompilerVersion.VERSION))
Implementation(kotlin("test", KotlinCompilerVersion.VERSION))
}
Here always wrong:
plugins {
id("com.android.application")
kotlin("android")
kotlin("android.extensions")
/*
* Error: Unresolved reference: KotlinCompilerVersion
*/
id("kotlinx-serialization") version KotlinCompilerVersion.VERSION
/*
* Error: Unresolved reference: KotlinCompilerVersion
*/
id("kotlinx-serialization") version "$KotlinCompilerVersion.VERSION"
/*
* Error: Unresolved reference: KotlinCompilerVersion
*/
id("kotlinx-serialization") version "${KotlinCompilerVersion.VERSION}"
}
How can I use it correctly in here, without declare an ext.xxxVersion var?
Yes, the syntax of the plugins DSL is limited because Gradle parses it before parsing the rest of the file, which requires the definition to be static (no references to variables, constants, etc., pretty much no code is allowed). See Limitations of the plugins DSL for details.
The way I handle defining Kotlin version only once is by actually using the version I specify in the plugins block as canonical in other sections of the file (I picked this up from this blog post by Simon Wirtz) like so:
import org.jetbrains.kotlin.gradle.plugin.KotlinPluginWrapper
val kotlinVersion = plugins.getPlugin(KotlinPluginWrapper::class.java)
.kotlinPluginVersion
plugins {
kotlin("jvm") version "1.3.30"
}
dependencies {
implementation(platform(kotlin("bom", kotlinVersion)))
implementation(kotlin("stdlib-jdk8"))
}
But yeah, in the plugins block it needs to be static and unfortunately repeated if needed.
Update: I actually just learned it's possible to use constants in the plugins DSL, but they must be defined before Gradle parses the build.gradle.kts file, i.e. from buildSrc. I noticed this in the fuel library. In essence, create buildSrc/build.gradle.kts with the following contents:
plugins {
`kotlin-dsl`
}
repositories {
jcenter()
}
Then create buildSrc/src/main/kotlin/Constants.kt with the following contents:
object Kotlin {
const val version = "1.3.30"
}
And then you'll be able to use the following in your main build.gradle.kts:
plugins {
kotlin("jvm") version Kotlin.version
}