在某些条件下序列化时忽略属性



Json.net有一个非常有用的属性,可以在JsonPropertyAttribute上设置称为NullValueHandling。如果你这样装饰一个属性:

[JsonProperty(NullValueHandling=NullValueHandling.Ignore)]
string MyProp { get; set; }

如果MyProp为null,则不包含在输出中。

我想做一些类似的事情,但是用不同的排除条件。例如-假设我们有一个enum

public enum MyEnum { None = 0, Value1 = 1, Value2 = 2, Value3 = 4 };

和属性

MyEnum MyProp { get; set; }

如果MyProp == MyEnum.None,那么我想将MyProp完全排除在输入之外。

我知道一个解决方案是使用MyEnum?而不是MyEnum,然后我可以再次使用NullValueHandling,但我不能在这里使用nullable。我想我可能能够使用JsonConverter,所以我尝试子类StringEnumConverter(因为我希望它们理想地输出为字符串):

    public class MyEnumConverter : Newtonsoft.Json.Converters.StringEnumConverter
    {            
        public override bool CanConvert(Type objectType)
        {
            return objectType == typeof(MyEnum);
        }
        public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
        {
            throw new NotImplementedException();
        }
        public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
        {
            // don't write if value is none
            var v = (MyEnum)value;
            if (v == MyEnum.None)
            {
                // what to do here? The two options below both include the property as null
                //writer.WriteNull();
                //serializer.Serialize(writer, null);
                return;        // just returning without doing anything will break the serialization
            }
            base.WriteJson(writer, value, serializer);
        }
    }

我可以,或者我应该,尝试子类化JsonProperty ?如果是这样,我需要重写什么来获得我想要的行为?

我希望避免必须附加一个转换器到包含此属性的类,因为这样我就必须手动序列化整个东西,这是一个痛苦。

可以使用签名为public bool ShouldSerialize*PropertyName*()的方法。

public enum MyEnum { None = 0, Value1 = 1, Value2 = 2, Value3 = 4 };
public class SomeClass
{
    public MyEnum MyProp { get; set; }
    public string Test = "aaaa";
    public bool ShouldSerializeMyProp()
    {
        return MyProp != MyEnum.None;
    }
}

var retVal1 = JsonConvert.SerializeObject(new SomeClass() { MyProp= MyEnum.None });
var retVal2 = JsonConvert.SerializeObject(new SomeClass() { MyProp = MyEnum.Value1 });
输出:

retVal1: {"Test":"aaaa"}

retVal2: {"Test":"aaaa","MyProp":1}

相关内容

  • 没有找到相关文章

最新更新