Updated serialization utils
This commit is contained in:
parent
b72300bfaa
commit
58e396f50c
@ -0,0 +1,169 @@
|
|||||||
|
package hep.dataforge.vis.spatial.gdml
|
||||||
|
|
||||||
|
import hep.dataforge.meta.Meta
|
||||||
|
import hep.dataforge.vis.spatial.*
|
||||||
|
import kotlinx.serialization.*
|
||||||
|
import kotlinx.serialization.json.*
|
||||||
|
import kotlinx.serialization.modules.SerialModule
|
||||||
|
import kotlinx.serialization.modules.SerialModuleCollector
|
||||||
|
import kotlin.reflect.KClass
|
||||||
|
|
||||||
|
internal val SerialDescriptor.jsonType
|
||||||
|
get() = when (this.kind) {
|
||||||
|
StructureKind.LIST -> "array"
|
||||||
|
PrimitiveKind.BYTE, PrimitiveKind.SHORT, PrimitiveKind.INT, PrimitiveKind.LONG,
|
||||||
|
PrimitiveKind.FLOAT, PrimitiveKind.DOUBLE -> "number"
|
||||||
|
PrimitiveKind.STRING, PrimitiveKind.CHAR, UnionKind.ENUM_KIND -> "string"
|
||||||
|
PrimitiveKind.BOOLEAN -> "boolean"
|
||||||
|
else -> "object"
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun SerialModule.enumerate(type: KClass<*>): Sequence<SerialDescriptor> {
|
||||||
|
val list = ArrayList<SerialDescriptor>()
|
||||||
|
fun send(descriptor: SerialDescriptor) = list.add(descriptor)
|
||||||
|
|
||||||
|
val enumerator = object : SerialModuleCollector {
|
||||||
|
override fun <T : Any> contextual(kClass: KClass<T>, serializer: KSerializer<T>) {
|
||||||
|
if (kClass == type) {
|
||||||
|
send(serializer.descriptor)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun <Base : Any, Sub : Base> polymorphic(
|
||||||
|
baseClass: KClass<Base>,
|
||||||
|
actualClass: KClass<Sub>,
|
||||||
|
actualSerializer: KSerializer<Sub>
|
||||||
|
) {
|
||||||
|
if (baseClass == type) {
|
||||||
|
send(actualSerializer.descriptor)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
dumpTo(enumerator)
|
||||||
|
return list.asSequence()
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates an [JsonObject] which contains Json Schema of given [descriptor].
|
||||||
|
*
|
||||||
|
* Schema can contain following fields:
|
||||||
|
* `description`, `type` for all descriptors;
|
||||||
|
* `properties` and `required` for objects;
|
||||||
|
* `enum` for enums;
|
||||||
|
* `items` for arrays.
|
||||||
|
*
|
||||||
|
* User can modify this schema to add additional validation keywords
|
||||||
|
* (as per [https://json-schema.org/latest/json-schema-validation.html])
|
||||||
|
* if they want.
|
||||||
|
*/
|
||||||
|
private fun jsonSchema(descriptor: SerialDescriptor, context: SerialModule): JsonObject {
|
||||||
|
|
||||||
|
if (descriptor.name in arrayOf(
|
||||||
|
"hep.dataforge.vis.spatial.Point3D",
|
||||||
|
"hep.dataforge.vis.spatial.Point2D",
|
||||||
|
Meta::class.qualifiedName
|
||||||
|
)
|
||||||
|
) return json {
|
||||||
|
"\$ref" to "#/definitions/${descriptor.name}"
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
val properties: MutableMap<String, JsonObject> = mutableMapOf()
|
||||||
|
val requiredProperties: MutableSet<String> = mutableSetOf()
|
||||||
|
val isEnum = descriptor.kind == UnionKind.ENUM_KIND
|
||||||
|
val isPolymorphic = descriptor.kind == UnionKind.POLYMORPHIC
|
||||||
|
|
||||||
|
|
||||||
|
if (!isEnum && !isPolymorphic) descriptor.elementDescriptors().forEachIndexed { index, child ->
|
||||||
|
val elementName = descriptor.getElementName(index)
|
||||||
|
|
||||||
|
properties[elementName] = when (elementName) {
|
||||||
|
"templates" -> json {
|
||||||
|
"\$ref" to "#/definitions/hep.dataforge.vis.spatial.VisualGroup3D"
|
||||||
|
}
|
||||||
|
"properties" -> json {
|
||||||
|
"\$ref" to "#/definitions/${Meta::class.qualifiedName}"
|
||||||
|
}
|
||||||
|
"first", "second" -> json{
|
||||||
|
"\$ref" to "#/definitions/children"
|
||||||
|
}
|
||||||
|
"styleSheet" -> json {
|
||||||
|
"type" to "object"
|
||||||
|
"additionalProperties" to json {
|
||||||
|
"\$ref" to "#/definitions/${Meta::class.qualifiedName}"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
in arrayOf("children") -> json {
|
||||||
|
"type" to "object"
|
||||||
|
"additionalProperties" to json {
|
||||||
|
"\$ref" to "#/definitions/children"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else -> jsonSchema(child, context)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!descriptor.isElementOptional(index)) requiredProperties.add(elementName)
|
||||||
|
}
|
||||||
|
|
||||||
|
val jsonType = descriptor.jsonType
|
||||||
|
val objectData: MutableMap<String, JsonElement> = mutableMapOf(
|
||||||
|
"description" to JsonLiteral(descriptor.name),
|
||||||
|
"type" to JsonLiteral(jsonType)
|
||||||
|
)
|
||||||
|
if (isEnum) {
|
||||||
|
val allElementNames = (0 until descriptor.elementsCount).map(descriptor::getElementName)
|
||||||
|
objectData += "enum" to JsonArray(allElementNames.map(::JsonLiteral))
|
||||||
|
}
|
||||||
|
when (jsonType) {
|
||||||
|
"object" -> {
|
||||||
|
objectData["properties"] = JsonObject(properties)
|
||||||
|
val required = requiredProperties.map { JsonLiteral(it) }
|
||||||
|
if (required.isNotEmpty()) {
|
||||||
|
objectData["required"] = JsonArray(required)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"array" -> objectData["items"] = properties.values.let {
|
||||||
|
check(it.size == 1) { "Array descriptor has returned inconsistent number of elements: expected 1, found ${it.size}" }
|
||||||
|
it.first()
|
||||||
|
}
|
||||||
|
else -> { /* no-op */
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return JsonObject(objectData)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun main() {
|
||||||
|
val context = Visual3DPlugin.serialModule
|
||||||
|
val definitions = json {
|
||||||
|
"children" to json {
|
||||||
|
"anyOf" to jsonArray {
|
||||||
|
context.enumerate(VisualObject3D::class).forEach {
|
||||||
|
if (it.name == "hep.dataforge.vis.spatial.VisualGroup3D") {
|
||||||
|
+json {
|
||||||
|
"\$ref" to "#/definitions/${it.name}"
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
+jsonSchema(it, context)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"hep.dataforge.vis.spatial.Point3D" to jsonSchema(Point3DSerializer.descriptor, context)
|
||||||
|
"hep.dataforge.vis.spatial.Point2D" to jsonSchema(Point2DSerializer.descriptor, context)
|
||||||
|
"hep.dataforge.vis.spatial.VisualGroup3D" to jsonSchema(VisualGroup3D.serializer().descriptor, context)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
println(
|
||||||
|
Json.indented.stringify(
|
||||||
|
JsonObjectSerializer,
|
||||||
|
json {
|
||||||
|
"definitions" to definitions
|
||||||
|
"\$ref" to "#/definitions/hep.dataforge.vis.spatial.VisualGroup3D"
|
||||||
|
}
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
@ -2,7 +2,7 @@
|
|||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.context.Context
|
import hep.dataforge.context.Context
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.*
|
import hep.dataforge.meta.*
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import hep.dataforge.vis.common.VisualFactory
|
import hep.dataforge.vis.common.VisualFactory
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
@file:UseSerializers(Point3DSerializer::class)
|
@file:UseSerializers(Point3DSerializer::class)
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.meta.MetaBuilder
|
import hep.dataforge.meta.MetaBuilder
|
||||||
import hep.dataforge.meta.update
|
import hep.dataforge.meta.update
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.meta.MetaBuilder
|
import hep.dataforge.meta.MetaBuilder
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
@file:UseSerializers(Point2DSerializer::class, Point3DSerializer::class)
|
@file:UseSerializers(Point2DSerializer::class, Point3DSerializer::class)
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import hep.dataforge.vis.common.number
|
import hep.dataforge.vis.common.number
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
|
|
||||||
import hep.dataforge.io.serialization.NameSerializer
|
import hep.dataforge.io.serialization.NameSerializer
|
||||||
import hep.dataforge.meta.*
|
import hep.dataforge.meta.*
|
||||||
@ -15,6 +15,7 @@ import hep.dataforge.vis.common.MutableVisualGroup
|
|||||||
import hep.dataforge.vis.common.VisualGroup
|
import hep.dataforge.vis.common.VisualGroup
|
||||||
import hep.dataforge.vis.common.VisualObject
|
import hep.dataforge.vis.common.VisualObject
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
import kotlinx.serialization.Transient
|
||||||
import kotlinx.serialization.UseSerializers
|
import kotlinx.serialization.UseSerializers
|
||||||
import kotlin.collections.component1
|
import kotlin.collections.component1
|
||||||
import kotlin.collections.component2
|
import kotlin.collections.component2
|
||||||
@ -72,6 +73,7 @@ class Proxy(val templateName: Name) : AbstractVisualObject(), VisualGroup, Visua
|
|||||||
ProxyChild(it.key.asName())
|
ProxyChild(it.key.asName())
|
||||||
} ?: emptyMap()
|
} ?: emptyMap()
|
||||||
|
|
||||||
|
@Transient
|
||||||
private val propertyCache: HashMap<Name, Config> = HashMap()
|
private val propertyCache: HashMap<Name, Config> = HashMap()
|
||||||
|
|
||||||
fun childPropertyName(childName: Name, propertyName: Name): Name {
|
fun childPropertyName(childName: Name, propertyName: Name): Name {
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
@file:UseSerializers(Point3DSerializer::class)
|
@file:UseSerializers(Point3DSerializer::class)
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.vis.common.AbstractVisualObject
|
import hep.dataforge.vis.common.AbstractVisualObject
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
@ -4,8 +4,8 @@ import hep.dataforge.context.AbstractPlugin
|
|||||||
import hep.dataforge.context.Context
|
import hep.dataforge.context.Context
|
||||||
import hep.dataforge.context.PluginFactory
|
import hep.dataforge.context.PluginFactory
|
||||||
import hep.dataforge.context.PluginTag
|
import hep.dataforge.context.PluginTag
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.io.MetaSerializer
|
import hep.dataforge.io.serialization.MetaSerializer
|
||||||
import hep.dataforge.io.serialization.NameSerializer
|
import hep.dataforge.io.serialization.NameSerializer
|
||||||
import hep.dataforge.meta.*
|
import hep.dataforge.meta.*
|
||||||
import hep.dataforge.names.Name
|
import hep.dataforge.names.Name
|
||||||
|
@ -8,8 +8,8 @@
|
|||||||
|
|
||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
import hep.dataforge.io.ConfigSerializer
|
import hep.dataforge.io.serialization.ConfigSerializer
|
||||||
import hep.dataforge.io.MetaSerializer
|
import hep.dataforge.io.serialization.MetaSerializer
|
||||||
import hep.dataforge.io.serialization.NameSerializer
|
import hep.dataforge.io.serialization.NameSerializer
|
||||||
import hep.dataforge.meta.Config
|
import hep.dataforge.meta.Config
|
||||||
import hep.dataforge.meta.Meta
|
import hep.dataforge.meta.Meta
|
||||||
|
@ -1,45 +1,97 @@
|
|||||||
package hep.dataforge.vis.spatial
|
package hep.dataforge.vis.spatial
|
||||||
|
|
||||||
|
import hep.dataforge.io.serialization.descriptor
|
||||||
import hep.dataforge.names.NameToken
|
import hep.dataforge.names.NameToken
|
||||||
import hep.dataforge.names.toName
|
import hep.dataforge.names.toName
|
||||||
import kotlinx.serialization.*
|
import kotlinx.serialization.*
|
||||||
|
import kotlinx.serialization.internal.DoubleSerializer
|
||||||
import kotlinx.serialization.internal.StringDescriptor
|
import kotlinx.serialization.internal.StringDescriptor
|
||||||
|
import kotlinx.serialization.internal.nullable
|
||||||
|
|
||||||
@Serializable
|
inline fun <R> Decoder.decodeStructure(
|
||||||
private data class Point2DSerial(val x: Double, val y: Double)
|
desc: SerialDescriptor,
|
||||||
|
vararg typeParams: KSerializer<*> = emptyArray(),
|
||||||
|
crossinline block: CompositeDecoder.() -> R
|
||||||
|
): R {
|
||||||
|
val decoder = beginStructure(desc, *typeParams)
|
||||||
|
val res = decoder.block()
|
||||||
|
decoder.endStructure(desc)
|
||||||
|
return res
|
||||||
|
}
|
||||||
|
|
||||||
@Serializable
|
inline fun Encoder.encodeStructure(
|
||||||
private data class Point3DSerial(val x: Double, val y: Double, val z: Double)
|
desc: SerialDescriptor,
|
||||||
|
vararg typeParams: KSerializer<*> = emptyArray(),
|
||||||
|
block: CompositeEncoder.() -> Unit
|
||||||
|
) {
|
||||||
|
val encoder = beginStructure(desc, *typeParams)
|
||||||
|
encoder.block()
|
||||||
|
encoder.endStructure(desc)
|
||||||
|
}
|
||||||
|
|
||||||
@Serializer(Point3D::class)
|
@Serializer(Point3D::class)
|
||||||
object Point3DSerializer : KSerializer<Point3D> {
|
object Point3DSerializer : KSerializer<Point3D> {
|
||||||
private val serializer = Point3DSerial.serializer()
|
override val descriptor: SerialDescriptor = descriptor("hep.dataforge.vis.spatial.Point3D") {
|
||||||
override val descriptor: SerialDescriptor get() = serializer.descriptor
|
double("x", true)
|
||||||
|
double("y", true)
|
||||||
|
double("z", true)
|
||||||
|
}
|
||||||
|
|
||||||
override fun deserialize(decoder: Decoder): Point3D {
|
override fun deserialize(decoder: Decoder): Point3D {
|
||||||
return serializer.deserialize(decoder).let {
|
var x: Double? = null
|
||||||
Point3D(it.x, it.y, it.z)
|
var y: Double? = null
|
||||||
|
var z: Double? = null
|
||||||
|
decoder.decodeStructure(descriptor) {
|
||||||
|
loop@ while (true) {
|
||||||
|
when (val i = decodeElementIndex(descriptor)) {
|
||||||
|
CompositeDecoder.READ_DONE -> break@loop
|
||||||
|
0 -> x = decodeNullableSerializableElement(descriptor, 0, DoubleSerializer.nullable) ?: 0.0
|
||||||
|
1 -> y = decodeNullableSerializableElement(descriptor, 0, DoubleSerializer.nullable) ?: 0.0
|
||||||
|
2 -> z = decodeNullableSerializableElement(descriptor, 0, DoubleSerializer.nullable) ?: 0.0
|
||||||
|
else -> throw SerializationException("Unknown index $i")
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
return Point3D(x?:0.0, y?:0.0, z?:0.0)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun serialize(encoder: Encoder, obj: Point3D) {
|
override fun serialize(encoder: Encoder, obj: Point3D) {
|
||||||
serializer.serialize(encoder, Point3DSerial(obj.x, obj.y, obj.z))
|
encoder.encodeStructure(descriptor) {
|
||||||
|
if (obj.x != 0.0) encodeDoubleElement(descriptor, 0, obj.x)
|
||||||
|
if (obj.y != 0.0) encodeDoubleElement(descriptor, 1, obj.y)
|
||||||
|
if (obj.z != 0.0) encodeDoubleElement(descriptor, 2, obj.z)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Serializer(Point2D::class)
|
@Serializer(Point2D::class)
|
||||||
object Point2DSerializer : KSerializer<Point2D> {
|
object Point2DSerializer : KSerializer<Point2D> {
|
||||||
private val serializer = Point2DSerial.serializer()
|
override val descriptor: SerialDescriptor = descriptor("hep.dataforge.vis.spatial.Point2D") {
|
||||||
override val descriptor: SerialDescriptor get() = serializer.descriptor
|
double("x", true)
|
||||||
|
double("y", true)
|
||||||
|
}
|
||||||
|
|
||||||
override fun deserialize(decoder: Decoder): Point2D {
|
override fun deserialize(decoder: Decoder): Point2D {
|
||||||
return serializer.deserialize(decoder).let {
|
var x: Double? = null
|
||||||
Point2D(it.x, it.y)
|
var y: Double? = null
|
||||||
|
decoder.decodeStructure(descriptor) {
|
||||||
|
loop@ while (true) {
|
||||||
|
when (val i = decodeElementIndex(descriptor)) {
|
||||||
|
CompositeDecoder.READ_DONE -> break@loop
|
||||||
|
0 -> x = decodeNullableSerializableElement(descriptor, 0, DoubleSerializer.nullable) ?: 0.0
|
||||||
|
1 -> y = decodeNullableSerializableElement(descriptor, 0, DoubleSerializer.nullable) ?: 0.0
|
||||||
|
else -> throw SerializationException("Unknown index $i")
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
return Point2D(x?:0.0, y?:0.0)
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun serialize(encoder: Encoder, obj: Point2D) {
|
override fun serialize(encoder: Encoder, obj: Point2D) {
|
||||||
serializer.serialize(encoder, Point2DSerial(obj.x, obj.y))
|
encoder.encodeStructure(descriptor) {
|
||||||
|
if (obj.x != 0.0) encodeDoubleElement(descriptor, 0, obj.x)
|
||||||
|
if (obj.y != 0.0) encodeDoubleElement(descriptor, 1, obj.y)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -11,6 +11,8 @@ class SerializationTest {
|
|||||||
fun testCubeSerialization(){
|
fun testCubeSerialization(){
|
||||||
val cube = Box(100f,100f,100f).apply{
|
val cube = Box(100f,100f,100f).apply{
|
||||||
color(222)
|
color(222)
|
||||||
|
x = 100
|
||||||
|
z = -100
|
||||||
}
|
}
|
||||||
val string = json.stringify(Box.serializer(),cube)
|
val string = json.stringify(Box.serializer(),cube)
|
||||||
println(string)
|
println(string)
|
||||||
|
Loading…
Reference in New Issue
Block a user