You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MessagePack与UnitsNet序列化报错:Int64转Enum无效转换的解决方法

解决UnitsNet UnitInfo MessagePack反序列化InvalidCastException问题

问题核心

反序列化时抛出InvalidCastException: 无法将System.Int64转换为System.Enum,本质是MessagePack将枚举数值以Int64类型读取后,直接强转枚举类型失败——C#不支持数值类型到枚举的直接强制转换,必须通过枚举解析方法处理。

具体解决步骤

1. 重构自定义Formatter为泛型版本

针对泛型UnitInfo<TEnum>创建专属Formatter,确保序列化/反序列化时正确处理枚举类型:

public class UnitInfoFormatter<TEnum> : IMessagePackFormatter<UnitInfo<TEnum>> 
    where TEnum : Enum
{
    public void Serialize(ref MessagePackWriter writer, UnitInfo<TEnum> value, MessagePackSerializerOptions options)
    {
        // 将枚举转为Int64写入MessagePack流
        var enumValue = (long)Convert.ChangeType(value.Unit, typeof(long));
        writer.Write(enumValue);
    }

    public UnitInfo<TEnum> Deserialize(ref MessagePackReader reader, MessagePackSerializerOptions options)
    {
        // 读取Int64数值后,解析为目标枚举类型
        long rawValue = reader.ReadInt64();
        TEnum targetEnum = (TEnum)Enum.Parse(typeof(TEnum), rawValue.ToString());
        return new UnitInfo<TEnum>(targetEnum);
    }
}

2. 调整TestClass的Formatter绑定

在TestClass的属性上指定对应的泛型Formatter:

[MessagePackObject]
public class TestClass
{
    [Key(0), MessagePackFormatter(typeof(UnitInfoFormatter<LengthUnit>))]
    public UnitInfo<LengthUnit> MyProperty { get; set; }
}

3. 正确注册CompositeResolver

确保泛型Formatter被纳入MessagePack的解析器链:

var customResolvers = new IMessagePackFormatter[]
{
    new UnitInfoFormatter<LengthUnit>()
};

var resolver = CompositeResolver.Create(
    customResolvers,
    StandardResolver.Instance
);

var serializeOptions = MessagePackSerializerOptions.Standard.WithResolver(resolver);

4. 剥离无关配置

你提到的JsonSerializerSettings和UnitsNetIQuantityJsonConverter是JSON序列化的配置,和MessagePack无关,直接移除或隔离,避免干扰MessagePack的序列化逻辑。

内容的提问来源于stack exchange,提问作者habib salimi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.01 05:10:26