From c4265b10c55e5c773f0571cb4536fa18fb3a936d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ensar=20Saraj=C4=8Di=C4=87?= Date: Mon, 20 Dec 2021 14:57:06 +0100 Subject: [PATCH 1/5] chore: update version to 0.4.4 --- gradle.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gradle.properties b/gradle.properties index f8e4ac3..ba26c09 100644 --- a/gradle.properties +++ b/gradle.properties @@ -11,4 +11,4 @@ org.gradle.parallel=true org.gradle.caching=true org.gradle.jvmargs=-XX:MaxMetaspaceSize=1g -version=0.4.3 +version=0.4.4 From a49b3aea650d311a9f588ae0a2663ec559ad3606 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ensar=20Saraj=C4=8Di=C4=87?= Date: Mon, 20 Dec 2021 15:36:33 +0100 Subject: [PATCH 2/5] feat: add configuration option for ignoring unknown keys This closes #69 --- .../MsgPackConfiguration.kt | 8 ++++++- .../internal/MsgPackDecoder.kt | 11 +++++++-- .../msgpack/MsgPackDecoderTest.kt | 9 ++++++++ .../serialization/msgpack/MsgPackTest.kt | 23 +++++++++++++++---- .../kotlinx/serialization/msgpack/TestData.kt | 3 +++ 5 files changed, 47 insertions(+), 7 deletions(-) diff --git a/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/MsgPackConfiguration.kt b/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/MsgPackConfiguration.kt index d99b702..367f544 100644 --- a/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/MsgPackConfiguration.kt +++ b/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/MsgPackConfiguration.kt @@ -31,7 +31,13 @@ data class MsgPackConfiguration( * Useful when combined with strict mode type * true by default */ - val preventOverflows: Boolean = true + val preventOverflows: Boolean = true, + /** + * Prevent exceptions when unknown keys are found when deserializing + * Useful when only parts of data are of interest + * false by default + */ + val ignoreUnknownKeys: Boolean = false ) { companion object { @JvmStatic diff --git a/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/internal/MsgPackDecoder.kt b/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/internal/MsgPackDecoder.kt index b74139e..69766c0 100644 --- a/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/internal/MsgPackDecoder.kt +++ b/serialization-msgpack/src/commonMain/kotlin/com.ensarsarajcic.kotlinx.serialization.msgpack/internal/MsgPackDecoder.kt @@ -1,6 +1,7 @@ package com.ensarsarajcic.kotlinx.serialization.msgpack.internal import com.ensarsarajcic.kotlinx.serialization.msgpack.MsgPackConfiguration +import com.ensarsarajcic.kotlinx.serialization.msgpack.MsgPackNullableDynamicSerializer import com.ensarsarajcic.kotlinx.serialization.msgpack.stream.MsgPackDataInputBuffer import com.ensarsarajcic.kotlinx.serialization.msgpack.types.MsgPackType import com.ensarsarajcic.kotlinx.serialization.msgpack.utils.joinToNumber @@ -29,8 +30,14 @@ internal class BasicMsgPackDecoder( if (descriptor.kind in arrayOf(StructureKind.CLASS, StructureKind.OBJECT)) { val next = dataBuffer.peekSafely() if (next != null && MsgPackType.String.isString(next)) { - val fieldName = kotlin.runCatching { decodeString() }.getOrNull() ?: return CompositeDecoder.DECODE_DONE - return descriptor.getElementIndex(fieldName) + val fieldName = kotlin.runCatching { decodeString() }.getOrNull() ?: return CompositeDecoder.UNKNOWN_NAME + val index = descriptor.getElementIndex(fieldName) + return if (index == CompositeDecoder.UNKNOWN_NAME && configuration.ignoreUnknownKeys) { + MsgPackNullableDynamicSerializer.deserialize(this) + decodeElementIndex(descriptor) + } else { + index + } } else { return CompositeDecoder.DECODE_DONE } diff --git a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackDecoderTest.kt b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackDecoderTest.kt index 04730c3..613e054 100644 --- a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackDecoderTest.kt +++ b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackDecoderTest.kt @@ -169,6 +169,15 @@ internal class MsgPackDecoderTest { } } + @Test + fun testDecodeIgnoreUnknownKeys() { + TestData.unknownKeysTestPairs.forEach { (input, result) -> + val decoder = BasicMsgPackDecoder(MsgPackConfiguration.default.copy(ignoreUnknownKeys = true), SerializersModule {}, input.hexStringToByteArray().toMsgPackBuffer()) + val serializer = TestData.SampleClass.serializer() + assertEquals(result, serializer.deserialize(decoder)) + } + } + private fun testPairs(decodeFunction: MsgPackDecoder.() -> RESULT, vararg pairs: Pair) { pairs.forEach { (input, result) -> MsgPackDecoder(BasicMsgPackDecoder(MsgPackConfiguration.default, SerializersModule {}, input.hexStringToByteArray().toMsgPackBuffer())).also { diff --git a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt index fdc4a53..626fb5b 100644 --- a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt +++ b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt @@ -1,6 +1,8 @@ package com.ensarsarajcic.kotlinx.serialization.msgpack import com.ensarsarajcic.kotlinx.serialization.msgpack.extensions.MsgPackTimestamp +import com.ensarsarajcic.kotlinx.serialization.msgpack.internal.BasicMsgPackDecoder +import com.ensarsarajcic.kotlinx.serialization.msgpack.stream.toMsgPackBuffer import kotlinx.serialization.KSerializer import kotlinx.serialization.builtins.ArraySerializer import kotlinx.serialization.builtins.ByteArraySerializer @@ -11,6 +13,7 @@ import kotlinx.serialization.builtins.nullable import kotlinx.serialization.builtins.serializer import kotlinx.serialization.decodeFromByteArray import kotlinx.serialization.encodeToByteArray +import kotlinx.serialization.modules.SerializersModule import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue @@ -292,6 +295,22 @@ internal class MsgPackTest { ) } + @Test + fun testDecodeIgnoreUnknownKeys() { + fun testPairs(dataList: Array>, serializer: KSerializer) { + dataList.forEach { (value, expectedResult) -> + val result = MsgPack( + configuration = MsgPackConfiguration(ignoreUnknownKeys = true) + ).decodeFromByteArray(serializer, value.hexStringToByteArray()) + assertEquals(expectedResult, result) + } + } + testPairs( + TestData.unknownKeysTestPairs, + TestData.SampleClass.serializer() + ) + } + @Test fun testOverflows() { fun testPairs(dataList: List, serializer: KSerializer) { @@ -337,10 +356,6 @@ internal class MsgPackTest { fun testNestedStructures() { val sm1: NestedMessage = listOf("Alice" to "Bob", "Charley" to "Delta") to "Random message Body here" val result = MsgPack.encodeToByteArray(sm1) - println(result.toHex()) - println(result.toList()) - println(result.size) - println(MsgPack.decodeFromByteArray>(MsgPack.encodeToByteArray(1 to 2))) val result2 = MsgPack.decodeFromByteArray(result) assertEquals(sm1, result2) } diff --git a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/TestData.kt b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/TestData.kt index cdfafdd..5fece31 100644 --- a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/TestData.kt +++ b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/TestData.kt @@ -155,6 +155,9 @@ object TestData { val sampleClassTestPairs = arrayOf( "83aa74657374537472696e67a3646566a774657374496e747bab74657374426f6f6c65616ec3" to SampleClass("def", 123, true) ) + val unknownKeysTestPairs = arrayOf( + "85aa74657374537472696e67a3646566ab7465737449676e6f72656491a969676e6f7265206d65a774657374496e747bab74657374556e6b6e6f776ea7756e6b6e6f776eab74657374426f6f6c65616ec3" to SampleClass("def", 123, true) + ) val pairsTestPairs: Array>> = arrayOf( "82a56669727374a5416c696365a67365636f6e64a3426f62" to Pair("Alice", "Bob") ) From cb138de9a7d2e2039cbcc2c2bb3d6799ae1c8a06 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ensar=20Saraj=C4=8Di=C4=87?= Date: Mon, 20 Dec 2021 15:40:59 +0100 Subject: [PATCH 3/5] chore: update changelog --- CHANGELOG.md | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 55d89cb..fbb83f3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,11 @@ All notable changes to this project will be documented in this file. This change log follows the conventions of [keepachangelog.com](http://keepachangelog.com/). ## [Unreleased] +- Added support for ignoring unknown keys ([#69][i69]) + +``` +val msgPack = MsgPack(MsgPackConfiguration.default.copy(ignoreUnknownKeys = true)) +``` ## [0.4.3] - 2021-12-17 - Added windows target using cross-compilation ([#60][i60]) @@ -75,13 +80,14 @@ MsgPack.default.encodeToByteArray(...) - `MsgPackDynamicSerializer` as placeholder for future [contextual serializer](https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/serializers.md#contextual-serialization) - Full implementation of msgpack spec excluding extension types and bin format family -[Unreleased]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.2...main +[Unreleased]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.3...main [0.2.0]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.1.0...0.2.0 [0.2.1]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.2.0...0.2.1 [0.3.0]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.2.1...0.3.0 [0.4.0]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.3.0...0.4.0 [0.4.1]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.0...0.4.1 [0.4.2]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.1...0.4.2 +[0.4.3]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.2...0.4.3 [i6]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/6 [i9]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/9 [i10]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/10 @@ -97,4 +103,5 @@ MsgPack.default.encodeToByteArray(...) [i57]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/57 [i60]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/60 [i63]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/63 +[i69]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/69 [p40]: https://github.com/esensar/kotlinx-serialization-msgpack/pull/40 From 673748644c8e43eca019456313eb925db498a0a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ensar=20Saraj=C4=8Di=C4=87?= Date: Mon, 20 Dec 2021 15:41:34 +0100 Subject: [PATCH 4/5] Update changelog for 0.4.4 release --- CHANGELOG.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index fbb83f3..8f209b5 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,8 @@ All notable changes to this project will be documented in this file. This change log follows the conventions of [keepachangelog.com](http://keepachangelog.com/). ## [Unreleased] + +## [0.4.4] - 2021-12-20 - Added support for ignoring unknown keys ([#69][i69]) ``` @@ -80,7 +82,7 @@ MsgPack.default.encodeToByteArray(...) - `MsgPackDynamicSerializer` as placeholder for future [contextual serializer](https://github.com/Kotlin/kotlinx.serialization/blob/master/docs/serializers.md#contextual-serialization) - Full implementation of msgpack spec excluding extension types and bin format family -[Unreleased]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.3...main +[Unreleased]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.4...main [0.2.0]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.1.0...0.2.0 [0.2.1]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.2.0...0.2.1 [0.3.0]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.2.1...0.3.0 @@ -88,6 +90,7 @@ MsgPack.default.encodeToByteArray(...) [0.4.1]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.0...0.4.1 [0.4.2]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.1...0.4.2 [0.4.3]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.2...0.4.3 +[0.4.4]: https://github.com/esensar/kotlinx-serialization-msgpack/compare/0.4.3...0.4.4 [i6]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/6 [i9]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/9 [i10]: https://github.com/esensar/kotlinx-serialization-msgpack/issues/10 From 73d921a5e63acfdea691f32a2918d9079b7ce3b4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ensar=20Saraj=C4=8Di=C4=87?= Date: Mon, 20 Dec 2021 15:47:56 +0100 Subject: [PATCH 5/5] style: fix ktlint issues in MsgPackTest --- .../ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt | 3 --- 1 file changed, 3 deletions(-) diff --git a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt index 626fb5b..1c9dc5e 100644 --- a/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt +++ b/serialization-msgpack/src/commonTest/kotlin/com/ensarsarajcic/kotlinx/serialization/msgpack/MsgPackTest.kt @@ -1,8 +1,6 @@ package com.ensarsarajcic.kotlinx.serialization.msgpack import com.ensarsarajcic.kotlinx.serialization.msgpack.extensions.MsgPackTimestamp -import com.ensarsarajcic.kotlinx.serialization.msgpack.internal.BasicMsgPackDecoder -import com.ensarsarajcic.kotlinx.serialization.msgpack.stream.toMsgPackBuffer import kotlinx.serialization.KSerializer import kotlinx.serialization.builtins.ArraySerializer import kotlinx.serialization.builtins.ByteArraySerializer @@ -13,7 +11,6 @@ import kotlinx.serialization.builtins.nullable import kotlinx.serialization.builtins.serializer import kotlinx.serialization.decodeFromByteArray import kotlinx.serialization.encodeToByteArray -import kotlinx.serialization.modules.SerializersModule import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertTrue