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

使用System.Text.Json序列化反序列化object属性时遇无效转换异常

解决System.Text.Json反序列化Object属性时的JsonElement转换错误

当你用System.Text.Json反序列化带有Object类型的属性时,默认会将该属性反序列化为JsonElement而非实际的.NET基本类型(如String、Boolean),这就是你遇到InvalidCastException的原因。以下是两种可行的解决方法:

方法一:自定义Object类型转换器(推荐)

通过自定义JsonConverter,让System.Text.Json自动将JSON值转换为对应的.NET基本类型,无需手动处理JsonElement。

  1. 创建自定义转换器类:
Public Class ObjectConverter
    Inherits JsonConverter(Of Object)

    Public Overrides Function Read(ByVal reader As Utf8JsonReader, ByVal typeToConvert As Type, ByVal options As JsonSerializerOptions) As Object
        Return reader.TokenType Switch
            JsonTokenType.String => reader.GetString(),
            JsonTokenType.Number => If(reader.TryGetInt64(out Dim longValue), longValue, reader.GetDouble()),
            JsonTokenType.True => True,
            JsonTokenType.False => False,
            JsonTokenType.Null => Nothing,
            ' 若需要处理数组或复杂对象,可在此扩展逻辑
            Else => JsonDocument.ParseValue(ref reader).RootElement.Clone()
        End Switch
    End Function

    Public Overrides Sub Write(ByVal writer As Utf8JsonWriter, ByVal value As Object, ByVal options As JsonSerializerOptions)
        JsonSerializer.Serialize(writer, value, value.GetType(), options)
    End Sub
End Class
  1. 在序列化配置中添加该转换器:
    修改你的GetJsonSerializerOptions方法,将自定义转换器加入配置:
Private Function GetJsonSerializerOptions() As JsonSerializerOptions
    Return New JsonSerializerOptions() With {
        .PropertyNamingPolicy = Nothing,
        .WriteIndented = True,
        .AllowTrailingCommas = True,
        .DefaultIgnoreCondition = JsonIgnoreCondition.WhenWritingNull,
        .Converters = {New ObjectConverter()}
    }
End Function

这样配置后,Answer属性在反序列化时会自动转换为对应的.NET类型(字符串、布尔值、数字等),直接使用即可。

方法二:手动处理JsonElement类型转换

如果不想修改全局序列化配置,可以在使用Answer属性时,先判断类型并手动转换:

If TypeOf Answer Is JsonElement Then
    Dim jsonElement = DirectCast(Answer, JsonElement)
    Select Case jsonElement.ValueKind
        Case JsonValueKind.String
            Dim strAnswer = jsonElement.GetString()
            ' 处理字符串类型的Answer
        Case JsonValueKind.True, JsonValueKind.False
            Dim boolAnswer = jsonElement.GetBoolean()
            ' 处理布尔类型的Answer
        Case JsonValueKind.Number
            If jsonElement.TryGetInt64(out Dim intAnswer) Then
                ' 处理整数类型
            Else
                Dim doubleAnswer = jsonElement.GetDouble()
                ' 处理浮点数类型
            End If
        Case JsonValueKind.Null
            ' 处理空值
    End Select
Else
    ' 此时Answer已经是实际的.NET类型,直接使用
    Dim actualValue = Answer
End If

注意事项

  • 如果Answer属性需要存储复杂自定义对象,方法一中的转换器需要扩展处理逻辑,将JsonElement反序列化为对应的自定义类型。
  • 方法一的全局配置会影响所有Object类型属性的序列化/反序列化行为,适合全局统一处理的场景;方法二更灵活,适合局部处理特定属性的场景。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.10 03:35:24