Closed abrooksv closed 2 months ago
External serializer generation is an experimental feature and likely shouldn't be allowed to be used on enums.
That would be very sad to hear unless a new way is added to get access to a plugin generated serializer (#1169)
Right now using the generated serializer gives you support for things like case insensitive enums and @SerialName
support. That is a lot of boiler plate to reproduce per enum if you want to wrap the serializer
Right now we use the plugin generated one with a fallback wrapper so that the serialization logic can be forwards compatible:
@Serializable
// Impossible to place this here to reduce copy paste from having to place at the use site: @Serializable(with = FamilySerializer::class)
enum class Family {
@SerialName("foo")
FOO,
UNKNOWN
}
object FamilySerializer : KSerializer<Family> by EnumWithFallbackSerializer(Family.serializer(), Family.UNKNOWN)
class EnumWithFallbackSerializer<T : Enum<T>>(
private val underlyingSerializer: KSerializer<T>,
private val fallbackValue: T
) : KSerializer<T> {
override val descriptor: SerialDescriptor = SerialDescriptor(
"EnumWithFallbackSerializer<${underlyingSerializer.descriptor.serialName}>",
underlyingSerializer.descriptor
)
override fun deserialize(decoder: Decoder): T {
return try {
underlyingSerializer.deserialize(decoder)
} catch (e: SerializationException) {
thisLogger().warn("Error deserializing message ${underlyingSerializer.descriptor.serialName}, falling back to $fallbackValue", e)
fallbackValue
}
}
override fun serialize(encoder: Encoder, value: T) {
underlyingSerializer.serialize(encoder, value)
}
}
So it's another use-case for #1169, I see
Fixed by #1169
Describe the bug When using the workaround to force generation of a plugin generated serializer for enums, the generated serializer always treats it as a class
To Reproduce
Generates:
Expected behavior Serializer should act the same as if generated by
@Serializable
Environment