<@UFT11FKSP> ```@Serializable data class SuccessRe...
# kvision
w
@Robert Jaros
Copy code
@Serializable
data class SuccessResponse<T>(
        val status: Int,
        val data: T,
        val message: String
) : ApiResponse()

@Serializable
data class ErrorResponse(
        val status: Int,
        val errorCode: Int,
        val message: String
) : ApiResponse()

@Serializable
sealed class ApiResponse
Copy code
remoteCall(
                ApiRoutes.LOGIN,
                Json.encodeToString(AdminRequest.serializer(), body),
                ApiResponse.serializer(),
                <http://HttpMethod.POST|HttpMethod.POST>
        )
Copy code
when (this) {
    is SuccessResponse<*> -> {
        val data = this.unsafeCast<SuccessResponse<T>>()
        success(data)
    }
    is ErrorResponse -> {
        failure(this)
    }
    else -> {
        console.log(this)
    }
}
Need help with deserializing sealed classes, without else block throws NoWhenBranchMatchedException
a
What type does
this
have?
w
ApiResponse
r
Are you on IR backend?
w
No
a
I have tested this case in my own js project(with no IR), but its seems there is no compilation error being thrown. Are you sure there is only two subclasses of ApiResponse?
w
Yes
r
Can you check in DevTools how does the raw (json) response look like?
the error shows there is probably 'null' value in json
it looks like the serialization problem on the backend side? what do you use?
w
Copy code
{
  "status": 200,
  "data": {
    "hash": "<http://MTIzNDU2Nzg5.MQ|MTIzNDU2Nzg5.MQ>==..",
    "key": "eyJhbGciOiJIUzUxMiJ9.."
  },
  "message": "",
  "httpStatusCode": 200
}
ktor with gson
a
I guess the problem lies in the usage of generic, because it can't deserialize the "data"
I tried to deserialize a simple object but got
basically same error
w
@Arslan Armanuly yes
r
I think gson serialization is not compatible with kotlinx deserialization
it doesn't generate class descriptor
you should try ktor with kotlinx.serialization instead of gson
a
I am using kotlinx.serialization instead of gson but having same error
I guess it is problem of serialization and should be redirected to the #serialization
w
a
I guess the workaround is to have
data
as String and deserialize it after the
when
w
I'll try
@Arslan Armanuly Same error guess need to add this
Copy code
private val module = SerializersModule {
        polymorphic(ApiResponse::class) {
            subclass(SuccessResponse::class)
            subclass(ErrorResponse::class)
        }
    }
 private val client = RestClient(module)
@Robert Jaros no constructor for RestClient(SerializersModule) ?
r
It is available in 4.0.0
w
Okay, ⬆️ Upgrading to 4.0.0
r
I've managed to get polymorphic deserialization with generic class working (with kotlinx serialization and deserialization)
this is my example code:
Copy code
@Serializable
data class SuccessResponse<T>(
    val status: Int,
    val data: T,
    val message: String
) : ApiResponse<T>()

@Serializable
data class ErrorResponse<T>(
    val status: Int,
    val errorCode: Int,
    val message: String
) : ApiResponse<T>()

@Serializable
sealed class ApiResponse<T>

@Serializable
data class Data(val hash: String, val key: String)
I've added
T
to the
ApiResponse
And then:
Copy code
val responseModule = SerializersModule {
                polymorphic(ApiResponse::class) {
                    subclass(SuccessResponse.serializer(PolymorphicSerializer(Any::class)))
                }
                polymorphic(Any::class) {
                    subclass(Data::class)
                }
            }
Copy code
val source = SuccessResponse(5, Data("h", "k"), "message")
            val json = Json {
                serializersModule = responseModule
            }.encodeToString(
                ApiResponse.serializer(Data.serializer()),
                source
            )
            console.log(json)
            val x = Json { serializersModule = responseModule }.decodeFromString(
                ApiResponse.serializer(Data.serializer()),
                json
            )
            console.log(x)
I think you could use this to get what you wanted if you get kotlinx.serialization on the Ktor side. The generated json looks like this:
Copy code
{
  "type": "com.example.SuccessResponse",
  "status": 5,
  "data": {
    "type": "com.example.Data",
    "hash": "h",
    "key": "k"
  },
  "message": "message"
}
of course you need to register serializers for all
T
you use
w
@Robert Jaros Thanks a lot! I'll update ktor backend to use kotlinx serialization.