I'm having an issue that my field name changes depending on my response from other items. In Kotlin Serialization I know we can serialize fields and such like this
@Serializable data class WeatherResponse (@SerialName("some_weather_id") val weatherData:WeatherData )
However, in my case "some_weather_id" annotation can change based on previous data and api responses. It can be "another_weather_id" etc.
My question is how can we change that or make the annotation dynamic?
I tried implementing a custom serializer, but I get the error
Field 'weatherData' is required for type with serial name 'com.test.WeatherResponse', but it was missing at path: $
Here is my custom serializer in case I'm doing something incorrect
object SerialNameSerializer : KSerializer<String> {
override val descriptor = PrimitiveSerialDescriptor("DynamicSerialName", PrimitiveKind.STRING)
override fun serialize(encoder: Encoder, value: String) {
val dynamicName = getWeatherID()
encoder.encodeStructure(descriptor){
encodeStringElement(descriptor, 0, dynamicName)
encodeStringElement(descriptor,1,value)
}
}
override fun deserialize(decoder: Decoder): String {
val dynamicName = getWeatherID()
decoder.decodeStructure(descriptor){
val name = decodeStringElement(descriptor,0)
if(name != dynamicName) {
throw SerializationException("Unexpected field name: $name")
}
return@decodeStructure decodeStringElement(descriptor, 1)
}
return dynamicName
}
private fun getWeatherID(): String {
return "some_weather_id"
}
}
I'm having an issue that my field name changes depending on my response from other items. In Kotlin Serialization I know we can serialize fields and such like this
@Serializable data class WeatherResponse (@SerialName("some_weather_id") val weatherData:WeatherData )
However, in my case "some_weather_id" annotation can change based on previous data and api responses. It can be "another_weather_id" etc.
My question is how can we change that or make the annotation dynamic?
I tried implementing a custom serializer, but I get the error
Field 'weatherData' is required for type with serial name 'com.test.WeatherResponse', but it was missing at path: $
Here is my custom serializer in case I'm doing something incorrect
object SerialNameSerializer : KSerializer<String> {
override val descriptor = PrimitiveSerialDescriptor("DynamicSerialName", PrimitiveKind.STRING)
override fun serialize(encoder: Encoder, value: String) {
val dynamicName = getWeatherID()
encoder.encodeStructure(descriptor){
encodeStringElement(descriptor, 0, dynamicName)
encodeStringElement(descriptor,1,value)
}
}
override fun deserialize(decoder: Decoder): String {
val dynamicName = getWeatherID()
decoder.decodeStructure(descriptor){
val name = decodeStringElement(descriptor,0)
if(name != dynamicName) {
throw SerializationException("Unexpected field name: $name")
}
return@decodeStructure decodeStringElement(descriptor, 1)
}
return dynamicName
}
private fun getWeatherID(): String {
return "some_weather_id"
}
}
If the names are known, you can use JsonNames like:
@Serializable
data class WeatherResponse(
@JsonNames("some_weather_id", "another_weather_id") val weatherData: WeatherData
)
More examples: https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/json.md#alternative-json-names