使用JsonConverter将JToken反序列化为bool时的转换报错如何解决
问题根源
你自定义的JsonConverter的ReadJson方法没有正确消费JSON令牌流,直接返回值后JsonReader的位置停在了isAllowed属性名的节点,Newtonsoft.Json会误将这个字符串当做外层Dictionary<int, PermissionValues>的键处理,自然抛出字符串转Int32失败的错误。
修复方案
- 补全
PermissionValues对应自定义转换器的逻辑,完整读取整个对象的所有令牌:
public class PermissionValuesConverter : JsonConverter<PermissionValues> { public override PermissionValues ReadJson(JsonReader reader, Type objectType, PermissionValues existingValue, bool hasExistingValue, JsonSerializer serializer) { var res = new PermissionValues(); if (reader.TokenType != JsonToken.StartObject) return res; reader.Read(); while (reader.TokenType == JsonToken.PropertyName) { var propName = reader.Value.ToString(); reader.Read(); if (propName.Equals(nameof(PermissionValues.IsAllowed), StringComparison.OrdinalIgnoreCase)) { // 空对象{}对应true,可按需调整逻辑 res.IsAllowed = reader.TokenType == JsonToken.StartObject; // 跳过空对象的闭合} if (reader.TokenType == JsonToken.StartObject) reader.Read(); } reader.Read(); } return res; } public override void WriteJson(JsonWriter writer, PermissionValues value, JsonSerializer serializer) { writer.WriteStartObject(); writer.WritePropertyName("isAllowed"); if (value.IsAllowed) { writer.WriteStartObject(); writer.WriteEndObject(); } else { writer.WriteNull(); } writer.WriteEndObject(); } }
- 注册转换器,二选一即可:
- 直接给
PermissionValues类加特性标记:
[JsonConverter(typeof(PermissionValuesConverter))] public class PermissionValues { public bool IsAllowed { get; set; } }
- 反序列化时传入配置:
var deserializeSettings = new JsonSerializerSettings { Converters = new List<JsonConverter> { new PermissionValuesConverter() } }; // 替换为你自己的外层类型 var result = JsonConvert.DeserializeObject<DataWrapper<Dictionary<int, Dictionary<DateTime, Dictionary<int, PermissionValues>>>>>(json, deserializeSettings);
内容的提问来源于stack exchange,提问作者Supergibbs
相关产品推荐
相关产品推荐

