错误:解析具有接口中定义的getter / setter值的类时,“声明多个名为...的JSON字段”

时间:2019-05-31 02:54:23

标签: kotlin gson

请考虑以下类/接口:

interface ExampleKotlinInterface {
    val name: String
}
interface ExampleKotlinInterfaceSubclass : ExampleKotlinInterface {
    override var name: String
}
abstract class ExampleKotlinImpl(@SerializedName("name") override val name: String = "zach") : ExampleKotlinInterface
class ExampleKotlinImplSubclass(override var name: String) : ExampleKotlinImpl(name), ExampleKotlinInterfaceSubclass

其中第一个接口定义了一个值name,第二个接口对此值进行了扩展,但将name值公开为一个变量。由于出现以下错误,我无法用Gson解析ExampleKotlinImplSubclass

java.lang.IllegalArgumentException: class com.example.kotlingetterinterfaceexample.ExampleKotlinImplSubclass declares multiple JSON fields named name

    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory.getBoundFields(ReflectiveTypeAdapterFactory.java:172)
    at com.google.gson.internal.bind.ReflectiveTypeAdapterFactory.create(ReflectiveTypeAdapterFactory.java:102)
    at com.google.gson.Gson.getAdapter(Gson.java:458)
    at com.google.gson.Gson.fromJson(Gson.java:926)
    at com.google.gson.Gson.fromJson(Gson.java:892)
    at com.google.gson.Gson.fromJson(Gson.java:841)
    at com.google.gson.Gson.fromJson(Gson.java:813)
    at com.example.kotlingetterinterfaceexample.ExampleGsonParseTests.testParseObject(ExampleGsonParseTests.kt:13)

使用此测试代码:

        val json = "{ \"name\" : \"test\" }"

        val result = Gson().fromJson(json, ExampleKotlinImplSubclass::class.java)

        assertNotNull(result)

        assertEquals("test", result.name)

从理论上讲,不应允许我的超类更改name的值,但子类应该能够。

关于如何解决此问题的任何想法?

指向显示此问题的示例项目的链接:https://github.com/ZOlbrys/kotlingetterinterfaceexample

1 个答案:

答案 0 :(得分:0)

请参阅基于Java的answer。 GSON不能很好地处理这种情况。我看到的唯一选择是您不覆盖字段。您可以做些什么-如果有帮助的话-在界面中再创建一个关卡,例如:

interface ExampleKotlinInterfaceTop {
    fun getName(): String
    ...
}

interface ExampleKotlinInterface : ExampleKotlinInterfaceTop {
    val name: String
    ...
}

interface ExampleKotlinInterfaceSubclass : ExampleKotlinInterfaceTop {
    var name: String
    ...
}

我不是Kotlin程序员,所以我想在示例代码中要解决很多问题,但这是可能解决方案的原则。