我正在努力有条件地序列化一个对象的属性,该属性是另一个对象本身的属性。考虑以下类结构:
public class Message
{
public string Content { get; set; }
public IEnumerable<Attachment> Attachments { get; set; }
}
public class Attachment
{
public string Base64Content { get; set; }
public string FileName { get; set; }
}
在某些情况下,我想序列化 Message
类中的所有内容,包括所有 Attachment
对象及其属性。这可以通过使用简单的 JsonConvert.SerializeObject()
来完成。如果我一直想忽略 Base64Content
属性,我可以只在该属性上添加一个“[JsonIgnore]”属性。但是,在某些情况下我希望序列化 Base64Content
,而在其他情况下我不需要。
我想创建一个自定义 ContractResolver
,它会忽略 Message
对象的 Attachments
属性。但当然,这会忽略 Attachment
对象的整个列表,而不仅仅是 Base64Content
属性。
有没有一种方法可以编写一个 ContractResolver
类,让我在序列化 Message
对象时忽略 Base64Content
属性?
最佳答案
只需创建一个自定义契约解析器,它在序列化时排除传递给它的属性,并有条件地传递其中的 Base64Content
属性。
public class CustomPropertiesContractResolver : DefaultContractResolver
{
private HashSet<string> _propertySet;
public CustomPropertiesContractResolver(IEnumerable<string> propertyNames)
{
if (propertyNames != null)
{
_propertySet = new HashSet<string>(propertyNames, StringComparer.OrdinalIgnoreCase);
}
}
protected override List<MemberInfo> GetSerializableMembers(Type objectType)
{
List<MemberInfo> serializableMembers = null;
var allMembers = base.GetSerializableMembers(objectType);
if (_propertySet != null && _propertySet.Count > 0)
{
serializableMembers = allMembers.Where(m => !_propertySet.Contains(m.Name)).ToList();
}
return serializableMembers != null && serializableMembers.Count > 0 ? serializableMembers : allMembers;
}
}
像这样使用它:
IEnumerable<string> properties = null;
if (condition)
{
properties = new List<string> { "Base64Content" };
}
var settings = new JsonSerializerSettings()
{
ContractResolver = new CustomPropertiesContractResolver(properties)
};
var serializedStr = JsonConvert.SerializeObject(messages, settings);
关于c# - 序列化对象时有条件地忽略嵌套属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45978898/