It is a useful question?? and I hope this help:
A)
If you have created your models manually (without Entity Framework
), mark the relation properties as virtual
first.
If your models were created by EF
, It has already done it for you and each Relation Property
is marked as virtual
, as seen below:
Sample class:
public class PC
{
public int FileFolderId {get;set;}
public virtual ICollection<string> Libs { get; set; }
public virtual ICollection<string> Books { get; set; }
public virtual ICollection<string> Files { get; set; }
}
B)
Those relation properties can now be ignored by the JSON
serializer by using the following ContractResolver
for JSON.NET
:
CustomResolver:
class CustomResolver : DefaultContractResolver
{
private readonly List<string> _namesOfVirtualPropsToKeep=new List<string>(new String[]{});
public CustomResolver(){}
public CustomResolver(IEnumerable<string> namesOfVirtualPropsToKeep)
{
this._namesOfVirtualPropsToKeep = namesOfVirtualPropsToKeep.Select(x=>x.ToLower()).ToList();
}
protected override JsonProperty CreateProperty(MemberInfo member, MemberSerialization memberSerialization)
{
JsonProperty prop = base.CreateProperty(member, memberSerialization);
var propInfo = member as PropertyInfo;
if (propInfo != null)
{
if (propInfo.GetMethod.IsVirtual && !propInfo.GetMethod.IsFinal
&& !_namesOfVirtualPropsToKeep.Contains(propInfo.Name.ToLower()))
{
prop.ShouldSerialize = obj => false;
}
}
return prop;
}
}
C)
Finally, to serialize your model easily use the above ContractResolver
. Set it up like this:
// -------------------------------------------------------------------
// Serializer settings
JsonSerializerSettings settings = new JsonSerializerSettings
{
// ContractResolver = new CustomResolver();
// OR:
ContractResolver = new CustomResolver(new []
{
nameof(PC.Libs), // keep Libs property among virtual properties
nameof(PC.Files) // keep Files property among virtual properties
}),
PreserveReferencesHandling = PreserveReferencesHandling.None,
ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
Formatting = Formatting.Indented
};
// -------------------------------------------------------------------
// Do the serialization and output to the console
var json = JsonConvert.SerializeObject(new PC(), settings);
Console.WriteLine(json);
// -------------------------------------------------------------------
// We can see that "Books" filed is ignored in the output:
// {
// "FileFolderId": 0,
// "Libs": null,
// "Files": null
// }
Now, all the navigation (relation) properties [virtual
properties] will be ignored automatically except you keep some of them by determine them in your code.??
Thanks from @BrianRogers for his answer here.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…