Extract ProtoBuf format to the separate module
* Including SerialId annotation that is clearly ProtoBuf-specific
* Copy-paste some of the test (but not main!) sources to make it work. These classes will be extracted to mediator module to workaround KT-35073 when CBOR is extracted as well
* Replace @SerialId in core tests with @Id from test sources
* Postpone readme and publication for a while
* Make some types public for the sake of simplicity, will be revisited them during cleanup phase
diff --git a/build.gradle b/build.gradle
index 10b4186..5c47b29 100644
--- a/build.gradle
+++ b/build.gradle
@@ -71,8 +71,6 @@
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
classpath "org.jetbrains.kotlin:kotlin-serialization:$kotlin_version"
classpath "com.jfrog.bintray.gradle:gradle-bintray-plugin:$bintray_version"
-
- // Protobuf is udes in JVM tests
classpath 'com.google.protobuf:protobuf-gradle-plugin:0.8.8'
// Various benchmarking stuff
diff --git a/examples/example-visitors/src/test/kotlin/kotlinx/serialization/schema/ProtoSchemaTest.kt b/examples/example-visitors/src/test/kotlin/kotlinx/serialization/schema/ProtoSchemaTest.kt
index 2322e3f..a317ddf 100644
--- a/examples/example-visitors/src/test/kotlin/kotlinx/serialization/schema/ProtoSchemaTest.kt
+++ b/examples/example-visitors/src/test/kotlin/kotlinx/serialization/schema/ProtoSchemaTest.kt
@@ -16,7 +16,6 @@
package kotlinx.serialization.schema
-import kotlinx.serialization.SerialId
import kotlinx.serialization.Serializable
import kotlinx.serialization.protobuf.ProtoNumberType
import kotlinx.serialization.protobuf.ProtoType
diff --git a/formats/protobuf/build.gradle b/formats/protobuf/build.gradle
new file mode 100644
index 0000000..9d4c7b0
--- /dev/null
+++ b/formats/protobuf/build.gradle
@@ -0,0 +1,121 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+apply plugin: 'java' // Needed for protobuf plugin only
+apply plugin: 'kotlin-multiplatform'
+apply plugin: 'kotlinx-serialization'
+apply plugin: 'com.google.protobuf'
+apply from: rootProject.file("gradle/targets.gradle")
+apply from: rootProject.file("gradle/native_mpp.gradle")
+
+protobuf {
+ protoc {
+ // Download from repositories
+ artifact = 'com.google.protobuf:protoc:3.0.0'
+ }
+}
+
+clean {
+ delete protobuf.generatedFilesBaseDir
+}
+
+kotlin {
+ targets {
+ fromPreset(presets.jvm, 'jvm') {
+ withJava()
+ configure([compilations.main, compilations.test]) {
+ kotlinOptions {
+ jvmTarget = '1.6'
+ }
+ }
+ }
+ fromPreset(presets.js, 'js') {
+ nodejs {}
+ configure([compilations.main, compilations.test]) {
+ kotlinOptions {
+ sourceMap = true
+ moduleKind = "umd"
+ metaInfo = true
+ }
+ }
+ }
+ }
+
+ sourceSets.all {
+ kotlin.srcDirs = ["$it.name/src"]
+ resources.srcDirs = ["$it.name/resources"]
+ languageSettings {
+ progressiveMode = true
+ useExperimentalAnnotation("kotlin.Experimental")
+ useExperimentalAnnotation("kotlin.ExperimentalMultiplatform")
+ useExperimentalAnnotation("kotlin.ExperimentalStdlibApi")
+ useExperimentalAnnotation("kotlinx.serialization.InternalSerializationApi")
+ }
+ }
+
+ sourceSets {
+ commonMain {
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-stdlib-common'
+ api project(":kotlinx-serialization-runtime")
+ }
+ }
+
+ commonTest {
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-test-common'
+ api 'org.jetbrains.kotlin:kotlin-test-annotations-common'
+ }
+ }
+
+ jvmMain {
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-stdlib'
+ }
+ }
+
+ jvmTest {
+ kotlin.srcDirs += file("${protobuf.generatedFilesBaseDir}/test/java")
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-test-junit'
+ implementation 'com.google.protobuf:protobuf-java:3.0.0'
+ implementation 'io.kotlintest:kotlintest:2.0.7'
+ }
+ }
+
+ jsMain {
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-stdlib-js'
+ }
+ }
+
+ jsTest {
+ dependencies {
+ api 'org.jetbrains.kotlin:kotlin-test-js'
+ }
+ }
+
+ nativeMain.dependencies {
+ }
+ }
+
+ sourceSets.findAll({ it.name.contains("Test") }).forEach { srcSet ->
+ srcSet.languageSettings {
+ it.useExperimentalAnnotation("kotlinx.serialization.UnstableDefault")
+ it.useExperimentalAnnotation("kotlinx.serialization.InternalSerializationApi")
+
+ if (srcSet.name.contains("jvm") || srcSet.name.contains("js")) {
+ it.useExperimentalAnnotation("kotlinx.serialization.ImplicitReflectionSerializer")
+ }
+ }
+ }
+}
+
+sourceSets.test.proto {
+ srcDirs = ['testProto']
+}
+
+compileTestKotlinJvm {
+ dependsOn 'generateTestProto'
+}
diff --git a/runtime/commonMain/src/kotlinx/serialization/protobuf/ProtoBuf.kt b/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/ProtoBuf.kt
similarity index 100%
rename from runtime/commonMain/src/kotlinx/serialization/protobuf/ProtoBuf.kt
rename to formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/ProtoBuf.kt
diff --git a/runtime/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt b/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt
similarity index 87%
rename from runtime/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt
rename to formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt
index 753c6d3..10a8d13 100644
--- a/runtime/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt
+++ b/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/ProtoTypes.kt
@@ -25,3 +25,6 @@
public class ProtobufDecodingException(message: String) : SerializationException(message)
+
+public fun getSerialId(desc: SerialDescriptor, index: Int): Int?
+ = desc.findAnnotation<SerialId>(index)?.id
diff --git a/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/SerialId.kt b/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/SerialId.kt
new file mode 100644
index 0000000..f118aaa
--- /dev/null
+++ b/formats/protobuf/commonMain/src/kotlinx/serialization/protobuf/SerialId.kt
@@ -0,0 +1,11 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.*
+
+@SerialInfo
+@Target(AnnotationTarget.PROPERTY)
+annotation class SerialId(val id: Int)
diff --git a/formats/protobuf/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt
new file mode 100644
index 0000000..7fa95c2
--- /dev/null
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization
+
+import kotlinx.serialization.modules.SerializersModule
+import kotlinx.serialization.protobuf.*
+
+@Serializable
+open class PolyBase(@SerialId(1) val id: Int) {
+ override fun hashCode(): Int {
+ return id
+ }
+
+ override fun toString(): String {
+ return "PolyBase(id=$id)"
+ }
+
+ override fun equals(other: Any?): Boolean {
+ if (this === other) return true
+ if (other == null || this::class != other::class) return false
+
+ other as PolyBase
+
+ if (id != other.id) return false
+
+ return true
+ }
+
+}
+
+@Serializable
+data class PolyDerived(@SerialId(2) val s: String) : PolyBase(1)
+
+val BaseAndDerivedModule = SerializersModule {
+ polymorphic(PolyBase::class, PolyBase.serializer()) {
+ PolyDerived::class with PolyDerived.serializer()
+ }
+}
+
+@Serializable
+abstract class SimpleAbstract
+
+@Serializable
+data class SimpleIntInheritor(val i: Int, val s: String) : SimpleAbstract()
+
+@Serializable
+data class SimpleStringInheritor(val s: String, val i: Int) : SimpleAbstract()
+
+@Serializable
+data class PolyBox(@Polymorphic val boxed: SimpleAbstract)
+
+val SimplePolymorphicModule = SerializersModule {
+ polymorphic<SimpleAbstract> {
+ SimpleIntInheritor::class with SimpleIntInheritor.serializer()
+ SimpleStringInheritor::class with SimpleStringInheritor.serializer()
+ }
+}
+
+@Serializable
+data class SealedBox(val boxed: List<SimpleSealed>)
+
+@Serializable
+sealed class SimpleSealed {
+ @Serializable
+ public data class SubSealedA(val s: String) : SimpleSealed()
+
+ @Serializable
+ public data class SubSealedB(val i: Int) : SimpleSealed()
+}
+
diff --git a/formats/protobuf/commonTest/src/kotlinx/serialization/TestUtils.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/TestUtils.kt
new file mode 100644
index 0000000..9084575
--- /dev/null
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/TestUtils.kt
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization
+
+import kotlinx.serialization.internal.*
+import kotlin.test.*
+
+inline fun <reified T : Any> assertSerializedToBinaryAndRestored(
+ original: T,
+ serializer: KSerializer<T>,
+ format: BinaryFormat,
+ printResult: Boolean = false,
+ hexResultToCheck: String? = null
+) {
+ val bytes = format.dump(serializer, original)
+ val hexString = HexConverter.printHexBinary(bytes, lowerCase = true)
+ if (printResult) {
+ println("[Serialized form] $hexString")
+ }
+ if (hexResultToCheck != null) {
+ assertEquals(
+ hexResultToCheck.toLowerCase(),
+ hexString,
+ "Expected serialized binary to be equal in hex representation"
+ )
+ }
+ val restored = format.load(serializer, bytes)
+ if (printResult) println("[Restored form] $restored")
+ assertEquals(original, restored)
+}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt
similarity index 97%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt
index f96cb5a..d5cbea6 100644
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/AutoAssignIdsTest.kt
@@ -16,7 +16,6 @@
package kotlinx.serialization.protobuf
-import kotlinx.serialization.SerialId
import kotlinx.serialization.Serializable
import kotlin.test.Test
import kotlin.test.assertEquals
diff --git a/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ByteArraySerializerTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ByteArraySerializerTest.kt
new file mode 100644
index 0000000..8c5cb6d
--- /dev/null
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ByteArraySerializerTest.kt
@@ -0,0 +1,54 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.*
+import kotlinx.serialization.internal.ByteArraySerializer
+import kotlinx.serialization.json.Json
+import kotlin.random.Random
+import kotlin.test.*
+
+class ByteArraySerializerTest {
+
+ @Serializable
+ class ByteArrayCarrier(@SerialId(2) @Serializable(with = ByteArraySerializer::class) val data: ByteArray) {
+ override fun equals(other: Any?): Boolean {
+ if (this === other) return true
+ if (other == null || this::class != other::class) return false
+
+ other as ByteArrayCarrier
+
+ if (!data.contentEquals(other.data)) return false
+
+ return true
+ }
+
+ override fun hashCode(): Int {
+ return data.contentHashCode()
+ }
+
+ override fun toString(): String {
+ return "ByteArrayCarrier(data=${data.contentToString()})"
+ }
+ }
+
+ @Test
+ fun testByteArrayProtobuf() {
+ val obj = ByteArrayCarrier(byteArrayOf(42, 100))
+ val s = ProtoBuf.dumps(ByteArrayCarrier.serializer(), obj)
+ assertEquals("""12022a64""", s)
+ val obj2 = ProtoBuf.loads(ByteArrayCarrier.serializer(), s)
+ assertEquals(obj, obj2)
+ }
+
+ @Test
+ fun testWrappedByteArrayProtobuf() {
+ val arraySize = 301
+ val arr = Random.nextBytes(ByteArray(arraySize))
+ val obj = ByteArrayCarrier(arr)
+ val bytes = ProtoBuf.dump(ByteArrayCarrier.serializer(), obj)
+ assertEquals(obj, ProtoBuf.load(ByteArrayCarrier.serializer(), bytes))
+ }
+}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt
similarity index 98%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt
index cb95fd7..705d3d3 100644
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomSerializersProtobufTest.kt
@@ -6,7 +6,6 @@
import kotlinx.serialization.*
import kotlinx.serialization.modules.serializersModuleOf
-import kotlinx.serialization.json.JsonCustomSerializersTest.*
import kotlin.test.Test
import kotlin.test.assertEquals
diff --git a/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomizedSerializableTestClasses.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomizedSerializableTestClasses.kt
new file mode 100644
index 0000000..ee5ac8c
--- /dev/null
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/CustomizedSerializableTestClasses.kt
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+@file:ContextualSerialization(B::class)
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.*
+
+@Serializable
+data class A(@SerialId(1) val b: B)
+
+data class B(@SerialId(1) val value: Int)
+
+object BSerializer : KSerializer<B> {
+ override fun serialize(encoder: Encoder, obj: B) {
+ encoder.encodeInt(obj.value)
+ }
+
+ override fun deserialize(decoder: Decoder): B {
+ return B(decoder.decodeInt())
+ }
+
+ override val descriptor: SerialDescriptor = PrimitiveDescriptor("B", PrimitiveKind.INT)
+}
+
+@Serializable
+data class BList(@SerialId(1) val bs: List<B>)
+
+@Serializable
+data class C(@SerialId(1) val a: Int = 31, @SerialId(2) val b: Int = 42) {
+ @Serializer(forClass = C::class)
+ companion object: KSerializer<C> {
+ override fun serialize(encoder: Encoder, obj: C) {
+ val elemOutput = encoder.beginStructure(descriptor)
+ elemOutput.encodeIntElement(descriptor, 1, obj.b)
+ if (obj.a != 31) elemOutput.encodeIntElement(descriptor, 0, obj.a)
+ elemOutput.endStructure(descriptor)
+ }
+ }
+}
+
+@Serializable
+data class CList1(@SerialId(1) val c: List<C>)
+
+@Serializable
+data class CList2(@SerialId(1) val d: Int = 5, @SerialId(2) val c: List<C>) {
+ @Serializer(forClass = CList2::class)
+ companion object: KSerializer<CList2> {
+ override fun serialize(encoder: Encoder, obj: CList2) {
+ val elemOutput = encoder.beginStructure(descriptor)
+ elemOutput.encodeSerializableElement(descriptor, 1, C.list, obj.c)
+ if (obj.d != 5) elemOutput.encodeIntElement(descriptor, 0, obj.d)
+ elemOutput.endStructure(descriptor)
+ }
+ }
+}
+
+@Serializable
+data class CList3(@SerialId(1) val e: List<C> = emptyList(), @SerialId(2) val f: Int) {
+ @Serializer(forClass = CList3::class)
+ companion object: KSerializer<CList3> {
+ override fun serialize(encoder: Encoder, obj: CList3) {
+ val elemOutput = encoder.beginStructure(descriptor)
+ if (obj.e.isNotEmpty()) elemOutput.encodeSerializableElement(descriptor, 0, C.list, obj.e)
+ elemOutput.encodeIntElement(descriptor, 1, obj.f)
+ elemOutput.endStructure(descriptor)
+ }
+ }
+}
+
+@Serializable
+data class CList4(@SerialId(1) val g: List<C> = emptyList(), @SerialId(2) val h: Int) {
+ @Serializer(forClass = CList4::class)
+ companion object: KSerializer<CList4> {
+ override fun serialize(encoder: Encoder, obj: CList4) {
+ val elemOutput = encoder.beginStructure(descriptor)
+ elemOutput.encodeIntElement(descriptor, 1, obj.h)
+ if (obj.g.isNotEmpty()) elemOutput.encodeSerializableElement(descriptor, 0, C.list, obj.g)
+ elemOutput.endStructure(descriptor)
+ }
+ }
+}
+
+@Serializable
+data class CList5(@SerialId(1) val g: List<Int> = emptyList(), @SerialId(2) val h: Int) {
+ @Serializer(forClass = CList5::class)
+ companion object: KSerializer<CList5> {
+ override fun serialize(encoder: Encoder, obj: CList5) {
+ val elemOutput = encoder.beginStructure(descriptor)
+ elemOutput.encodeIntElement(descriptor, 1, obj.h)
+ if (obj.g.isNotEmpty()) elemOutput.encodeSerializableElement(descriptor, 0, IntSerializer.list,
+ obj.g)
+ elemOutput.endStructure(descriptor)
+ }
+ }
+}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufMissingFieldsTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufMissingFieldsTest.kt
similarity index 100%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufMissingFieldsTest.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufMissingFieldsTest.kt
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt
similarity index 91%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt
index 0f7582f..8cf7129 100644
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPolymorphismTest.kt
@@ -5,7 +5,6 @@
package kotlinx.serialization.protobuf
import kotlinx.serialization.*
-import kotlinx.serialization.test.assertSerializedToBinaryAndRestored
import kotlin.test.Test
class ProtobufPolymorphismTest {
diff --git a/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPrimitivesTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPrimitivesTest.kt
new file mode 100644
index 0000000..fee0814
--- /dev/null
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufPrimitivesTest.kt
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2017 JetBrains s.r.o.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.*
+import kotlin.test.*
+
+// TODO these tests are far from being comoplete
+class ProtobufPrimitivesTest {
+
+ private fun <T> testConversion(data: T, serializer: KSerializer<T>, expectedHexString: String) {
+ val string = ProtoBuf.dumps(serializer, data).toUpperCase()
+ assertEquals(expectedHexString, string)
+ assertEquals(data, ProtoBuf.loads(serializer, string))
+ }
+
+ @Test
+ fun testSignedInteger() {
+ testConversion(TestInt(-150), TestInt.serializer(), "08AB02")
+ }
+
+ @Test
+ fun testIntList() {
+ testConversion(TestList(listOf(150, 228, 1337)), TestList.serializer(), "08960108E40108B90A")
+
+ }
+
+ @Test
+ fun testString() {
+ testConversion(TestString("testing"), TestString.serializer(), "120774657374696E67")
+ }
+
+ @Test
+ fun testTwiceNested() {
+ testConversion(TestInner(TestInt(-150)), TestInner.serializer(), "1A0308AB02")
+ }
+
+ @Test
+ fun testMixedTags() {
+ testConversion(TestComplex(42, "testing"), TestComplex.serializer(), "D0022A120774657374696E67")
+ }
+
+ @Test
+ fun testDefaultPrimitiveValues() {
+ testConversion(TestInt(0), TestInt.serializer(), "0800")
+ testConversion(TestList(listOf()), TestList.serializer(), "")
+ testConversion(TestString(""), TestString.serializer(), "1200")
+ }
+
+ @Test
+ fun testFixedIntWithLong() {
+ testConversion(TestNumbers(100500, Long.MAX_VALUE), TestNumbers.serializer(), "0D9488010010FFFFFFFFFFFFFFFF7F")
+ }
+}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt
similarity index 90%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt
index f31f4ea..47245f0 100644
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/ProtobufUnionEnumTest.kt
@@ -22,7 +22,7 @@
fun testEnum() {
val data = WithUnions("foo", SomeEnum.BETA)
val hex = ProtoBuf.dumps(WithUnions.serializer(), data)
- val restored = ProtoBuf.loads<WithUnions>(WithUnions.serializer(), hex)
+ val restored = ProtoBuf.loads(WithUnions.serializer(), hex)
assertEquals(data, restored)
}
}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/SampleClasses.kt b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/SerializableTestClasses.kt
similarity index 78%
rename from runtime/commonTest/src/kotlinx/serialization/protobuf/SampleClasses.kt
rename to formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/SerializableTestClasses.kt
index 1a8d83a..01fa9f6 100644
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/SampleClasses.kt
+++ b/formats/protobuf/commonTest/src/kotlinx/serialization/protobuf/SerializableTestClasses.kt
@@ -16,9 +16,7 @@
package kotlinx.serialization.protobuf
-import kotlinx.serialization.SerialId
import kotlinx.serialization.Serializable
-import kotlin.test.assertEquals
@Serializable
data class TestInt(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Int)
@@ -43,13 +41,3 @@
@SerialId(1) val s: Int,
@SerialId(10) val l: List<Int>
)
-
-val t1 = TestInt(-150)
-val t1e = TestInt(0)
-val t2 = TestList(listOf(150, 228, 1337))
-val t2e = TestList(listOf())
-val t3 = TestString("testing")
-val t3e = TestString("")
-val t4 = TestInner(t1)
-val t5 = TestComplex(42, "testing")
-val t6 = TestNumbers(100500, Long.MAX_VALUE)
diff --git a/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/FormatConverterHelpers.kt b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/FormatConverterHelpers.kt
new file mode 100644
index 0000000..91b191b
--- /dev/null
+++ b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/FormatConverterHelpers.kt
@@ -0,0 +1,93 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import com.google.protobuf.GeneratedMessageV3
+import kotlinx.io.*
+import java.io.ByteArrayOutputStream
+import kotlinx.serialization.dump
+import kotlinx.serialization.loads
+
+interface IMessage {
+ fun toProtobufMessage(): GeneratedMessageV3
+}
+
+fun GeneratedMessageV3.toHex(): String {
+ val b = ByteArrayOutputStream()
+ this.writeTo(b)
+ return (HexConverter.printHexBinary(b.toByteArray(), lowerCase = true))
+}
+
+inline fun <reified T : IMessage> dumpCompare(it: T): Boolean {
+ val msg = it.toProtobufMessage()
+ var parsed: GeneratedMessageV3?
+ val c = try {
+ val bytes = ProtoBuf.dump(it)
+ parsed = msg.parserForType.parseFrom(bytes)
+ msg == parsed
+ } catch (e: Exception) {
+ e.printStackTrace()
+ parsed = null
+ false
+ }
+ return c
+}
+
+inline fun <reified T : IMessage> readCompare(it: T, alwaysPrint: Boolean = false): Boolean {
+ var obj: T?
+ val c = try {
+ val msg = it.toProtobufMessage()
+ val hex = msg.toHex()
+ obj = ProtoBuf.loads(hex)
+ obj == it
+ } catch (e: Exception) {
+ obj = null
+ e.printStackTrace()
+ false
+ }
+ if (!c || alwaysPrint) println("Expected: $it\nfound: $obj")
+ return c
+}
+
+object HexConverter {
+ fun parseHexBinary(s: String): ByteArray {
+ val len = s.length
+ require(len % 2 == 0) { "HexBinary string must be even length" }
+ val bytes = ByteArray(len / 2)
+ var i = 0
+
+ while (i < len) {
+ val h = hexToInt(s[i])
+ val l = hexToInt(s[i + 1])
+ require(!(h == -1 || l == -1)) { "Invalid hex chars: ${s[i]}${s[i+1]}" }
+
+ bytes[i / 2] = ((h shl 4) + l).toByte()
+ i += 2
+ }
+
+ return bytes
+ }
+
+ private fun hexToInt(ch: Char): Int = when (ch) {
+ in '0'..'9' -> ch - '0'
+ in 'A'..'F' -> ch - 'A' + 10
+ in 'a'..'f' -> ch - 'a' + 10
+ else -> -1
+ }
+
+ private const val hexCode = "0123456789ABCDEF"
+
+ fun printHexBinary(data: ByteArray, lowerCase: Boolean = false): String {
+ val r = StringBuilder(data.size * 2)
+ for (b in data) {
+ r.append(hexCode[b.toInt() shr 4 and 0xF])
+ r.append(hexCode[b.toInt() and 0xF])
+ }
+ return if (lowerCase) r.toString().toLowerCase() else r.toString()
+ }
+
+ fun toHexString(n: Int) = printHexBinary(ByteBuffer.allocate(4).putInt(n).flip().array(), true)
+ .trimStart('0').takeIf { it.isNotEmpty() } ?: "0"
+}
diff --git a/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/PolymorphicWithJvmClassTest.kt b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/PolymorphicWithJvmClassTest.kt
new file mode 100644
index 0000000..e592a76
--- /dev/null
+++ b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/PolymorphicWithJvmClassTest.kt
@@ -0,0 +1,45 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.*
+import kotlinx.serialization.modules.SerializersModule
+
+import org.junit.Test
+import java.text.*
+import java.util.*
+import kotlin.test.assertEquals
+
+class PolymorphicWithJvmClassTest {
+ @Serializable
+ data class DateWrapper(@SerialId(1) @Serializable(with = PolymorphicSerializer::class) val date: Date)
+
+ @Serializer(forClass = Date::class)
+ object DateSerializer : KSerializer<Date> {
+ override val descriptor: SerialDescriptor = PrimitiveDescriptor("java.util.Date", PrimitiveKind.STRING)
+
+ // Consider wrapping in ThreadLocal if serialization may happen in multiple threads
+ private val df: DateFormat = SimpleDateFormat("dd/MM/yyyy HH:mm:ss.SSS").apply {
+ timeZone = TimeZone.getTimeZone("GMT+2")
+ }
+
+ override fun serialize(encoder: Encoder, obj: Date) {
+ encoder.encodeString(df.format(obj))
+ }
+
+ override fun deserialize(decoder: Decoder): Date {
+ return df.parse(decoder.decodeString())
+ }
+ }
+
+ @Test
+ fun testPolymorphicWrappedOverride() {
+ val protobuf = ProtoBuf(context = SerializersModule { polymorphic(Date::class, DateSerializer) })
+ val obj = DateWrapper(Date())
+ val bytes = protobuf.dumps(obj)
+ val restored = protobuf.loads<DateWrapper>(bytes)
+ assertEquals(obj, restored)
+ }
+}
diff --git a/runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtoCompatibilityTest.kt b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtoCompatibilityTest.kt
similarity index 78%
rename from runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtoCompatibilityTest.kt
rename to formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtoCompatibilityTest.kt
index 37101d1..21de867 100644
--- a/runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtoCompatibilityTest.kt
+++ b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtoCompatibilityTest.kt
@@ -1,16 +1,18 @@
-package kotlinx.serialization.formats.protobuf
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
import kotlinx.serialization.*
-import kotlinx.serialization.formats.KTestData
-import kotlinx.serialization.formats.toHex
-import kotlinx.serialization.protobuf.ProtoBuf
import org.junit.Test
import kotlin.test.assertEquals
import kotlin.test.assertTrue
class ProtoCompatibilityTest {
+
@Test
- fun mapTest() {
+ fun testMap() {
val mapData = KTestData.KTestMap(mapOf("a" to "b", "c" to "d"), emptyMap())
val kxData = ProtoBuf.dump(mapData)
val kxHex = ProtoBuf.dumps(mapData)
diff --git a/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtobufEnumWithSerialIdTest.kt b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtobufEnumWithSerialIdTest.kt
new file mode 100644
index 0000000..152ba69
--- /dev/null
+++ b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/ProtobufEnumWithSerialIdTest.kt
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import kotlinx.serialization.Serializable
+import org.junit.*
+import kotlin.test.assertTrue
+
+class ProtobufEnumWithSerialIdTest {
+
+ @Serializable
+ enum class EnumWithIds(val id: Int) {
+ @SerialId(10)
+ FIRST(10),
+ @SerialId(20)
+ SECOND(20);
+ }
+
+ @Serializable
+ data class EnumHolder(@SerialId(5) val a: EnumWithIds) : IMessage {
+ override fun toProtobufMessage(): TestData.EnumHolder =
+ TestData.EnumHolder.newBuilder().setA(TestData.TestEnumWithIds.forNumber(a.id)).build()
+ }
+
+ @Test
+ fun testEnumsSupportSerialIds() {
+ assertTrue(readCompare(EnumHolder(EnumWithIds.SECOND)))
+ assertTrue(dumpCompare(EnumHolder(EnumWithIds.SECOND)))
+ }
+}
diff --git a/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/RandomTests.kt b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/RandomTests.kt
new file mode 100644
index 0000000..2d85c22
--- /dev/null
+++ b/formats/protobuf/jvmTest/src/kotlinx/serialization/protobuf/RandomTests.kt
@@ -0,0 +1,219 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization.protobuf
+
+import com.google.protobuf.GeneratedMessageV3
+import io.kotlintest.properties.Gen
+import io.kotlintest.properties.forAll
+import io.kotlintest.specs.ShouldSpec
+import kotlinx.serialization.Serializable
+import kotlinx.serialization.protobuf.TestData.*
+
+fun Gen<String>.generateNotEmpty() = nextPrintableString(Gen.choose(1, 100).generate())
+
+object KTestData {
+ @Serializable
+ data class KTestInt32(@SerialId(1) val a: Int) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestInt32.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestInt32> {
+ override fun generate(): KTestInt32 = KTestInt32(Gen.int().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestSignedInt(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Int) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedInt.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestSignedInt> {
+ override fun generate(): KTestSignedInt = KTestSignedInt(Gen.int().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestSignedLong(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Long) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedLong.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestSignedLong> {
+ override fun generate(): KTestSignedLong = KTestSignedLong(Gen.long().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestFixedInt(@SerialId(1) @ProtoType(ProtoNumberType.FIXED) val a: Int) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestFixedInt.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestFixedInt> {
+ override fun generate(): KTestFixedInt = KTestFixedInt(Gen.int().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestDouble(@SerialId(1) val a: Double) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestDouble.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestDouble> {
+ override fun generate(): KTestDouble = KTestDouble(Gen.double().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestBoolean(@SerialId(1) val a: Boolean) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestBoolean.newBuilder().setA(a).build()
+
+ companion object : Gen<KTestBoolean> {
+ override fun generate(): KTestBoolean = KTestBoolean(Gen.bool().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestAllTypes(
+ @SerialId(1) val i32: Int,
+ @SerialId(2) @ProtoType(ProtoNumberType.SIGNED) val si32: Int,
+ @SerialId(3) @ProtoType(ProtoNumberType.FIXED) val f32: Int,
+ @SerialId(10) val i64: Long,
+ @SerialId(11) @ProtoType(ProtoNumberType.SIGNED) val si64: Long,
+ @SerialId(12) @ProtoType(ProtoNumberType.FIXED) val f64: Long,
+ @SerialId(21) val f: Float,
+ @SerialId(22) val d: Double,
+ @SerialId(41) val b: Boolean = false,
+ @SerialId(51) val s: String
+ ) : IMessage {
+ override fun toProtobufMessage(): TestAllTypes = TestAllTypes.newBuilder()
+ .setI32(i32)
+ .setSi32(si32)
+ .setF32(f32)
+ .setI64(i64)
+ .setSi64(si64)
+ .setF64(f64)
+ .setF(f)
+ .setD(d)
+ .setB(b)
+ .setS(s)
+ .build()
+
+ companion object : Gen<KTestAllTypes> {
+ override fun generate(): KTestAllTypes = KTestAllTypes(
+ Gen.int().generate(),
+ Gen.int().generate(),
+ Gen.int().generate(),
+ Gen.long().generate(),
+ Gen.long().generate(),
+ Gen.long().generate(),
+ Gen.float().generate(),
+ Gen.double().generate(),
+ Gen.bool().generate(),
+ Gen.string().generateNotEmpty()
+ )
+ }
+ }
+
+ @Serializable
+ data class KTestOuterMessage(
+ @SerialId(1) val a: Int,
+ @SerialId(2) val b: Double,
+ @SerialId(10) val inner: KTestAllTypes,
+ @SerialId(20) val s: String
+ ) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestOuterMessage.newBuilder()
+ .setA(a)
+ .setB(b)
+ .setInner(inner.toProtobufMessage())
+ .setS(s)
+ .build()
+
+ companion object : Gen<KTestOuterMessage> {
+ override fun generate(): KTestOuterMessage = KTestOuterMessage(
+ Gen.int().generate(),
+ Gen.double().generate(),
+ KTestAllTypes.generate(),
+ Gen.string().generateNotEmpty()
+ )
+ }
+ }
+
+ @Serializable
+ data class KTestIntListMessage(
+ @SerialId(1) val s: Int,
+ @SerialId(10) val l: List<Int>
+ ) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedIntMessage.newBuilder().setS(s).addAllB(l).build()
+
+ companion object : Gen<KTestIntListMessage> {
+ override fun generate() = KTestIntListMessage(Gen.int().generate(), Gen.list(Gen.int()).generate())
+ }
+ }
+
+ @Serializable
+ data class KTestObjectListMessage(
+ @SerialId(1) val inner: List<KTestAllTypes>
+ ) : IMessage {
+ override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedObjectMessage.newBuilder().addAllInner(inner.map { it.toProtobufMessage() }).build()
+
+ companion object : Gen<KTestObjectListMessage> {
+ override fun generate() = KTestObjectListMessage(Gen.list(KTestAllTypes.Companion).generate())
+ }
+ }
+
+ enum class KCoffee { AMERICANO, LATTE, CAPPUCCINO }
+
+ @Serializable
+ data class KTestEnum(@SerialId(1) val a: KCoffee): IMessage {
+ override fun toProtobufMessage() = TestEnum.newBuilder().setA(TestEnum.Coffee.forNumber(a.ordinal)).build()
+
+ companion object : Gen<KTestEnum> {
+ override fun generate(): KTestEnum = KTestEnum(Gen.oneOf<KCoffee>().generate())
+ }
+ }
+
+ @Serializable
+ data class KTestMap(@SerialId(1) val s: Map<String, String>, @SerialId(2) val o: Map<Int, KTestAllTypes> = emptyMap()) :
+ IMessage {
+ override fun toProtobufMessage() = TestMap.newBuilder()
+ .putAllStringMap(s)
+ .putAllIntObjectMap(o.mapValues { it.value.toProtobufMessage() })
+ .build()
+
+ companion object : Gen<KTestMap> {
+ override fun generate(): KTestMap =
+ KTestMap(Gen.map(Gen.string(), Gen.string()).generate(), Gen.map(Gen.int(), KTestAllTypes).generate())
+ }
+ }
+}
+
+
+class RandomTest : ShouldSpec() {
+
+ init {
+ "Protobuf serialization" {
+ should("serialize random int32") { forAll(KTestData.KTestInt32.Companion) { dumpCompare(it) } }
+ should("serialize random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { dumpCompare(it) } }
+ should("serialize random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { dumpCompare(it) } }
+ should("serialize random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { dumpCompare(it) } }
+ should("serialize random doubles") { forAll(KTestData.KTestDouble.Companion) { dumpCompare(it) } }
+ should("serialize random booleans") { forAll(KTestData.KTestBoolean.Companion) { dumpCompare(it) } }
+ should("serialize random enums") { forAll(KTestData.KTestEnum.Companion) { dumpCompare(it) } }
+ should("serialize all base random types") { forAll(KTestData.KTestAllTypes.Companion) { dumpCompare(it) } }
+ should("serialize random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { dumpCompare(it) } }
+ should("serialize random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { dumpCompare(it) } }
+ should("serialize messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { dumpCompare(it) } }
+ should("serialize messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { dumpCompare(it) } }
+ }
+
+ "Protobuf deserialization" {
+ should("read random int32") { forAll(KTestData.KTestInt32.Companion) { readCompare(it) } }
+ should("read random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { readCompare(it) } }
+ should("read random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { readCompare(it) } }
+ should("read random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { readCompare(it) } }
+ should("read random doubles") { forAll(KTestData.KTestDouble.Companion) { readCompare(it) } }
+ should("read random enums") { forAll(KTestData.KTestEnum.Companion) { readCompare(it) } }
+ should("read all base random types") { forAll(KTestData.KTestAllTypes.Companion) { readCompare(it) } }
+ should("read random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { readCompare(it) } }
+ should("read random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { readCompare(it) } }
+ should("read random messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { readCompare(it) } }
+ should("read messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { readCompare(it) } }
+ }
+ }
+}
diff --git a/runtime/testProto/test_data.proto b/formats/protobuf/testProto/test_data.proto
similarity index 95%
rename from runtime/testProto/test_data.proto
rename to formats/protobuf/testProto/test_data.proto
index a0ba6ae..b9e3602 100644
--- a/runtime/testProto/test_data.proto
+++ b/formats/protobuf/testProto/test_data.proto
@@ -1,5 +1,5 @@
syntax = "proto2";
-option java_package = "kotlinx.serialization.formats.proto";
+option java_package = "kotlinx.serialization.protobuf";
message TestInt32 {
required int32 a = 1;
diff --git a/gradle/publishing.gradle b/gradle/publishing.gradle
index 5b12a23..030dc68 100644
--- a/gradle/publishing.gradle
+++ b/gradle/publishing.gradle
@@ -10,7 +10,7 @@
apply from: project.rootProject.file('gradle/mavenMetadata.gradle')
-def isMultiplatform = project.name == "kotlinx-serialization-runtime"
+def isMultiplatform = project.name == "kotlinx-serialization-runtime" || project.name == "kotlinx-serialization-protobuf"
task stubSources(type: Jar) {
classifier = 'sources'
diff --git a/runtime/build.gradle b/runtime/build.gradle
index 372f957..ec650bf 100644
--- a/runtime/build.gradle
+++ b/runtime/build.gradle
@@ -1,33 +1,16 @@
/*
* Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
*/
-apply plugin: 'java' // Needed for protobuf plugin only
apply plugin: 'kotlin-multiplatform'
apply plugin: 'kotlinx-serialization'
+apply from: rootProject.file("gradle/targets.gradle")
+apply from: rootProject.file("gradle/native_mpp.gradle")
ext {
jacksonVersion = '2.10.0.pr1'
}
-// Protobuf plugin used in tests
-
-apply plugin: 'com.google.protobuf'
-
-protobuf {
- protoc {
- // Download from repositories
- artifact = 'com.google.protobuf:protoc:3.0.0'
- }
-}
-
-clean {
- delete protobuf.generatedFilesBaseDir
-}
-
-apply from: rootProject.file("gradle/targets.gradle")
-apply from: rootProject.file("gradle/native_mpp.gradle")
-
kotlin {
targets {
fromPreset(presets.jvm, 'jvm') {
@@ -83,23 +66,15 @@
}
jvmTest {
- kotlin.srcDirs += file("${protobuf.generatedFilesBaseDir}/test/java")
-
dependencies {
api 'org.jetbrains.kotlin:kotlin-test-junit'
-
implementation 'io.kotlintest:kotlintest:2.0.7'
implementation 'com.google.guava:guava:24.1.1-jre'
-
- implementation 'com.google.protobuf:protobuf-java:3.0.0'
-
implementation group: 'com.fasterxml.jackson.core', name: 'jackson-core', version: jacksonVersion
implementation group: 'com.fasterxml.jackson.core', name: 'jackson-databind', version: jacksonVersion
implementation group: 'com.fasterxml.jackson.module', name: 'jackson-module-kotlin', version: jacksonVersion
implementation group: 'com.fasterxml.jackson.dataformat', name: 'jackson-dataformat-cbor', version: jacksonVersion
-
implementation group: 'com.google.code.gson', name: 'gson', version: '2.8.5'
-
implementation group: 'com.upokecenter', name: 'cbor', version: '4.0.0-beta1'
}
}
@@ -131,11 +106,3 @@
}
}
}
-
-sourceSets.test.proto {
- srcDirs = ['testProto']
-}
-
-compileTestKotlinJvm {
- dependsOn 'generateTestProto'
-}
diff --git a/runtime/commonMain/src/kotlinx/serialization/SerialFormat.kt b/runtime/commonMain/src/kotlinx/serialization/SerialFormat.kt
index 53fbb29..f53eb79 100644
--- a/runtime/commonMain/src/kotlinx/serialization/SerialFormat.kt
+++ b/runtime/commonMain/src/kotlinx/serialization/SerialFormat.kt
@@ -29,6 +29,7 @@
fun <T> load(deserializer: DeserializationStrategy<T>, bytes: ByteArray): T
}
+// TODO migrate
fun <T> BinaryFormat.dumps(serializer: SerializationStrategy<T>, obj: T): String =
HexConverter.printHexBinary(dump(serializer, obj), lowerCase = true)
diff --git a/runtime/commonMain/src/kotlinx/serialization/Shorthands.kt b/runtime/commonMain/src/kotlinx/serialization/Shorthands.kt
index 80592d9..ecb0c63 100644
--- a/runtime/commonMain/src/kotlinx/serialization/Shorthands.kt
+++ b/runtime/commonMain/src/kotlinx/serialization/Shorthands.kt
@@ -52,7 +52,7 @@
* Returns null if there are no annotations with such type.
* Throws [IllegalStateException] if there are duplicated annotations for a given type.
*/
-internal inline fun <reified A: Annotation> SerialDescriptor.findAnnotation(elementIndex: Int): A? {
+public inline fun <reified A: Annotation> SerialDescriptor.findAnnotation(elementIndex: Int): A? {
val candidates = getElementAnnotations(elementIndex).filterIsInstance<A>()
return when (candidates.size) {
0 -> null
diff --git a/runtime/commonMain/src/kotlinx/serialization/Tagged.kt b/runtime/commonMain/src/kotlinx/serialization/Tagged.kt
index 02444fc..32b7606 100644
--- a/runtime/commonMain/src/kotlinx/serialization/Tagged.kt
+++ b/runtime/commonMain/src/kotlinx/serialization/Tagged.kt
@@ -4,14 +4,9 @@
package kotlinx.serialization
-import kotlinx.serialization.CompositeDecoder.Companion.READ_ALL
import kotlinx.serialization.modules.EmptyModule
import kotlinx.serialization.modules.SerialModule
-@SerialInfo
-@Target(AnnotationTarget.PROPERTY)
-annotation class SerialId(val id: Int)
-
abstract class TaggedEncoder<Tag : Any?> : Encoder, CompositeEncoder {
/**
@@ -132,10 +127,6 @@
throw SerializationException("No tag in stack for requested element")
}
-abstract class IntTaggedEncoder : TaggedEncoder<Int?>() {
- final override fun SerialDescriptor.getTag(index: Int): Int? = getSerialId(this, index)
-}
-
abstract class NamedValueEncoder(val rootName: String = "") : TaggedEncoder<String>() {
final override fun SerialDescriptor.getTag(index: Int): String = nested(elementName(this, index))
@@ -144,9 +135,6 @@
open fun composeName(parentName: String, childName: String) = if (parentName.isEmpty()) childName else "$parentName.$childName"
}
-internal fun getSerialId(desc: SerialDescriptor, index: Int): Int?
- = desc.findAnnotation<SerialId>(index)?.id
-
abstract class TaggedDecoder<Tag : Any?> : Decoder, CompositeDecoder {
override val context: SerialModule
get() = EmptyModule
@@ -198,7 +186,6 @@
return this
}
-
final override fun decodeUnitElement(desc: SerialDescriptor, index: Int) = decodeTaggedUnit(desc.getTag(index))
final override fun decodeBooleanElement(desc: SerialDescriptor, index: Int): Boolean = decodeTaggedBoolean(desc.getTag(index))
final override fun decodeByteElement(desc: SerialDescriptor, index: Int): Byte = decodeTaggedByte(desc.getTag(index))
@@ -255,10 +242,6 @@
}
}
-abstract class IntTaggedDecoder: TaggedDecoder<Int?>() {
- final override fun SerialDescriptor.getTag(index: Int): Int? = getSerialId(this, index)
-}
-
abstract class NamedValueDecoder(val rootName: String = "") : TaggedDecoder<String>() {
final override fun SerialDescriptor.getTag(index: Int): String = nested(elementName(this, index))
diff --git a/runtime/commonMain/src/kotlinx/serialization/internal/Tuples.kt b/runtime/commonMain/src/kotlinx/serialization/internal/Tuples.kt
index 61960be..8012765 100644
--- a/runtime/commonMain/src/kotlinx/serialization/internal/Tuples.kt
+++ b/runtime/commonMain/src/kotlinx/serialization/internal/Tuples.kt
@@ -8,7 +8,7 @@
private val NULL = Any()
-internal sealed class KeyValueSerializer<K, V, R>(
+public sealed class KeyValueSerializer<K, V, R>(
private val keySerializer: KSerializer<K>,
private val valueSerializer: KSerializer<V>
) : KSerializer<R> {
@@ -57,7 +57,7 @@
}
@Suppress("EXTENSION_SHADOWED_BY_MEMBER")
-internal class MapEntrySerializer<K, V>(
+public class MapEntrySerializer<K, V>(
keySerializer: KSerializer<K>,
valueSerializer: KSerializer<V>
) : KeyValueSerializer<K, V, Map.Entry<K, V>>(keySerializer, valueSerializer) {
diff --git a/runtime/commonMain/src/kotlinx/serialization/internal/Util.kt b/runtime/commonMain/src/kotlinx/serialization/internal/Util.kt
index f3a9193..6a10940 100644
--- a/runtime/commonMain/src/kotlinx/serialization/internal/Util.kt
+++ b/runtime/commonMain/src/kotlinx/serialization/internal/Util.kt
@@ -8,7 +8,7 @@
import kotlinx.io.IOException
import kotlinx.io.InputStream
-internal fun InputStream.readExactNBytes(bytes: Int): ByteArray {
+public fun InputStream.readExactNBytes(bytes: Int): ByteArray {
val array = ByteArray(bytes)
var read = 0
while (read < bytes) {
@@ -19,7 +19,7 @@
return array
}
-internal fun InputStream.readToByteBuffer(bytes: Int): ByteBuffer {
+public fun InputStream.readToByteBuffer(bytes: Int): ByteBuffer {
val arr = readExactNBytes(bytes)
val buf = ByteBuffer.allocate(bytes)
buf.put(arr).flip()
diff --git a/runtime/commonTest/src/kotlinx/serialization/EnumSerializationTest.kt b/runtime/commonTest/src/kotlinx/serialization/EnumSerializationTest.kt
index 522ce8c..7002232 100644
--- a/runtime/commonTest/src/kotlinx/serialization/EnumSerializationTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/EnumSerializationTest.kt
@@ -16,7 +16,7 @@
@SerialName("foo_a")
FooA,
@SerialName("foo_b")
- @SerialId(10)
+ @Id(10)
FooB
}
diff --git a/runtime/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt b/runtime/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt
index 4250143..5180ac6 100644
--- a/runtime/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/PolymorphismTestData.kt
@@ -7,7 +7,7 @@
import kotlinx.serialization.modules.SerializersModule
@Serializable
-open class PolyBase(@SerialId(1) val id: Int) {
+open class PolyBase(@Id(1) val id: Int) {
override fun hashCode(): Int {
return id
}
@@ -30,7 +30,7 @@
}
@Serializable
-data class PolyDerived(@SerialId(2) val s: String) : PolyBase(1)
+data class PolyDerived(@Id(2) val s: String) : PolyBase(1)
val BaseAndDerivedModule = SerializersModule {
polymorphic(PolyBase::class, PolyBase.serializer()) {
diff --git a/runtime/commonTest/src/kotlinx/serialization/SerialDescriptorSpecificationTest.kt b/runtime/commonTest/src/kotlinx/serialization/SerialDescriptorSpecificationTest.kt
index 4e2ee2e..03e7f19 100644
--- a/runtime/commonTest/src/kotlinx/serialization/SerialDescriptorSpecificationTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/SerialDescriptorSpecificationTest.kt
@@ -6,13 +6,13 @@
import kotlinx.serialization.CompositeDecoder.Companion.UNKNOWN_NAME
import kotlinx.serialization.internal.*
-import kotlinx.serialization.test.*
+
import kotlin.test.*
class SerialDescriptorSpecificationTest {
@Serializable
- class Holder(val a: Int?, @SerialId(42) val b: String = "", @SerialName("c") val d: Long)
+ class Holder(val a: Int?, @Id(42) val b: String = "", @SerialName("c") val d: Long)
@Test
fun testAutoGeneratedDescriptorContract() {
@@ -34,7 +34,7 @@
addElement("b", true)
pushDescriptor(StringSerializer.descriptor)
// Can't create an annotation manually
- pushAnnotation(Holder.serializer().descriptor.findAnnotation<SerialId>(1)!!)
+ pushAnnotation(Holder.serializer().descriptor.findAnnotation<Id>(1)!!)
addElement("c")
pushDescriptor(LongSerializer.descriptor)
@@ -60,7 +60,7 @@
// Children annotations
run {
assertEquals(0, d.getElementAnnotations(0).size)
- d.assertSingleAnnotation(1) { it is SerialId && it.id == 42 }
+ d.assertSingleAnnotation(1) { it is Id && it.id == 42 }
assertEquals(0, d.getElementAnnotations(2).size)
}
// Optionality
@@ -95,7 +95,7 @@
@Serializable
@Suppress("UNUSED")
enum class NamedEnum {
- @SerialId(42)
+ @Id(42)
FIRST,
@SerialName("SECOND")
THIRD
@@ -117,7 +117,7 @@
assertEquals("SECOND", d.getElementName(1))
assertFailsWith<IndexOutOfBoundsException> { d.getElementName(2) }
// Annotations
- d.assertSingleAnnotation(0) { it is SerialId && it.id == 42 }
+ d.assertSingleAnnotation(0) { it is Id && it.id == 42 }
assertEquals(0, d.getElementAnnotations(1).size)
// Element descriptors
assertSame(d, d.getElementDescriptor(0))
diff --git a/runtime/commonTest/src/kotlinx/serialization/TaggedTest.kt b/runtime/commonTest/src/kotlinx/serialization/TaggedTest.kt
index 3a9df6a..25597f9 100644
--- a/runtime/commonTest/src/kotlinx/serialization/TaggedTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/TaggedTest.kt
@@ -14,22 +14,25 @@
@Serializable
data class DataWithId(
- @SerialId(1) val first: Int,
- @SerialId(2) val second: String,
+ @Id(1) val first: Int,
+ @Id(2) val second: String,
val noId: Unit = Unit,
- @SerialId(42) val last: Boolean = true
+ @Id(42) val last: Boolean = true
)
- class Collector : IntTaggedEncoder() {
+ class Collector : TaggedEncoder<Int?>() {
+ override fun SerialDescriptor.getTag(index: Int): Int? = getSerialId(this, index)
val tagList = mutableMapOf<Int?, Any>()
override fun encodeTaggedValue(tag: Int?, value: Any) {
tagList[tag] = value
}
}
- class Emitter(val collected: Collector) : IntTaggedDecoder() {
+ class Emitter(val collected: Collector) : TaggedDecoder<Int?>() {
private var i = 0
+
override fun decodeSequentially(): Boolean = true
+ override fun SerialDescriptor.getTag(index: Int): Int? = getSerialId(this, index)
override fun decodeElementIndex(desc: SerialDescriptor): Int {
// js doesn't generate code for .decodeSequentially for the sake of keeping output small
diff --git a/runtime/commonTest/src/kotlinx/serialization/TestId.kt b/runtime/commonTest/src/kotlinx/serialization/TestId.kt
new file mode 100644
index 0000000..2d3d1c5
--- /dev/null
+++ b/runtime/commonTest/src/kotlinx/serialization/TestId.kt
@@ -0,0 +1,12 @@
+/*
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
+ */
+
+package kotlinx.serialization
+
+@SerialInfo
+@Target(AnnotationTarget.PROPERTY)
+annotation class Id(val id: Int)
+
+public fun getSerialId(desc: SerialDescriptor, index: Int): Int?
+ = desc.findAnnotation<Id>(index)?.id
diff --git a/runtime/commonTest/src/kotlinx/serialization/features/ByteArraySerializerTest.kt b/runtime/commonTest/src/kotlinx/serialization/features/ByteArraySerializerTest.kt
index e7488aa..4119356 100644
--- a/runtime/commonTest/src/kotlinx/serialization/features/ByteArraySerializerTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/features/ByteArraySerializerTest.kt
@@ -7,35 +7,35 @@
import kotlinx.serialization.*
import kotlinx.serialization.internal.ByteArraySerializer
import kotlinx.serialization.json.Json
-import kotlinx.serialization.protobuf.ProtoBuf
import kotlin.random.Random
import kotlin.test.*
-@Serializable
-class ByteArrayCarrier(@SerialId(2) @Serializable(with = ByteArraySerializer::class) val data: ByteArray) {
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other == null || this::class != other::class) return false
-
- other as ByteArrayCarrier
-
- if (!data.contentEquals(other.data)) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- return data.contentHashCode()
- }
-
- override fun toString(): String {
- return "ByteArrayCarrier(data=${data.contentToString()})"
- }
-}
-
class ByteArraySerializerTest {
+
+ @Serializable
+ class ByteArrayCarrier(@Id(2) @Serializable(with = ByteArraySerializer::class) val data: ByteArray) {
+ override fun equals(other: Any?): Boolean {
+ if (this === other) return true
+ if (other == null || this::class != other::class) return false
+
+ other as ByteArrayCarrier
+
+ if (!data.contentEquals(other.data)) return false
+
+ return true
+ }
+
+ override fun hashCode(): Int {
+ return data.contentHashCode()
+ }
+
+ override fun toString(): String {
+ return "ByteArrayCarrier(data=${data.contentToString()})"
+ }
+ }
+
@Test
- fun plain() {
+ fun testByteArrayJson() {
val bytes = byteArrayOf(42, 43, 44, 45)
val s = Json.stringify(ByteArraySerializer, bytes)
assertEquals(s, """[42,43,44,45]""")
@@ -44,30 +44,11 @@
}
@Test
- fun inObject() {
+ fun testWrappedByteArrayJson() {
val obj = ByteArrayCarrier(byteArrayOf(42, 100))
val s = Json.stringify(ByteArrayCarrier.serializer(), obj)
assertEquals("""{"data":[42,100]}""", s)
val obj2 = Json.parse(ByteArrayCarrier.serializer(), s)
assertEquals(obj, obj2)
}
-
- @Test
- fun inProto() {
- val obj = ByteArrayCarrier(byteArrayOf(42, 100))
- val s = ProtoBuf.dumps(ByteArrayCarrier.serializer(), obj)
- assertEquals("""12022a64""", s)
- val obj2 = ProtoBuf.loads(ByteArrayCarrier.serializer(), s)
- assertEquals(obj, obj2)
- }
-
- @Test
- fun serializeAndDeserializeLongArrays() {
- val arraySize = 301
- val arr = Random.nextBytes(ByteArray(arraySize))
- val obj = ByteArrayCarrier(arr)
- val bytes = ProtoBuf.dump(ByteArrayCarrier.serializer(), obj)
- assertEquals(obj, ProtoBuf.load(ByteArrayCarrier.serializer(), bytes))
- }
-
}
diff --git a/runtime/commonTest/src/kotlinx/serialization/features/PolymorphismTest.kt b/runtime/commonTest/src/kotlinx/serialization/features/PolymorphismTest.kt
index cec5c4c..05fc183 100644
--- a/runtime/commonTest/src/kotlinx/serialization/features/PolymorphismTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/features/PolymorphismTest.kt
@@ -7,15 +7,14 @@
import kotlinx.serialization.*
import kotlinx.serialization.json.Json
import kotlinx.serialization.modules.*
-import kotlinx.serialization.protobuf.ProtoBuf
import kotlin.test.*
class PolymorphismTest {
@Serializable
data class Wrapper(
- @SerialId(1) @Polymorphic val polyBase1: PolyBase,
- @SerialId(2) @Polymorphic val polyBase2: PolyBase
+ @Id(1) @Polymorphic val polyBase1: PolyBase,
+ @Id(2) @Polymorphic val polyBase2: PolyBase
)
private val module: SerialModule = BaseAndDerivedModule + SerializersModule {
@@ -26,7 +25,7 @@
}
private val json = Json { unquoted = true; useArrayPolymorphism = true; serialModule = module }
- private val protobuf = ProtoBuf(context = module)
+// private val protobuf = ProtoBuf(context = module)
@Test
fun testInheritanceJson() {
@@ -41,16 +40,16 @@
)
}
- @Test
- fun testInheritanceProtobuf() {
- val obj = Wrapper(
- PolyBase(2),
- PolyDerived("b")
- )
- val bytes = protobuf.dumps(Wrapper.serializer(), obj)
- val restored = protobuf.loads(Wrapper.serializer(), bytes)
- assertEquals(obj, restored)
- }
+// @Test
+// fun testInheritanceProtobuf() {
+// val obj = Wrapper(
+// PolyBase(2),
+// PolyDerived("b")
+// )
+// val bytes = protobuf.dumps(Wrapper.serializer(), obj)
+// val restored = protobuf.loads(Wrapper.serializer(), bytes)
+// assertEquals(obj, restored)
+// }
@Test
fun testSerializeWithExplicitPolymorhpicSerializer() {
diff --git a/runtime/commonTest/src/kotlinx/serialization/json/JsonCustomSerializersTest.kt b/runtime/commonTest/src/kotlinx/serialization/json/JsonCustomSerializersTest.kt
index 683a5c0..cc5b62b 100644
--- a/runtime/commonTest/src/kotlinx/serialization/json/JsonCustomSerializersTest.kt
+++ b/runtime/commonTest/src/kotlinx/serialization/json/JsonCustomSerializersTest.kt
@@ -15,9 +15,9 @@
class JsonCustomSerializersTest : JsonTestBase() {
@Serializable
- data class A(@SerialId(1) val b: B)
+ data class A(@Id(1) val b: B)
- data class B(@SerialId(1) val value: Int)
+ data class B(@Id(1) val value: Int)
object BSerializer : KSerializer<B> {
override fun serialize(encoder: Encoder, obj: B) {
@@ -35,10 +35,10 @@
}
@Serializable
- data class BList(@SerialId(1) val bs: List<B>)
+ data class BList(@Id(1) val bs: List<B>)
@Serializable
- data class C(@SerialId(1) val a: Int = 31, @SerialId(2) val b: Int = 42) {
+ data class C(@Id(1) val a: Int = 31, @Id(2) val b: Int = 42) {
@Serializer(forClass = C::class)
companion object: KSerializer<C> {
override fun serialize(encoder: Encoder, obj: C) {
@@ -51,10 +51,10 @@
}
@Serializable
- data class CList1(@SerialId(1) val c: List<C>)
+ data class CList1(@Id(1) val c: List<C>)
@Serializable
- data class CList2(@SerialId(1) val d: Int = 5, @SerialId(2) val c: List<C>) {
+ data class CList2(@Id(1) val d: Int = 5, @Id(2) val c: List<C>) {
@Serializer(forClass = CList2::class)
companion object: KSerializer<CList2> {
override fun serialize(encoder: Encoder, obj: CList2) {
@@ -67,7 +67,7 @@
}
@Serializable
- data class CList3(@SerialId(1) val e: List<C> = emptyList(), @SerialId(2) val f: Int) {
+ data class CList3(@Id(1) val e: List<C> = emptyList(), @Id(2) val f: Int) {
@Serializer(forClass = CList3::class)
companion object: KSerializer<CList3> {
override fun serialize(encoder: Encoder, obj: CList3) {
@@ -80,7 +80,7 @@
}
@Serializable
- data class CList4(@SerialId(1) val g: List<C> = emptyList(), @SerialId(2) val h: Int) {
+ data class CList4(@Id(1) val g: List<C> = emptyList(), @Id(2) val h: Int) {
@Serializer(forClass = CList4::class)
companion object: KSerializer<CList4> {
override fun serialize(encoder: Encoder, obj: CList4) {
@@ -93,7 +93,7 @@
}
@Serializable
- data class CList5(@SerialId(1) val g: List<Int> = emptyList(), @SerialId(2) val h: Int) {
+ data class CList5(@Id(1) val g: List<Int> = emptyList(), @Id(2) val h: Int) {
@Serializer(forClass = CList5::class)
companion object: KSerializer<CList5> {
override fun serialize(encoder: Encoder, obj: CList5) {
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufReaderTest.kt b/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufReaderTest.kt
deleted file mode 100644
index 0527110..0000000
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufReaderTest.kt
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
- */
-
-package kotlinx.serialization.protobuf
-
-import kotlinx.serialization.loads
-import kotlinx.serialization.test.isNative
-import kotlinx.serialization.test.shouldBe
-import kotlin.test.Ignore
-import kotlin.test.Test
-
-class ProtobufReaderTest {
-
- @Test
- fun readSimpleObject() {
- ProtoBuf.loads(TestInt.serializer(), "08ab02") shouldBe t1
- }
-
- @Test
- fun readObjectWithString() {
- ProtoBuf.loads(TestString.serializer(), "120774657374696E67") shouldBe t3
- }
-
- @Test
- fun readObjectWithList() {
- ProtoBuf.loads(TestList.serializer(), "08960108E40108B90A") shouldBe t2
- }
-
- @Test
- fun readInnerObject() {
- ProtoBuf.loads(TestInner.serializer(), "1a0308ab02") shouldBe t4
- }
-
- @Test
- fun readObjectWithUnorderedTags() {
- ProtoBuf.loads(TestComplex.serializer(), "120774657374696E67D0022A") shouldBe t5
- }
-
- @Test
- fun readObjectsWithEmptyValues() {
- ProtoBuf.loads(TestInt.serializer(), "0800") shouldBe t1e
- ProtoBuf.loads(TestList.serializer(), "") shouldBe t2e
- ProtoBuf.loads(TestString.serializer(), "1200") shouldBe t3e
- }
-
- @Test
- fun readObjectWithUnknownFields() {
- ProtoBuf.loads(TestInt.serializer(), "08960108E40108B90A08ab02120774657374696E67") shouldBe t1
- }
-
- @Test
- fun readNumbers() {
- ProtoBuf.loads(TestNumbers.serializer(), "0d9488010010ffffffffffffffff7f") shouldBe t6
- }
-
- @Test
- fun mergeListIfSplitByAnotherField() {
- if (isNative()) return // todo: support update on Native
- ProtoBuf.loads(TestIntWithList.serializer(), "500308960150045005") shouldBe TestIntWithList(150, listOf(3, 4, 5))
- }
-}
diff --git a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufWriterTest.kt b/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufWriterTest.kt
deleted file mode 100644
index 45a1674..0000000
--- a/runtime/commonTest/src/kotlinx/serialization/protobuf/ProtobufWriterTest.kt
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2017 JetBrains s.r.o.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package kotlinx.serialization.protobuf
-
-import kotlinx.serialization.dumps
-import kotlinx.serialization.test.shouldBe
-import kotlin.test.Test
-
-class ProtobufWriterTest {
-
- @Test
- fun writeSignedInteger() {
- ProtoBuf.dumps(TestInt.serializer(), t1).toLowerCase() shouldBe "08ab02"
- }
-
- @Test
- fun writeListOfVarintIntegers() {
- ProtoBuf.dumps(TestList.serializer(), t2).toUpperCase() shouldBe "08960108E40108B90A"
- }
-
- @Test
- fun writeString() {
- ProtoBuf.dumps(TestString.serializer(), t3).toUpperCase() shouldBe "120774657374696E67"
- }
-
- @Test
- fun writeInnerObject() {
- ProtoBuf.dumps(TestInner.serializer(), t4).toLowerCase() shouldBe "1a0308ab02"
- }
-
- @Test
- fun writeObjectWithUnorderedTags() {
- ProtoBuf.dumps(TestComplex.serializer(), t5).toUpperCase() shouldBe "D0022A120774657374696E67"
- }
-
- @Test
- fun writeObjectsWithEmptyDefaultValues() {
- ProtoBuf.dumps(TestInt.serializer(), t1e) shouldBe "0800"
- ProtoBuf.dumps(TestList.serializer(), t2e) shouldBe ""
- ProtoBuf.dumps(TestString.serializer(), t3e) shouldBe "1200"
- }
-
- @Test
- fun writeNumbers() {
- ProtoBuf.dumps(TestNumbers.serializer(), t6).toLowerCase() shouldBe "0d9488010010ffffffffffffffff7f"
- }
-}
diff --git a/runtime/jvmTest/src/kotlinx/serialization/features/PolymorphicWithJvmClassTest.kt b/runtime/jvmTest/src/kotlinx/serialization/features/PolymorphicWithJvmClassTest.kt
deleted file mode 100644
index f21ea24..0000000
--- a/runtime/jvmTest/src/kotlinx/serialization/features/PolymorphicWithJvmClassTest.kt
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2018 JetBrains s.r.o.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package kotlinx.serialization.features
-
-import kotlinx.serialization.*
-import kotlinx.serialization.modules.SerializersModule
-import kotlinx.serialization.protobuf.ProtoBuf
-import org.junit.Test
-import java.util.*
-import kotlin.test.assertEquals
-
-class PolymorphicWithJvmClassTest {
- @Serializable
- data class DateWrapper(@SerialId(1) @Serializable(with = PolymorphicSerializer::class) val date: Date)
-
- @Test
- fun testPolymorphicWrappedOverride() {
- val protobuf = ProtoBuf(context = SerializersModule { polymorphic(Date::class, DateSerializer) })
- val obj = DateWrapper(Date())
- val bytes = protobuf.dumps(obj)
- val restored = protobuf.loads<DateWrapper>(bytes)
- assertEquals(obj, restored)
- }
-}
diff --git a/runtime/jvmTest/src/kotlinx/serialization/formats/FormatConverterHelpers.kt b/runtime/jvmTest/src/kotlinx/serialization/formats/FormatConverterHelpers.kt
deleted file mode 100644
index edab409..0000000
--- a/runtime/jvmTest/src/kotlinx/serialization/formats/FormatConverterHelpers.kt
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
- */
-
-package kotlinx.serialization.formats
-
-import com.fasterxml.jackson.databind.ObjectMapper
-import com.fasterxml.jackson.dataformat.cbor.CBORFactory
-import com.fasterxml.jackson.module.kotlin.readValue
-import com.fasterxml.jackson.module.kotlin.registerKotlinModule
-import com.google.protobuf.GeneratedMessageV3
-import kotlinx.serialization.*
-import kotlinx.serialization.cbor.Cbor
-import kotlinx.serialization.internal.HexConverter
-import kotlinx.serialization.protobuf.ProtoBuf
-import java.io.ByteArrayOutputStream
-
-interface IMessage {
- fun toProtobufMessage(): GeneratedMessageV3
-}
-
-fun GeneratedMessageV3.toHex(): String {
- val b = ByteArrayOutputStream()
- this.writeTo(b)
- return (HexConverter.printHexBinary(b.toByteArray(), lowerCase = true))
-}
-
-inline fun <reified T : IMessage> dumpCompare(it: T, alwaysPrint: Boolean = false): Boolean {
- val msg = it.toProtobufMessage()
- var parsed: GeneratedMessageV3?
- val c = try {
- val bytes = ProtoBuf.dump(it)
- if (alwaysPrint) println("Serialized bytes: ${HexConverter.printHexBinary(bytes)}")
- parsed = msg.parserForType.parseFrom(bytes)
- msg == parsed
- } catch (e: Exception) {
- e.printStackTrace()
- parsed = null
- false
- }
- if (!c || alwaysPrint) println("Expected: $msg\nfound: $parsed")
- return c
-}
-
-inline fun <reified T : IMessage> readCompare(it: T, alwaysPrint: Boolean = false): Boolean {
- var obj: T?
- val c = try {
- val msg = it.toProtobufMessage()
- val hex = msg.toHex()
- obj = ProtoBuf.loads<T>(hex)
- obj == it
- } catch (e: Exception) {
- obj = null
- e.printStackTrace()
- false
- }
- if (!c || alwaysPrint) println("Expected: $it\nfound: $obj")
- return c
-}
-
-internal val cborJackson = ObjectMapper(CBORFactory()).apply { registerKotlinModule() }
-
-internal inline fun <reified T : IMessage> dumpCborCompare(it: T, alwaysPrint: Boolean = false): Boolean {
- var parsed: T?
- val c = try {
- val bytes = Cbor.dump(it)
- parsed = cborJackson.readValue<T>(bytes)
- it == parsed
- } catch (e: Exception) {
- e.printStackTrace()
- parsed = null
- false
- }
- if (!c || alwaysPrint) println("Expected: $it\nfound: $parsed")
- return c
-}
-
-internal inline fun <reified T : IMessage> readCborCompare(it: T, alwaysPrint: Boolean = false): Boolean {
- var obj: T?
- val c = try {
- val hex = cborJackson.writeValueAsBytes(it)
- obj = Cbor.load<T>(hex)
- obj == it
- } catch (e: Exception) {
- obj = null
- e.printStackTrace()
- false
- }
- if (!c || alwaysPrint) println("Expected: $it\nfound: $obj")
- return c
-}
diff --git a/runtime/jvmTest/src/kotlinx/serialization/formats/RandomTests.kt b/runtime/jvmTest/src/kotlinx/serialization/formats/RandomTests.kt
index 7135186..7e35c7d 100644
--- a/runtime/jvmTest/src/kotlinx/serialization/formats/RandomTests.kt
+++ b/runtime/jvmTest/src/kotlinx/serialization/formats/RandomTests.kt
@@ -2,249 +2,247 @@
* Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
*/
-package kotlinx.serialization.formats
-
-import com.google.protobuf.GeneratedMessageV3
-import io.kotlintest.properties.Gen
-import io.kotlintest.properties.forAll
-import io.kotlintest.specs.ShouldSpec
-import kotlinx.serialization.SerialId
-import kotlinx.serialization.Serializable
-import kotlinx.serialization.formats.proto.TestData.*
-import kotlinx.serialization.protobuf.ProtoNumberType
-import kotlinx.serialization.protobuf.ProtoType
-
-fun Gen<String>.generateNotEmpty() = nextPrintableString(Gen.choose(1, 100).generate())
-
-object KTestData {
- @Serializable
- data class KTestInt32(@SerialId(1) val a: Int) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestInt32.newBuilder().setA(a).build()
-
- companion object : Gen<KTestInt32> {
- override fun generate(): KTestInt32 = KTestInt32(Gen.int().generate())
- }
- }
-
- @Serializable
- data class KTestSignedInt(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Int) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedInt.newBuilder().setA(a).build()
-
- companion object : Gen<KTestSignedInt> {
- override fun generate(): KTestSignedInt = KTestSignedInt(Gen.int().generate())
- }
- }
-
- @Serializable
- data class KTestSignedLong(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Long) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedLong.newBuilder().setA(a).build()
-
- companion object : Gen<KTestSignedLong> {
- override fun generate(): KTestSignedLong = KTestSignedLong(Gen.long().generate())
- }
- }
-
- @Serializable
- data class KTestFixedInt(@SerialId(1) @ProtoType(ProtoNumberType.FIXED) val a: Int) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestFixedInt.newBuilder().setA(a).build()
-
- companion object : Gen<KTestFixedInt> {
- override fun generate(): KTestFixedInt = KTestFixedInt(Gen.int().generate())
- }
- }
-
- @Serializable
- data class KTestDouble(@SerialId(1) val a: Double) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestDouble.newBuilder().setA(a).build()
-
- companion object : Gen<KTestDouble> {
- override fun generate(): KTestDouble = KTestDouble(Gen.double().generate())
- }
- }
-
- @Serializable
- data class KTestBoolean(@SerialId(1) val a: Boolean) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestBoolean.newBuilder().setA(a).build()
-
- companion object : Gen<KTestBoolean> {
- override fun generate(): KTestBoolean = KTestBoolean(Gen.bool().generate())
- }
- }
-
- @Serializable
- data class KTestAllTypes(
- @SerialId(1) val i32: Int,
- @SerialId(2) @ProtoType(ProtoNumberType.SIGNED) val si32: Int,
- @SerialId(3) @ProtoType(ProtoNumberType.FIXED) val f32: Int,
- @SerialId(10) val i64: Long,
- @SerialId(11) @ProtoType(ProtoNumberType.SIGNED) val si64: Long,
- @SerialId(12) @ProtoType(ProtoNumberType.FIXED) val f64: Long,
- @SerialId(21) val f: Float,
- @SerialId(22) val d: Double,
- @SerialId(41) val b: Boolean = false,
- @SerialId(51) val s: String
- ) : IMessage {
- override fun toProtobufMessage(): TestAllTypes = TestAllTypes.newBuilder()
- .setI32(i32)
- .setSi32(si32)
- .setF32(f32)
- .setI64(i64)
- .setSi64(si64)
- .setF64(f64)
- .setF(f)
- .setD(d)
- .setB(b)
- .setS(s)
- .build()
-
- companion object : Gen<KTestAllTypes> {
- override fun generate(): KTestAllTypes = KTestAllTypes(
- Gen.int().generate(),
- Gen.int().generate(),
- Gen.int().generate(),
- Gen.long().generate(),
- Gen.long().generate(),
- Gen.long().generate(),
- Gen.float().generate(),
- Gen.double().generate(),
- Gen.bool().generate(),
- Gen.string().generateNotEmpty()
- )
- }
- }
-
- @Serializable
- data class KTestOuterMessage(
- @SerialId(1) val a: Int,
- @SerialId(2) val b: Double,
- @SerialId(10) val inner: KTestAllTypes,
- @SerialId(20) val s: String
- ) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestOuterMessage.newBuilder()
- .setA(a)
- .setB(b)
- .setInner(inner.toProtobufMessage())
- .setS(s)
- .build()
-
- companion object : Gen<KTestOuterMessage> {
- override fun generate(): KTestOuterMessage = KTestOuterMessage(
- Gen.int().generate(),
- Gen.double().generate(),
- KTestAllTypes.generate(),
- Gen.string().generateNotEmpty()
- )
- }
- }
-
- @Serializable
- data class KTestIntListMessage(
- @SerialId(1) val s: Int,
- @SerialId(10) val l: List<Int>
- ) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedIntMessage.newBuilder().setS(s).addAllB(l).build()
-
- companion object : Gen<KTestIntListMessage> {
- override fun generate() = KTestIntListMessage(Gen.int().generate(), Gen.list(Gen.int()).generate())
- }
- }
-
- @Serializable
- data class KTestObjectListMessage(
- @SerialId(1) val inner: List<KTestAllTypes>
- ) : IMessage {
- override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedObjectMessage.newBuilder().addAllInner(inner.map { it.toProtobufMessage() }).build()
-
- companion object : Gen<KTestObjectListMessage> {
- override fun generate() = KTestObjectListMessage(Gen.list(KTestAllTypes.Companion).generate())
- }
- }
-
- enum class KCoffee { AMERICANO, LATTE, CAPPUCCINO }
-
- @Serializable
- data class KTestEnum(@SerialId(1) val a: KCoffee): IMessage {
- override fun toProtobufMessage() = TestEnum.newBuilder().setA(TestEnum.Coffee.forNumber(a.ordinal)).build()
-
- companion object : Gen<KTestEnum> {
- override fun generate(): KTestEnum = KTestEnum(Gen.oneOf<KCoffee>().generate())
- }
- }
-
- @Serializable
- data class KTestMap(@SerialId(1) val s: Map<String, String>, @SerialId(2) val o: Map<Int, KTestAllTypes> = emptyMap()) :
- IMessage {
- override fun toProtobufMessage() = TestMap.newBuilder()
- .putAllStringMap(s)
- .putAllIntObjectMap(o.mapValues { it.value.toProtobufMessage() })
- .build()
-
- companion object : Gen<KTestMap> {
- override fun generate(): KTestMap =
- KTestMap(Gen.map(Gen.string(), Gen.string()).generate(), Gen.map(Gen.int(), KTestAllTypes).generate())
- }
- }
-}
-
-
-class RandomTest : ShouldSpec() {
-
- init {
- "Protobuf serialization" {
- should("serialize random int32") { forAll(KTestData.KTestInt32.Companion) { dumpCompare(it) } }
- should("serialize random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { dumpCompare(it) } }
- should("serialize random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { dumpCompare(it) } }
- should("serialize random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { dumpCompare(it) } }
- should("serialize random doubles") { forAll(KTestData.KTestDouble.Companion) { dumpCompare(it) } }
- should("serialize random booleans") { forAll(KTestData.KTestBoolean.Companion) { dumpCompare(it) } }
- should("serialize random enums") { forAll(KTestData.KTestEnum.Companion) { dumpCompare(it) } }
- should("serialize all base random types") { forAll(KTestData.KTestAllTypes.Companion) { dumpCompare(it) } }
- should("serialize random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { dumpCompare(it) } }
- should("serialize random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { dumpCompare(it) } }
- should("serialize messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { dumpCompare(it) } }
- should("serialize messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { dumpCompare(it) } }
- }
-
- "Protobuf deserialization" {
- should("read random int32") { forAll(KTestData.KTestInt32.Companion) { readCompare(it) } }
- should("read random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { readCompare(it) } }
- should("read random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { readCompare(it) } }
- should("read random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { readCompare(it) } }
- should("read random doubles") { forAll(KTestData.KTestDouble.Companion) { readCompare(it) } }
- should("read random enums") { forAll(KTestData.KTestEnum.Companion) { readCompare(it) } }
- should("read all base random types") { forAll(KTestData.KTestAllTypes.Companion) { readCompare(it) } }
- should("read random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { readCompare(it) } }
- should("read random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { readCompare(it) } }
- should("read random messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { readCompare(it) } }
- should("read messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { readCompare(it) } }
- }
-
- "CBOR Writer" {
- should("serialize random int32") { forAll(KTestData.KTestInt32.Companion) { dumpCborCompare(it) } }
- should("serialize random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { dumpCborCompare(it) } }
- should("serialize random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { dumpCborCompare(it) } }
- should("serialize random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { dumpCborCompare(it) } }
- should("serialize random doubles") { forAll(KTestData.KTestDouble.Companion) { dumpCborCompare(it) } }
- should("serialize random booleans") { forAll(KTestData.KTestBoolean.Companion) { dumpCborCompare(it) } }
- should("serialize random enums") { forAll(KTestData.KTestEnum.Companion) { dumpCborCompare(it) } }
- should("serialize all base random types") { forAll(KTestData.KTestAllTypes.Companion) { dumpCborCompare(it) } }
- should("serialize random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { dumpCborCompare(it) } }
- should("serialize random messages with primitive list fields") { forAll(KTestData.KTestIntListMessage.Companion) { dumpCborCompare(it) } }
- should("serialize messages with object list fields") { forAll(KTestData.KTestObjectListMessage.Companion) { dumpCborCompare(it) } }
- should("serialize messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { dumpCborCompare(it) } }
- }
-
- "CBOR Reader" {
- should("read random int32") { forAll(KTestData.KTestInt32.Companion) { readCborCompare(it) } }
- should("read random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { readCborCompare(it) } }
- should("read random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { readCborCompare(it) } }
- should("read random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { readCborCompare(it) } }
- should("read random doubles") { forAll(KTestData.KTestDouble.Companion) { readCborCompare(it) } }
- should("read random enums") { forAll(KTestData.KTestEnum.Companion) { readCborCompare(it) } }
- should("read all base random types") { forAll(KTestData.KTestAllTypes.Companion) { readCborCompare(it) } }
- should("read random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { readCborCompare(it) } }
- should("read random messages with primitive list fields") { forAll(KTestData.KTestIntListMessage.Companion) { readCborCompare(it) } }
- should("read random messages with object list fields") { forAll(KTestData.KTestObjectListMessage.Companion) { readCborCompare(it) } }
- }
- }
-}
+//package kotlinx.serialization.formats
+//
+//import com.google.protobuf.GeneratedMessageV3
+//import io.kotlintest.properties.Gen
+//import io.kotlintest.properties.forAll
+//import io.kotlintest.specs.ShouldSpec
+//import kotlinx.serialization.SerialId
+//import kotlinx.serialization.Serializable
+//import kotlinx.serialization.formats.proto.TestData.*
+//
+//fun Gen<String>.generateNotEmpty() = nextPrintableString(Gen.choose(1, 100).generate())
+//
+//object KTestData {
+// @Serializable
+// data class KTestInt32(@SerialId(1) val a: Int) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestInt32.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestInt32> {
+// override fun generate(): KTestInt32 = KTestInt32(Gen.int().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestSignedInt(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Int) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedInt.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestSignedInt> {
+// override fun generate(): KTestSignedInt = KTestSignedInt(Gen.int().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestSignedLong(@SerialId(1) @ProtoType(ProtoNumberType.SIGNED) val a: Long) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestSignedLong.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestSignedLong> {
+// override fun generate(): KTestSignedLong = KTestSignedLong(Gen.long().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestFixedInt(@SerialId(1) @ProtoType(ProtoNumberType.FIXED) val a: Int) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestFixedInt.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestFixedInt> {
+// override fun generate(): KTestFixedInt = KTestFixedInt(Gen.int().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestDouble(@SerialId(1) val a: Double) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestDouble.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestDouble> {
+// override fun generate(): KTestDouble = KTestDouble(Gen.double().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestBoolean(@SerialId(1) val a: Boolean) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestBoolean.newBuilder().setA(a).build()
+//
+// companion object : Gen<KTestBoolean> {
+// override fun generate(): KTestBoolean = KTestBoolean(Gen.bool().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestAllTypes(
+// @SerialId(1) val i32: Int,
+// @SerialId(2) @ProtoType(ProtoNumberType.SIGNED) val si32: Int,
+// @SerialId(3) @ProtoType(ProtoNumberType.FIXED) val f32: Int,
+// @SerialId(10) val i64: Long,
+// @SerialId(11) @ProtoType(ProtoNumberType.SIGNED) val si64: Long,
+// @SerialId(12) @ProtoType(ProtoNumberType.FIXED) val f64: Long,
+// @SerialId(21) val f: Float,
+// @SerialId(22) val d: Double,
+// @SerialId(41) val b: Boolean = false,
+// @SerialId(51) val s: String
+// ) : IMessage {
+// override fun toProtobufMessage(): TestAllTypes = TestAllTypes.newBuilder()
+// .setI32(i32)
+// .setSi32(si32)
+// .setF32(f32)
+// .setI64(i64)
+// .setSi64(si64)
+// .setF64(f64)
+// .setF(f)
+// .setD(d)
+// .setB(b)
+// .setS(s)
+// .build()
+//
+// companion object : Gen<KTestAllTypes> {
+// override fun generate(): KTestAllTypes = KTestAllTypes(
+// Gen.int().generate(),
+// Gen.int().generate(),
+// Gen.int().generate(),
+// Gen.long().generate(),
+// Gen.long().generate(),
+// Gen.long().generate(),
+// Gen.float().generate(),
+// Gen.double().generate(),
+// Gen.bool().generate(),
+// Gen.string().generateNotEmpty()
+// )
+// }
+// }
+//
+// @Serializable
+// data class KTestOuterMessage(
+// @SerialId(1) val a: Int,
+// @SerialId(2) val b: Double,
+// @SerialId(10) val inner: KTestAllTypes,
+// @SerialId(20) val s: String
+// ) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestOuterMessage.newBuilder()
+// .setA(a)
+// .setB(b)
+// .setInner(inner.toProtobufMessage())
+// .setS(s)
+// .build()
+//
+// companion object : Gen<KTestOuterMessage> {
+// override fun generate(): KTestOuterMessage = KTestOuterMessage(
+// Gen.int().generate(),
+// Gen.double().generate(),
+// KTestAllTypes.generate(),
+// Gen.string().generateNotEmpty()
+// )
+// }
+// }
+//
+// @Serializable
+// data class KTestIntListMessage(
+// @SerialId(1) val s: Int,
+// @SerialId(10) val l: List<Int>
+// ) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedIntMessage.newBuilder().setS(s).addAllB(l).build()
+//
+// companion object : Gen<KTestIntListMessage> {
+// override fun generate() = KTestIntListMessage(Gen.int().generate(), Gen.list(Gen.int()).generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestObjectListMessage(
+// @SerialId(1) val inner: List<KTestAllTypes>
+// ) : IMessage {
+// override fun toProtobufMessage(): GeneratedMessageV3 = TestRepeatedObjectMessage.newBuilder().addAllInner(inner.map { it.toProtobufMessage() }).build()
+//
+// companion object : Gen<KTestObjectListMessage> {
+// override fun generate() = KTestObjectListMessage(Gen.list(KTestAllTypes.Companion).generate())
+// }
+// }
+//
+// enum class KCoffee { AMERICANO, LATTE, CAPPUCCINO }
+//
+// @Serializable
+// data class KTestEnum(@SerialId(1) val a: KCoffee): IMessage {
+// override fun toProtobufMessage() = TestEnum.newBuilder().setA(TestEnum.Coffee.forNumber(a.ordinal)).build()
+//
+// companion object : Gen<KTestEnum> {
+// override fun generate(): KTestEnum = KTestEnum(Gen.oneOf<KCoffee>().generate())
+// }
+// }
+//
+// @Serializable
+// data class KTestMap(@SerialId(1) val s: Map<String, String>, @SerialId(2) val o: Map<Int, KTestAllTypes> = emptyMap()) :
+// IMessage {
+// override fun toProtobufMessage() = TestMap.newBuilder()
+// .putAllStringMap(s)
+// .putAllIntObjectMap(o.mapValues { it.value.toProtobufMessage() })
+// .build()
+//
+// companion object : Gen<KTestMap> {
+// override fun generate(): KTestMap =
+// KTestMap(Gen.map(Gen.string(), Gen.string()).generate(), Gen.map(Gen.int(), KTestAllTypes).generate())
+// }
+// }
+//}
+//
+//
+//class RandomTest : ShouldSpec() {
+//
+// init {
+// "Protobuf serialization" {
+// should("serialize random int32") { forAll(KTestData.KTestInt32.Companion) { dumpCompare(it) } }
+// should("serialize random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { dumpCompare(it) } }
+// should("serialize random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { dumpCompare(it) } }
+// should("serialize random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { dumpCompare(it) } }
+// should("serialize random doubles") { forAll(KTestData.KTestDouble.Companion) { dumpCompare(it) } }
+// should("serialize random booleans") { forAll(KTestData.KTestBoolean.Companion) { dumpCompare(it) } }
+// should("serialize random enums") { forAll(KTestData.KTestEnum.Companion) { dumpCompare(it) } }
+// should("serialize all base random types") { forAll(KTestData.KTestAllTypes.Companion) { dumpCompare(it) } }
+// should("serialize random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { dumpCompare(it) } }
+// should("serialize random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { dumpCompare(it) } }
+// should("serialize messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { dumpCompare(it) } }
+// should("serialize messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { dumpCompare(it) } }
+// }
+//
+// "Protobuf deserialization" {
+// should("read random int32") { forAll(KTestData.KTestInt32.Companion) { readCompare(it) } }
+// should("read random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { readCompare(it) } }
+// should("read random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { readCompare(it) } }
+// should("read random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { readCompare(it) } }
+// should("read random doubles") { forAll(KTestData.KTestDouble.Companion) { readCompare(it) } }
+// should("read random enums") { forAll(KTestData.KTestEnum.Companion) { readCompare(it) } }
+// should("read all base random types") { forAll(KTestData.KTestAllTypes.Companion) { readCompare(it) } }
+// should("read random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { readCompare(it) } }
+// should("read random messages with primitive list fields as repeated") { forAll(KTestData.KTestIntListMessage.Companion) { readCompare(it) } }
+// should("read random messages with object list fields as repeated") { forAll(KTestData.KTestObjectListMessage.Companion) { readCompare(it) } }
+// should("read messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { readCompare(it) } }
+// }
+//
+// "CBOR Writer" {
+// should("serialize random int32") { forAll(KTestData.KTestInt32.Companion) { dumpCborCompare(it) } }
+// should("serialize random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { dumpCborCompare(it) } }
+// should("serialize random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { dumpCborCompare(it) } }
+// should("serialize random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { dumpCborCompare(it) } }
+// should("serialize random doubles") { forAll(KTestData.KTestDouble.Companion) { dumpCborCompare(it) } }
+// should("serialize random booleans") { forAll(KTestData.KTestBoolean.Companion) { dumpCborCompare(it) } }
+// should("serialize random enums") { forAll(KTestData.KTestEnum.Companion) { dumpCborCompare(it) } }
+// should("serialize all base random types") { forAll(KTestData.KTestAllTypes.Companion) { dumpCborCompare(it) } }
+// should("serialize random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { dumpCborCompare(it) } }
+// should("serialize random messages with primitive list fields") { forAll(KTestData.KTestIntListMessage.Companion) { dumpCborCompare(it) } }
+// should("serialize messages with object list fields") { forAll(KTestData.KTestObjectListMessage.Companion) { dumpCborCompare(it) } }
+// should("serialize messages with scalar-key maps") { forAll(KTestData.KTestMap.Companion) { dumpCborCompare(it) } }
+// }
+//
+// "CBOR Reader" {
+// should("read random int32") { forAll(KTestData.KTestInt32.Companion) { readCborCompare(it) } }
+// should("read random signed int32") { forAll(KTestData.KTestSignedInt.Companion) { readCborCompare(it) } }
+// should("read random signed int64") { forAll(KTestData.KTestSignedLong.Companion) { readCborCompare(it) } }
+// should("read random fixed int32") { forAll(KTestData.KTestFixedInt.Companion) { readCborCompare(it) } }
+// should("read random doubles") { forAll(KTestData.KTestDouble.Companion) { readCborCompare(it) } }
+// should("read random enums") { forAll(KTestData.KTestEnum.Companion) { readCborCompare(it) } }
+// should("read all base random types") { forAll(KTestData.KTestAllTypes.Companion) { readCborCompare(it) } }
+// should("read random messages with embedded message") { forAll(KTestData.KTestOuterMessage.Companion) { readCborCompare(it) } }
+// should("read random messages with primitive list fields") { forAll(KTestData.KTestIntListMessage.Companion) { readCborCompare(it) } }
+// should("read random messages with object list fields") { forAll(KTestData.KTestObjectListMessage.Companion) { readCborCompare(it) } }
+// }
+// }
+//}
diff --git a/runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtobufEnumWithSerialIdTest.kt b/runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtobufEnumWithSerialIdTest.kt
deleted file mode 100644
index d2c8d79..0000000
--- a/runtime/jvmTest/src/kotlinx/serialization/formats/protobuf/ProtobufEnumWithSerialIdTest.kt
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
- */
-
-package kotlinx.serialization.formats.protobuf
-
-import kotlinx.serialization.SerialId
-import kotlinx.serialization.Serializable
-import kotlinx.serialization.formats.*
-import kotlinx.serialization.formats.proto.TestData
-import org.junit.Test
-import kotlin.test.assertTrue
-
-@Serializable
-enum class EnumWithIds(val id: Int) {
- @SerialId(10)
- FIRST(10),
- @SerialId(20)
- SECOND(20);
-}
-
-@Serializable
-data class EnumHolder(@SerialId(5) val a: EnumWithIds) : IMessage {
- override fun toProtobufMessage(): TestData.EnumHolder =
- TestData.EnumHolder.newBuilder().setA(TestData.TestEnumWithIds.forNumber(a.id)).build()
-}
-
-class ProtobufEnumWithSerialIdTest {
- @Test
- fun enumsSupportSerialIds() {
- assertTrue(readCompare(EnumHolder(EnumWithIds.SECOND), alwaysPrint = true))
- }
-
- @Test
- fun enumsSupportSerialIds2() {
- assertTrue(dumpCompare(EnumHolder(EnumWithIds.SECOND), alwaysPrint = true))
- }
-}
diff --git a/settings.gradle b/settings.gradle
index b7cb4d8..703166a 100644
--- a/settings.gradle
+++ b/settings.gradle
@@ -1,17 +1,5 @@
/*
- * Copyright 2018 JetBrains s.r.o.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
+ * Copyright 2017-2019 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license.
*/
rootProject.name = 'kotlinx-serialization'
@@ -20,9 +8,11 @@
include ':kotlinx-serialization-runtime'
project(':kotlinx-serialization-runtime').projectDir = file('./runtime')
+include ':kotlinx-serialization-protobuf'
+project(':kotlinx-serialization-protobuf').projectDir = file('./formats/protobuf')
+
include ':kotlinx-serialization-runtime-configparser'
project(':kotlinx-serialization-runtime-configparser').projectDir = file('./formats/config')
-// todo: migrate benchmark to multiplatform benchmarks?
include ':benchmark'
project(':benchmark').projectDir = file('./benchmark')