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

将属性从byte[]改为List<byte[]>时JSON序列化器报500错误如何解决?

Base64图片列表反序列化失败导致500错误

问题背景

通过纯JSON上传Base64编码图片,属性类型为byte[]时运行正常,但改为List<byte[]>以支持多文件上传后,出现500错误:

System.Private.CoreLib: Unable to cast object of type 'System.Byte[]' to type 'System.Collections.Generic.List`1[System.Byte[]]'

现有代码

原Json转换器

public class Base64FileJsonConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        return objectType == typeof(string);
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        if (reader?.Value == null) return Array.Empty<byte>();

        return Convert.FromBase64String(reader.Value as string);
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        throw new InvalidOperationException("Read only converter");
    }
}

模型属性定义

[ApiBodyParameter(
    IsOptional = true,
    Description = "List/array of BASE64 encoded image data for the item images"
    )]
[JsonConverter(typeof(Base64FileJsonConverter))]
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public List<byte[]> ResellImageBase64Data { get; set; }

尝试修改的失败代码

public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
    if (reader?.Value == null) return Array.Empty<byte>();

    var returnList = new List<byte[]>();

    foreach (var image in reader.ReadAsBytes())
    {
        var jongel = Convert.FromBase64String(image.ToString());

        returnList.Add(jongel);
    }

    return returnList;
}

问题原因

  1. 原转换器仅能处理单个字符串转byte[],但现在要处理的是字符串数组转List<byte[]>,CanConvert的判断逻辑完全不匹配当前属性类型。
  2. 将转换器直接挂在List<byte[]>属性上后,转换器仍返回单个byte[]实例,导致框架尝试将byte[]强制转换为List<byte[]>,触发类型转换异常。

解决方案

方案一:复用原转换器(推荐)

调整转换器的CanConvert逻辑,让它负责处理单个byte[]的反序列化,JSON.NET会自动处理数组到列表的转换:

  1. 修改转换器:
public class Base64FileJsonConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        // 改为支持byte[]类型
        return objectType == typeof(byte[]);
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        if (reader?.Value == null) return Array.Empty<byte>();

        return Convert.FromBase64String(reader.Value as string);
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        throw new InvalidOperationException("Read only converter");
    }
}
  1. 移除模型属性上的转换器(JSON.NET会自动遍历数组元素并应用转换器):
[ApiBodyParameter(
    IsOptional = true,
    Description = "List/array of BASE64 encoded image data for the item images"
    )]
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public List<byte[]> ResellImageBase64Data { get; set; }

方案二:编写支持列表的转换器

如果需要自定义列表级别的处理(比如空值兼容、特殊格式校验),可以编写专门处理List<byte[]>的转换器:

public class Base64FileListJsonConverter : JsonConverter
{
    public override bool CanConvert(Type objectType)
    {
        return objectType == typeof(List<byte[]>) || objectType == typeof(byte[]);
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        // 处理空值
        if (reader.TokenType == JsonToken.Null)
        {
            return objectType == typeof(List<byte[]>) ? new List<byte[]>() : Array.Empty<byte>();
        }

        // 处理单个Base64字符串(兼容旧格式)
        if (reader.TokenType == JsonToken.String)
        {
            var bytes = Convert.FromBase64String(reader.Value as string);
            return objectType == typeof(List<byte[]>) ? new List<byte[]> { bytes } : bytes;
        }

        // 处理Base64字符串数组
        if (reader.TokenType == JsonToken.StartArray)
        {
            var imageList = new List<byte[]>();
            while (reader.Read())
            {
                if (reader.TokenType == JsonToken.EndArray) break;
                if (reader.TokenType == JsonToken.String)
                {
                    imageList.Add(Convert.FromBase64String(reader.Value as string));
                }
            }
            return imageList;
        }

        throw new JsonSerializationException("无效的Base64图片数据格式");
    }

    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        throw new InvalidOperationException("Read only converter");
    }
}

然后在模型属性上使用这个新转换器:

[ApiBodyParameter(
    IsOptional = true,
    Description = "List/array of BASE64 encoded image data for the item images"
    )]
[JsonConverter(typeof(Base64FileListJsonConverter))]
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public List<byte[]> ResellImageBase64Data { get; set; }

内容的提问来源于stack exchange,提问作者Matt Douhan

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.04 01:25:29