jsTest.kotlinx.serialization.json.DecodeFromDynamicTest.kt Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of kotlinx-serialization-json
Show all versions of kotlinx-serialization-json
Kotlin multiplatform serialization runtime library
/*
* Copyright 2017-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
*/
package kotlinx.serialization.json
import kotlinx.serialization.descriptors.*
import kotlinx.serialization.encoding.*
import kotlinx.serialization.*
import kotlinx.serialization.modules.*
import kotlinx.serialization.test.*
import kotlin.test.*
import kotlin.test.assertFailsWith
class DecodeFromDynamicTest {
@Serializable
data class Data(val a: Int)
@Serializable
data class DataWrapper(val s: String, val d: Data?)
@Serializable
data class DataWrapperOptional(val s: String,val d: Data? = null)
@Serializable
data class IntList(val l: List)
@Serializable
data class ListOfLists(val l: List>)
@Serializable
data class MapWrapper(val m: Map)
@Serializable
data class ComplexMapWrapper(val m: Map)
@Serializable
data class IntMapWrapper(val m: Map)
@Serializable
data class WithChar(val a: Char)
@Serializable
data class AllTypes(
val b: Byte,
val s: Short,
val i: Int,
val f: Float,
val d: Double,
val c: Char,
val B: Boolean,
val S: String
)
@Serializable
data class NonTrivialMap(val m: Map)
data class NotDefault(val a: Int)
object NDSerializer : KSerializer {
override val descriptor = buildClassSerialDescriptor("notDefault") {
element("a")
}
override fun serialize(encoder: Encoder, value: NotDefault) {
encoder.encodeInt(value.a)
}
override fun deserialize(decoder: Decoder): NotDefault {
return NotDefault(decoder.decodeInt())
}
}
@Serializable
data class NDWrapper(@Contextual val data: NotDefault)
@Test
fun dynamicSimpleTest() {
val dyn = js("{a: 42}")
val parsed = Json.decodeFromDynamic(Data.serializer(), dyn)
assertEquals(Data(42), parsed)
val dyn2 = js("{a: 'a'}")
val parsed2 = Json.decodeFromDynamic(WithChar.serializer(), dyn2)
assertEquals(WithChar('a'), parsed2)
val dyn3 = js("{a: 97}")
val parsed3 = Json.decodeFromDynamic(WithChar.serializer(), dyn3)
assertEquals(WithChar('a'), parsed3)
}
@Test
fun dynamicAllTypesTest() {
val dyn = js("""{ b: 1, s: 2, i: 3, f: 1.0, d: 42.0, c: 'a', B: true, S: "str"}""")
val kotlinObj = AllTypes(1, 2, 3, 1.0f, 42.0, 'a', true, "str")
assertEquals(kotlinObj, Json.decodeFromDynamic(AllTypes.serializer(), dyn))
}
@Test
fun dynamicNestedTest() {
val dyn = js("""{s:"foo", d:{a:42}}""")
val parsed = Json.decodeFromDynamic(DataWrapper.serializer(), dyn)
val expected = DataWrapper("foo", Data(42))
assertEquals(expected, parsed)
assertEquals(3, parsed.s.length)
assertFailsWith(ClassCastException::class) { dyn as DataWrapper }
}
@Test
fun dynamicNullableTest() {
val dyn1 = js("""({s:"foo", d: null})""")
val dyn2 = js("""({s:"foo"})""")
val dyn3 = js("""({s:"foo", d: undefined})""")
assertEquals(DataWrapper("foo", null), Json.decodeFromDynamic(DataWrapper.serializer(), dyn1))
assertFailsWithMissingField {
Json.decodeFromDynamic(
DataWrapper.serializer(),
dyn2
)
}
assertFailsWithMissingField {
Json.decodeFromDynamic(
DataWrapper.serializer(),
dyn3
)
}
}
@Test
fun dynamicOptionalTest() {
val dyn1 = js("""({s:"foo", d: null})""")
val dyn2 = js("""({s:"foo"})""")
val dyn3 = js("""({s:"foo", d: undefined})""")
assertEquals(
DataWrapperOptional("foo", null),
Json.decodeFromDynamic(DataWrapperOptional.serializer(), dyn1)
)
assertEquals(
DataWrapperOptional("foo", null),
Json.decodeFromDynamic(DataWrapperOptional.serializer(), dyn2)
)
assertEquals(
DataWrapperOptional("foo", null),
Json.decodeFromDynamic(DataWrapperOptional.serializer(), dyn3)
)
}
@Test
fun dynamicListTest() {
val dyn1 = js("""({l:[1,2]})""")
val dyn2 = js("""({l:[[],[{a:42}]]})""")
assertEquals(IntList(listOf(1, 2)), Json.decodeFromDynamic(IntList.serializer(), dyn1))
assertEquals(
ListOfLists(listOf(listOf(), listOf(Data(42)))),
Json.decodeFromDynamic(ListOfLists.serializer(), dyn2)
)
}
@Test
fun dynamicMapTest() {
val dyn = js("({m : {\"a\": 1, \"b\" : 2}})")
val m = MapWrapper(mapOf("a" to 1, "b" to 2))
assertEquals(m, Json.decodeFromDynamic(MapWrapper.serializer(), dyn))
}
@Test
fun testFunnyMap() {
val dyn = js("({m: {\"a\": 'b', \"b\" : 'a'}})")
val m = NonTrivialMap(mapOf("a" to 'b', "b" to 'a'))
assertEquals(m, Json.decodeFromDynamic(NonTrivialMap.serializer(), dyn))
}
@Test
fun dynamicMapComplexTest() {
val dyn = js("({m: {1: {a: 42}, 2: {a: 43}}})")
val m = ComplexMapWrapper(mapOf("1" to Data(42), "2" to Data(43)))
assertEquals(m, Json.decodeFromDynamic(ComplexMapWrapper.serializer(), dyn))
}
@Test
fun testIntMapTest() {
val dyn = js("({m: {1: 2, 3: 4}})")
val m = IntMapWrapper(mapOf(1 to 2, 3 to 4))
assertEquals(m, Json.decodeFromDynamic(IntMapWrapper.serializer(), dyn))
}
@Test
fun parseWithCustomSerializers() {
val json = Json { serializersModule = serializersModuleOf(NotDefault::class, NDSerializer) }
val dyn1 = js("({data: 42})")
assertEquals(NDWrapper(NotDefault(42)),
json.decodeFromDynamic(NDWrapper.serializer(), dyn1)
)
}
}