如何让System.Text.Json.JsonSerializer忽略指定类型的所有属性?
实现自定义注解让System.Text.Json忽略指定类型属性
需求是自定义[SomeJsonIgnoreAnnotation]注解,标记在类上后,所有包含该类型属性的类在序列化时,这些属性会被自动忽略,效果等同于标注[JsonIgnore]。
实现步骤
- 定义自定义注解
[AttributeUsage(AttributeTargets.Class)] public class SomeJsonIgnoreAnnotation : Attribute { }
- 实现自定义转换器工厂
这个工厂会识别标注了自定义注解的类型,序列化时跳过对应属性:
public class IgnoredTypeConverterFactory : JsonConverterFactory { public override bool CanConvert(Type typeToConvert) { return typeToConvert.GetCustomAttributes(typeof(SomeJsonIgnoreAnnotation), inherit: true).Any(); } public override JsonConverter CreateConverter(Type typeToConvert, JsonSerializerOptions options) { return (JsonConverter)Activator.CreateInstance( typeof(IgnoredTypeConverter<>).MakeGenericType(typeToConvert), BindingFlags.Instance | BindingFlags.Public, binder: null, args: new object[] { options }, culture: null)!; } private class IgnoredTypeConverter<T> : JsonConverter<T> { public IgnoredTypeConverter(JsonSerializerOptions options) { } public override T Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { return default!; } public override void Write(Utf8JsonWriter writer, T value, JsonSerializerOptions options) { writer.Skip(); } } }
- 使用示例
// 标记自定义注解的类 [SomeJsonIgnoreAnnotation] class MySecret { public int Secret { get; set; } = 1; } class A { public MySecret SecretA { get; set; } = new(); public string NormalProp { get; set; } = "A的正常属性"; } class B { public MySecret SecretB { get; set; } = new(); public int NormalInt { get; set; } = 100; } // 序列化配置与测试 var options = new JsonSerializerOptions(); options.Converters.Add(new IgnoredTypeConverterFactory()); var a = new A(); string jsonA = JsonSerializer.Serialize(a, options); // 输出:{"NormalProp":"A的正常属性"} var b = new B(); string jsonB = JsonSerializer.Serialize(b, options); // 输出:{"NormalInt":100}
原理说明
自定义转换器工厂会检查属性的类型是否带有[SomeJsonIgnoreAnnotation],如果匹配,就使用对应的转换器处理:序列化时直接跳过该属性的写入操作,反序列化时返回类型默认值,从而实现全局忽略该类型属性的效果。
内容的提问来源于stack exchange,提问作者XWX
相关产品推荐
相关产品推荐

