Kotlin / kotlinx.serialization

Kotlin multiplatform / multi-format serialization
Apache License 2.0
5.41k stars 620 forks source link

Strings are converted to Int in non-lenient mode #2696

Open spand opened 5 months ago

spand commented 5 months ago

Describe the bug It seems that strings will be automatically converted to Int by default in Json. That is highly surprising and especially so when lenient is set to false.

To Reproduce

    @Serializable
    data class Asd(
        val itsAnInt: Int,
    )

    @Test
    fun asd() {
        Json.decodeFromString<Asd>("""{"itsAnInt":"1"}""")
    }

Expected behavior I expected it to throw an exception

Environment

sandwwraith commented 5 months ago

Can you explain why it is problematic for strings to be parsed as integers? From my experience, people find it more convenient when they don't have to think whether a particular value was quoted, since the serialization side is not always in their control. kotlinx.serialization itself always produces unquoted integers on encodeToString though. Also it simplifies working with maps (see #2438)

JakeWharton commented 5 months ago

While this is for 32-bit integers, I've also seen integers larger than 53 bits quoted so as to not lose precision with JS clients/servers/proxies. Having them transparently unwrapped when a proper 64-bit integer type is available is convenient.

spand commented 5 months ago

Concretely we had a bug where a developer had used Int in the type definition where it should have been a String since the possible values were more than just quoted numbers. You could put that on the developer but at least if this feature had not existed the developer would have been forced to use String and handle the "not a number" case explicitly.

In the abstract it is quite odd that such behavior is standard because

I believe I have made my point here so I will stop unless you want more.

Obviously I understand the convenience for such features given the amount of crazy json out there but to have it anything other than opt-in I dont really get.

pdvrieze commented 5 months ago

@JakeWharton I can see the point of quoting for long, but I also agree with @spand. I've seen too much going wrong with "almostJson", "almostXML" etc. formats. It should not be too challenging to have a configuration flag for this behaviour (say strictInts).

@sandwwraith The "problematic" aspect is that it creates a dialect (non-serialization) producers of messages get away with an incorrect message without this being signalled