I am serializing an Entity
on a server:
public class Entity
{
private List<Component> _components = new List<Component>();
[Key(0)]
public List<Component> Components {
get {
return _components;
}
set
{
_components = value;
}
}
public T GetComponent<T>() where T : Component
{
foreach (Component component in _components)
{
var componentType = component.GetType();
Debug.WriteLine(componentType);
if (componentType.Equals(typeof(T)))
{
return (T)component;
}
}
return null;
}
}
[MessagePackObject]
public class Component
{
[IgnoreMember]
public Entity entity;
}
[MessagePackObject]
public class Tile : Component
{
public enum TileType
{
Soil,
Mud,
}
[Key(0)]
public TileType Type { get; set; }
public Tile(TileType type)
{
Type = type;
}
}
Every Entity
has a Tile
(which inherits from Component
). Before serializing I check the type of the Tile
and it returns World2D.ECS.Components.Tile
.
Then I send the serialized Entity
to a client.
On the client I check reflection type of the component:
public T GetComponent<T>() where T : Component
{
foreach (Component component in _components)
{
var componentType = component.GetType();
Debug.WriteLine(componentType); // returns World2D.ECS.Components.Component instead of World2D.ECS.Components.Tile as on the server
if (componentType.Equals(typeof(T)))
{
return (T)component;
}
}
return null;
}
After deserealizing Entity
on the client, reflection returns World2D.ECS.Components.Component
instead of World2D.ECS.Components.Tile
.
Update 1: Confirmed that this doesn't occur due to sending the serialized Entity
over the network because the bug occurs even if serializing and deserializing on the same machine.
https://github.com/neuecc/MessagePack-CSharp/issues/1405
By default, type information is not included in the messagepack stream. The best way to add type information is to apply the [Union] attribute as described in the readme. You might also find the Typeless resolver can solve your problem, but that comes with security implications and a larger data size.