如何获取与模型命名策略匹配的 JSON 属性名称?

时间:2021-03-17 18:16:45

标签: c# json.net

假设一个应用程序具有带有 CamelCasePropertyNamesContractResolver 的序列化程序设置并且我有一个模型:

public class Model
{
    public int Id { get; set; }

    [JsonProperty(Name = "content_text")]
    public string Text { get; set; }
}

我想找到一种方法来获取序列化程序在为每个属性序列化时生成的结果名称,以便以下内容成立:

string JsonName<T>(string cSharpPropertyName)
{
    //
}

JsonName<Model>(nameof(Model.Id)) == "id";
JsonName<Model>(nameof(Model.Text)) == "content_text";

我正在为自定义类型编写自定义反序列化器(JSON 转换器),我想将我的 Model 属性与 JSON 输入相匹配,但不区分大小写,但使用当前的序列化器策略。

我有想法只是将包装在新 JSON 对象中的每个传入 JToken 反序列化为 c# object 并检查结果属性名称,但它似乎不是很有效。有没有更好的方法来做到这一点?

1 个答案:

答案 0 :(得分:1)

您可以使用合同解析器本身来完成这项工作。

使您的 JsonName 方法接受一个 IContractResolver 作为参数以及属性名称。实现可能如下所示:

public static string JsonName<T>(string cSharpPropertyName, IContractResolver resolver) where T : class
{
    var contract = resolver.ResolveContract(typeof(T)) as JsonObjectContract;
    var property = contract?.Properties.FirstOrDefault(p => p.UnderlyingName == cSharpPropertyName);
    return property?.PropertyName;
}

在您的 JsonConverter 中,您可以从序列化程序中获取合约解析器,它作为参数提供给 ReadJson

public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
{
    var resolver = serializer.ContractResolver;
    ...
}
相关问题