Test serializing booleans
assert(serializeCbor(true) == [0xf5]); assert(serializeCbor(false) == [0xf4]);
Test serializing nulls
assert(serializeCbor(null) == [0xf6]);
Test serializing signed integral types
import mir.test; // Bytes serializeCbor(byte.min).should == [0x38, 0x7F]; serializeCbor(byte.max).should == [0x18, 0x7F]; // Shorts serializeCbor(short(byte.max)).should == [0x18, 0x7F]; serializeCbor(short(byte.max) + 1).should == [0x18, 0x80]; serializeCbor(short.min).should == [0x39, 0x7F, 0xFF]; serializeCbor(short.max).should == [0x19, 0x7F, 0xFF]; // Integers serializeCbor(int(-32)).should == [0x38, 0x1F]; serializeCbor(int(byte.max)).should == [0x18, 0x7F]; serializeCbor(int(short.max)).should == [0x19, 0x7F, 0xFF]; serializeCbor(int(short.max) + 1).should == [0x19, 0x80, 0x00]; serializeCbor(int.min).should == [0x3A, 0x7f, 0xff, 0xff, 0xff]; serializeCbor(int.max).should == [0x1A, 0x7f, 0xff, 0xff, 0xff]; // Long integers serializeCbor(long(int.max)).should == [0x1A, 0x7f, 0xff, 0xff, 0xff]; serializeCbor(long(int.max) + 1).should == [0x1A, 0x80, 0x00, 0x00, 0x00]; serializeCbor(long.max).should == [0x1b, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]; serializeCbor(long.min).should == [0x3b, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff];
Test serializing unsigned integral types
import mir.test; // Unsigned bytes serializeCbor(ubyte.min).should == [0x00]; serializeCbor(ubyte((1 << 7) - 1)).should == [0x18, 0x7F]; serializeCbor(ubyte((1 << 7))).should == [0x18, 0x80]; serializeCbor(ubyte.max).should == [0x18, 0xff]; // Unsigned shorts serializeCbor(ushort(ubyte.max)).should == [0x18, 0xff]; serializeCbor(ushort(ubyte.max + 1)).should == [0x19, 0x01, 0x00]; serializeCbor(ushort.min).should == [0x00]; serializeCbor(ushort.max).should == [0x19, 0xff, 0xff]; // Unsigned integers serializeCbor(uint(ubyte.max)).should == [0x18, 0xff]; serializeCbor(uint(ushort.max)).should == [0x19, 0xff, 0xff]; serializeCbor(uint(ushort.max + 1)).should == [0x1A, 0x00, 0x01, 0x00, 0x00]; serializeCbor(uint.min).should == [0x00]; serializeCbor(uint.max).should == [0x1A, 0xff, 0xff, 0xff, 0xff]; // Long unsigned integers serializeCbor(ulong(ubyte.max)).should == [0x18, 0xff]; serializeCbor(ulong(ushort.max)).should == [0x19, 0xff, 0xff]; serializeCbor(ulong(uint.max)).should == [0x1A, 0xff, 0xff, 0xff, 0xff]; serializeCbor(ulong(uint.max) + 1).should == [0x1B, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00]; serializeCbor(ulong.min).should == [0x00]; serializeCbor(ulong.max).should == [0x1B, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]; // Mir's BigIntView import mir.bignum.integer : BigInt; serializeCbor(BigInt!2(0xDEADBEEF)).should == [0x1A, 0xde, 0xad, 0xbe, 0xef];
Test serializing floats / doubles / reals
import mir.test; serializeCbor(float.min_normal).should == [0xfa, 0x00, 0x80, 0x00, 0x00]; serializeCbor(float.max).should == [0xfa, 0x7f, 0x7f, 0xff, 0xff]; serializeCbor(double.min_normal).should == [0xfb, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00]; serializeCbor(double.max).should == [0xfb, 0x7f, 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff]; static if (real.mant_dig == 64) { serializeCbor(real.min_normal).should == serializeCbor(double(0)); serializeCbor(real.max).should == serializeCbor(double.infinity); } // Mir's Decimal import mir.bignum.decimal : Decimal; serializeCbor(Decimal!2("777.777")).should == [0xfb,0x40,0x88,0x4e,0x37,0x4b,0xc6,0xa7,0xf0]; serializeCbor(Decimal!2("-777.7")).should == [0xfb,0xc0,0x88,0x4d,0x99,0x99,0x99,0x99,0x9a];
Test serializing timestamps
import mir.test; import mir.timestamp : Timestamp; serializeCbor(Timestamp(1970, 1, 1)).should == [0x6a, 0x31, 0x39, 0x37, 0x30, 0x2D, 0x30, 0x31, 0x2D, 0x30, 0x31];
Test serializing strings
import mir.test; import std.array : replicate; serializeCbor("a").should == [0x61, 0x61]; // These need to be trusted because we cast const(char)[] to ubyte[] (which is fine here!) () @trusted { auto a = "a".replicate(32); serializeCbor(a).should == cast(ubyte[])[0x78, 0x20] ~ cast(ubyte[])a; } (); () @trusted { auto a = "a".replicate(ushort.max); serializeCbor(a).should == cast(ubyte[])[0x79, 0xff, 0xff] ~ cast(ubyte[])a; } (); () @trusted { auto a = "a".replicate(ushort.max + 1); serializeCbor(a).should == cast(ubyte[])[0x7a, 0x00, 0x01, 0x00, 0x00] ~ cast(ubyte[])a; } ();
Test serializing blobs / clobs
import mir.test; import mir.lob : Blob, Clob; import std.array : replicate; // Blobs // These need to be trusted because we cast const(char)[] to ubyte[] (which is fine here!) () @trusted { auto de = "\xde".replicate(32); serializeCbor(Blob(cast(ubyte[])de)).should == cast(ubyte[])[0x58, 0x20] ~ cast(ubyte[])de; } (); () @trusted { auto de = "\xde".replicate(ushort.max); serializeCbor(Blob(cast(ubyte[])de)).should == cast(ubyte[])[0x59, 0xff, 0xff] ~ cast(ubyte[])de; } (); () @trusted { auto de = "\xde".replicate(ushort.max + 1); serializeCbor(Blob(cast(ubyte[])de)).should == cast(ubyte[])[0x5a, 0x00, 0x01, 0x00, 0x00] ~ cast(ubyte[])de; } (); // Clobs (serialized just as regular strings here) () @trusted { auto de = "\xde".replicate(32); serializeCbor(Clob(de)).should == cast(ubyte[])[0x78, 0x20] ~ cast(ubyte[])de; } ();
Test serializing arrays
import mir.test; // nested arrays serializeCbor([["foo"], ["bar"], ["baz"]]).should == [0x83, 0x81, 0x63, 0x66, 0x6F, 0x6F, 0x81, 0x63, 0x62, 0x61, 0x72, 0x81, 0x63, 0x62, 0x61, 0x7A]; serializeCbor([0xDEADBEEF, 0xCAFEBABE, 0xAAAA_AAAA]).should == [0x83, 0x1A, 0xDE, 0xAD, 0xBE, 0xEF, 0x1A, 0xCA, 0xFE, 0xBA, 0xBE, 0x1A, 0xAA, 0xAA, 0xAA, 0xAA]; serializeCbor(["foo", "bar", "baz"]).should == [0x83, 0x63, 0x66, 0x6F, 0x6F, 0x63, 0x62, 0x61, 0x72, 0x63, 0x62, 0x61, 0x7A]; serializeCbor([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]).should == [0x91, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0x10, 0x11];
Test serializing enums
enum Foo { Bar, Baz } assert(serializeCbor(Foo.Bar) == [0x63,0x42,0x61,0x72]); assert(serializeCbor(Foo.Baz) == [0x63,0x42,0x61,0x7a]);
Test serializing maps (structs)
import mir.test; struct Book { string title; bool wouldRecommend; string description; uint numberOfNovellas; double price; float weight; string[] tags; } Book book = Book("A Hero of Our Time", true, "", 5, 7.99, 6.88, ["russian", "novel", "19th century"]); // This will probably break if you modify how any of the data types // are serialized. serializeCbor(book).should == [0xBF, 0x65, 0x74, 0x69, 0x74, 0x6C, 0x65, 0x72, 0x41, 0x20, 0x48, 0x65, 0x72, 0x6F, 0x20, 0x6F, 0x66, 0x20, 0x4F, 0x75, 0x72, 0x20, 0x54, 0x69, 0x6D, 0x65, 0x6E, 0x77, 0x6F, 0x75, 0x6C, 0x64, 0x52, 0x65, 0x63, 0x6F, 0x6D, 0x6D, 0x65, 0x6E, 0x64, 0xF5, 0x6B, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6F, 0x6E, 0x60, 0x70, 0x6E, 0x75, 0x6D, 0x62, 0x65, 0x72, 0x4F, 0x66, 0x4E, 0x6F, 0x76, 0x65, 0x6C, 0x6C, 0x61, 0x73, 0x05, 0x65, 0x70, 0x72, 0x69, 0x63, 0x65, 0xFB, 0x40, 0x1F, 0xF5, 0xC2, 0x8F, 0x5C, 0x28, 0xF6, 0x66, 0x77, 0x65, 0x69, 0x67, 0x68, 0x74, 0xFA, 0x40, 0xDC, 0x28, 0xF6, 0x64, 0x74, 0x61, 0x67, 0x73, 0x83, 0x67, 0x72, 0x75, 0x73, 0x73, 0x69, 0x61, 0x6E, 0x65, 0x6E, 0x6F, 0x76, 0x65, 0x6C, 0x6C, 0x31, 0x39, 0x74, 0x68, 0x20, 0x63, 0x65, 0x6E, 0x74, 0x75, 0x72, 0x79, 0xFF];
Test maps with serdeMembersExactly
import mir.test; import mir.serde: serdeMembersExactly; @serdeMembersExactly(7) struct Book { string title; bool wouldRecommend; string description; uint numberOfNovellas; double price; float weight; string[] tags; } Book book = Book("A Hero of Our Time", true, "", 5, 7.99, 6.88, ["russian", "novel", "19th century"]); // This will probably break if you modify how any of the data types // are serialized. serializeCbor(book).should == [0xA7, 0x65, 0x74, 0x69, 0x74, 0x6C, 0x65, 0x72, 0x41, 0x20, 0x48, 0x65, 0x72, 0x6F, 0x20, 0x6F, 0x66, 0x20, 0x4F, 0x75, 0x72, 0x20, 0x54, 0x69, 0x6D, 0x65, 0x6E, 0x77, 0x6F, 0x75, 0x6C, 0x64, 0x52, 0x65, 0x63, 0x6F, 0x6D, 0x6D, 0x65, 0x6E, 0x64, 0xF5, 0x6B, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6F, 0x6E, 0x60, 0x70, 0x6E, 0x75, 0x6D, 0x62, 0x65, 0x72, 0x4F, 0x66, 0x4E, 0x6F, 0x76, 0x65, 0x6C, 0x6C, 0x61, 0x73, 0x05, 0x65, 0x70, 0x72, 0x69, 0x63, 0x65, 0xFB, 0x40, 0x1F, 0xF5, 0xC2, 0x8F, 0x5C, 0x28, 0xF6, 0x66, 0x77, 0x65, 0x69, 0x67, 0x68, 0x74, 0xFA, 0x40, 0xDC, 0x28, 0xF6, 0x64, 0x74, 0x61, 0x67, 0x73, 0x83, 0x67, 0x72, 0x75, 0x73, 0x73, 0x69, 0x61, 0x6E, 0x65, 0x6E, 0x6F, 0x76, 0x65, 0x6C, 0x6C, 0x31, 0x39, 0x74, 0x68, 0x20, 0x63, 0x65, 0x6E, 0x74, 0x75, 0x72, 0x79];
Test serializing annotated structs
import mir.test; import mir.algebraic; import mir.serde : serdeAlgebraicAnnotation; @serdeAlgebraicAnnotation("Foo") static struct Foo { string bar; } @serdeAlgebraicAnnotation("Fooz") static struct Fooz { long bar; } alias V = Variant!(Foo, Fooz); auto foo = V(Foo("baz")); serializeCbor(foo).should == [0xA1, 0x63, 0x46, 0x6F, 0x6F, 0xBF, 0x63, 0x62, 0x61, 0x72, 0x63, 0x62, 0x61, 0x7A, 0xFF];
Test custom serialize function with Cbor
import mir.test; static class MyExampleClass { string text; this(string text) { this.text = text; } void serialize(S)(scope ref S serializer) scope const { auto state = serializer.stringBegin; serializer.putStringPart("Hello! "); serializer.putStringPart("String passed: "); serializer.putStringPart(this.text); serializer.stringEnd(state); } } serializeCbor(new MyExampleClass("foo bar baz")).should == [0x7F, 0x67, 0x48, 0x65, 0x6C, 0x6C, 0x6F, 0x21, 0x20, 0x6F, 0x53, 0x74, 0x72, 0x69, 0x6E, 0x67, 0x20, 0x70, 0x61, 0x73, 0x73, 0x65, 0x64, 0x3A, 0x20, 0x6B, 0x66, 0x6F, 0x6F, 0x20, 0x62, 0x61, 0x72, 0x20, 0x62, 0x61, 0x7A, 0xFF];
Serializes a value to CBOR format, returning the encoded byte array. (community summary)