victordobry
victordobry

Reputation: 3408

"Accidental override: The following declarations have the same JVM signature" when implementing Java interface

I faced the following error trying to extend RuntimeException and implement GraphQLError interface, defined in Java, from my Kotlin code. This is the error:

Accidental override: The following declarations have the same JVM signature (getMessage()Ljava.lang.string;):

public open fun <get-message>(): String? defined in NegativeCountException public open fun getMessage(): String? defined in NegativeCountException

The following is my code:

class NegativeCountException() : RuntimeException(), GraphQLError {
  override fun getMessage(): String? {
    TODO("not implemented")
  }
  <...>
}

where GraphQLError is an interface, defined in Java as shown bellow:

public interface GraphQLError {
  String getMessage();
  <...>
}

Seems like it clashes with getMessage() defined in Throwable.

I can't change code of the interface, because it comes from a library.

How can I create my own runtime exception, that will implement GraphQLError?


PS: I also tried the following, and received a very similar error:

class NegativeCountException(override val message: String?) : RuntimeException(), GraphQLError {
  <...>
}

Upvotes: 13

Views: 4111

Answers (5)

Joey
Joey

Reputation: 820

There's actually a good solution for this (provided here):

class NegativeCountException(@JvmField override val message: String) : RuntimeException(message), GraphQLError {
    override fun getMessage(): String? = super.message
  <...>
}

Upvotes: 0

Inego
Inego

Reputation: 1159

There is a quick and dirty workaround, in case your project allows Java alongside Kolin. Write your NegativeCountException in Java :D

Upvotes: 0

Togrias
Togrias

Reputation: 101

This is a graphql problem. My workaround:

Reimplement GraphQLError, ExceptionWhileDataFetching and DataFetcherErrorHandler.

KGraphQLError is a "fixed" kotlin interface (with val instead of getters) that you use for your custom errors.

in KDataFetcherErrorHandler: Replace ExceptionWhileDataFetching in this line with KExceptionWhileDataFetching:
val error = ExceptionWhileDataFetching(path, exception, sourceLocation)

KExceptionWhileErrorHandling implements GraphQLError. Look through the code and replace all instances of if (exception is GraphQLError) with (exception is KGraphQLError)

Pass the new KDataFetcherErrorHandler to your queryExecutionStrategy and mutationExecutionStrategy.

Your custom errors can now extend Throwable and implement KGraphQLError, and get handled properly.

More info here: http://graphql-java.readthedocs.io/en/latest/execution.html

Upvotes: 2

Hendrik Marx
Hendrik Marx

Reputation: 744

I think it would work, when message was not a field in the one class (Throwable) and a method in the other. But it seems kotlin can not resolve the ambiguity when message is a field in the class and a method in the interface. If you have control over your GraphQlError you could do this:

class NegativeCountException() : RuntimeException(), GraphQLError {
    override val message: String?
        get() = super.message
}

interface GraphQLError {
    val message: String?
}

Upvotes: 1

Joshua
Joshua

Reputation: 6241

This is because Kotlin will create getters and setters for your variables when generating Java byte code. For example,

class Foo(val bar)

Foo with have getBar in Java byte code. To avoid name conflict, use @JvmField and @JvmName.

Read more about this here.

Upvotes: 0

Related Questions