com.xmobitea.changx.msgpack
v1.5.2
Published
XmobiTea Unity Toolkit packages
Readme
XmobiTea MsgPack
Lightweight MessagePack codec for Unity that works with raw primitive values and container shapes.
AI Quick Contract
- Main runtime API:
XmobiTea.Binary.IBinaryConverterXmobiTea.Binary.MessagePack.BinaryConverterXmobiTea.Binary.Helper.Convert
- This package is not a DTO/object mapper.
Deserialize<T>(...)directly casts the raw decoded value.- Arrays decode to
object[]. - Maps decode to
Dictionary<object, object>. - Extensions decode to
Tuple<sbyte, byte[]>. - Integer decode type is based on the MessagePack payload width, not the original CLR source type.
Serialize((int)12)is not a safe match forDeserialize<int>(...).- Only
byte[]is a safe binary serialization input.List<byte>and other byte collections are not safe defaults here. TryParse<T>(...)only wrapsDeserialize<T>(...)intry/catch.charand arbitrary custom classes are not safe serialization targets.Convert.ToBoolean(...)uses odd/even numeric parity for numeric inputs, not a generic "non-zero means true" rule.
Need-Based Routing
Open these only when the current task needs them.
AI_USAGE.md: shortest machine-friendly rules for generating code without reading runtime files.AGENTS.md: package-level rules for maintainers and coding agents.Runtime/MessagePack/BinaryConverter.cs: public MessagePack entry point.Runtime/MessagePack/Serialize/*: exact write-path behavior.Runtime/MessagePack/Deserialize/*: exact read-path behavior.Runtime/Helper/Convert.csandRuntime/Helper/Parsers/*: post-deserialize conversion semantics.
What This Package Provides
IBinaryConverter
Public serialize/deserialize contract.
BinaryConverter
MessagePack implementation of IBinaryConverter.
Convert
Helper methods for coercing loose decoded object values into primitive CLR types after deserialization.
Exact Runtime Behavior
1. Serialization
Safe input shapes
Reliable input shapes are:
nullbool- integer primitives:
sbyte,byte,short,ushort,int,uint,long,ulong floatdoublestringbyte[]System.Collections.ICollection-compatible collections whose elements are themselves supportedSystem.Collections.IDictionary-compatible maps whose keys and values are themselves supported- explicit MessagePack extension tuples:
Tuple<sbyte, byte[]>
Important serialization rules
- Integer encoding width is chosen by value, not by original CLR type.
- Non-negative signed integers are usually encoded through unsigned MessagePack integer forms.
byte[]is handled by the binary writer.- Non-byte collections are handled by the array writer.
- Maps are handled only when the runtime type is assignable to
System.Collections.IDictionary. - Unsupported object types fall through to the extension writer, which expects
Tuple<sbyte, byte[]>.
Unsupported or risky input shapes
Do not treat these as safe defaults:
- arbitrary DTO classes
- arbitrary custom classes
charList<byte>or other byte collections that are not actualbyte[]- shapes that only implement
IEnumerablebut notICollection/IDictionary
Why these fail:
charis classified like a string type, but the string writer expects a realstringinstance.- unsupported object types are routed to the extension writer and usually fail because they are not
Tuple<sbyte, byte[]>. - byte collections such as
List<byte>are classified like binary data, but the binary writer expects an actualbyte[].
2. Deserialization
Deserialize<T>(...) does not map into DTOs or convert container shapes.
The implementation is effectively:
(T)rawDecodedValueRaw decoded runtime shapes
- MessagePack
nil->null - MessagePack
bool->bool - MessagePack integer -> one of
sbyte,byte,short,ushort,int,uint,long,ulong - MessagePack
float32->float - MessagePack
float64->double - MessagePack string ->
string - MessagePack binary ->
byte[] - MessagePack array ->
object[] - MessagePack map ->
Dictionary<object, object> - MessagePack extension ->
Tuple<sbyte, byte[]>
Safe direct-cast targets
These are the safe default targets:
objectobject[]orSystem.Collections.ICollectionfor arraysDictionary<object, object>orSystem.Collections.IDictionaryfor mapsbyte[]for binary payloadsTuple<sbyte, byte[]>for extension payloadsbool,string,float,doublewhen the payload kind is already exact
Integer round-trip consequence
Integer round-trip is value-shaped, not source-type-shaped.
Examples:
Serialize((int)12)typically decodes asbyteSerialize((int)300)typically decodes asushortSerialize((int)-5)typically decodes assbyte
That means these are not safe default assumptions:
Deserialize<int>(...)Deserialize<long>(...)Deserialize<short>(...)
unless you already know the incoming MessagePack payload width matches that exact CLR type.
3. TryParse<T>(...)
TryParse<T>(...) only catches exceptions from Deserialize<T>(...).
It does not:
- convert integer widths
- map arrays into typed lists
- map maps into typed generic dictionaries
- bind decoded values into DTOs
So this is safe:
TryParse<object[]>(...)TryParse<System.Collections.IDictionary>(...)TryParse<byte[]>(...)
And these are still unsafe default patterns:
TryParse<int>(...)for generic integer payloadsTryParse<List<object>>(...)TryParse<Dictionary<string, object>>(...)TryParse<MyDto>(...)
4. Convert
XmobiTea.Binary.Helper.Convert is the intended helper after deserializing into raw shapes.
Available helpers:
ToBooleanToSByteToByteToInt16ToUInt16ToInt32ToUInt32ToInt64ToUInt64ToSingleToDoubleToCharToString
Important behavior:
nullreturns the default value of the target type.- numeric conversions are package-specific and can truncate or overflow silently on some explicit cast paths.
ToBoolean(...)uses% 2 != 0for numeric andcharinputs.- invalid string/object conversions can still throw.
ToChar(...)exists for post-processing only; it does not makechara safe serialization target.
5. Current Limits And Edge Cases
These are current runtime constraints, not documentation policy choices:
- large
str32,bin32, andext32payloads above65535bytes are not safe decode targets in the current readers because the final byte read path is narrowed toushort - arrays decode to
object[], notList<T> - maps decode to
Dictionary<object, object>, notDictionary<string, object> - exact integer CLR types are not preserved by value-minimizing MessagePack encoding
Basic Usage
Raw map usage with manual conversion
using System.Collections;
using System.Collections.Generic;
using XmobiTea.Binary.MessagePack;
using XmobiTea.Binary.Helper;
var converter = new BinaryConverter();
var payload = new Dictionary<string, object>
{
["id"] = 12,
["name"] = "player",
["flags"] = new object[] { true, false }
};
var bytes = converter.Serialize(payload);
var decoded = converter.Deserialize<IDictionary>(bytes);
var id = Convert.ToInt32(decoded["id"]);
var name = Convert.ToString(decoded["name"]);Integer payload usage
using XmobiTea.Binary.MessagePack;
using XmobiTea.Binary.Helper;
var converter = new BinaryConverter();
var bytes = converter.Serialize(12);
var raw = converter.Deserialize<object>(bytes);
var value = Convert.ToInt32(raw);Extension usage
using System;
using XmobiTea.Binary.MessagePack;
var converter = new BinaryConverter();
var ext = Tuple.Create((sbyte)1, new byte[] { 1, 2, 3 });
var bytes = converter.Serialize(ext);
var decoded = converter.Deserialize<Tuple<sbyte, byte[]>>(bytes);Do / Don't
Do
- Do deserialize into raw runtime shapes first.
- Do use
object,object[],IDictionary,byte[], andTuple<sbyte, byte[]>as the default safe targets. - Do use
XmobiTea.Binary.Helper.Convertfor leaf primitive coercion. - Do manually map decoded data into domain models when typed models are needed.
- Do treat integer payloads as width-based values rather than source-type-stable values.
Don't
- Don't advertise this package as automatic DTO serialization.
- Don't assume
Deserialize<int>(...)is a safe default for integer payloads. - Don't deserialize maps directly into
Dictionary<string, object>by default. - Don't deserialize arrays directly into
List<T>by default. - Don't serialize
List<byte>as if it were guaranteed binary-safe. - Don't rely on
charserialization.
Common Mistakes
Mistake 1: Treating Deserialize<T>(...) like model binding
It is only a direct cast over the raw decoded object.
Mistake 2: Expecting integer CLR types to round-trip unchanged
The writer minimizes integer width by value, so decode type often differs from the original source type.
Mistake 3: Treating List<byte> like byte[]
Only byte[] is a safe binary serialization input here.
Mistake 4: Expecting typed generic containers on decode
Maps decode to Dictionary<object, object> and arrays decode to object[].
Mistake 5: Assuming Convert.ToBoolean(...) uses generic non-zero semantics
Its numeric conversion rule is parity-based in the current implementation.
Required Setup
No scene setup, resource asset, or editor setup is required.
This is a pure runtime serialization package.
Namespace
using XmobiTea.Binary;
using XmobiTea.Binary.MessagePack;
using XmobiTea.Binary.Helper;Assembly Definition
Runtime assembly:
XmobiTea.MsgPack.runtimePackage Metadata
- Package name:
com.xmobitea.changx.msgpack - Unity version:
2022.3+ - License:
Apache-2.0
