如何在我的JSON模型类中使用保留关键字作为标识符?

Mic*_*man 10 .net c# asp.net-mvc asp.net-web-api

我之前从未使用过Web API,但我需要一个接受/返回JSON对象的Web服务,并且使用它似乎是一个合理的事情.它看起来很简单(如果不是为了我的目的有点过分),但我需要处理的数据结构看起来像:

{
    "values":["foo", "bar"],
    "default":"bar"
}
Run Code Online (Sandbox Code Playgroud)

所以我去制作一个Model对象:

class DropDownValues {
    public string[] values { get; set; }
    public string default { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

问题是默认似乎是受保护的关键字.必须有一些方法可以解决这个问题,对吗?

mur*_*tgu 14

您可以在C#中使用关键字作为标识符,方法是在它们前面添加@.


Rad*_*ler 10

我建议采取不同的方式.保持您的C#对象模型尽可能多的标准(我不会使用@sign和C# keywords属性名称).

我们可以通过使用Json.NET功能来分离序列化(JSON)世界和C#对象.

使用最简单的一个是带属性的装饰:

[JsonProperty(PropertyName = "default")]
public string DefaultValue { get; set; }
Run Code Online (Sandbox Code Playgroud)

在这种情况下,我们必须在项目中引用Newtonsoft.Json.如果它必须是POCO,我们可以引入CustomResolver来自DefaultContractResolver并定义这些转换......

但我会说,在这种情况下,关注点的分离是一个更纯粹的解决方案

编辑:JSON合同解析器草案 (见评论)

重要说明:Newtonsoft.Json是Web API的一部分.它不仅是一个开源的,甚至MS团队都认为它是一个核心的JSON序列化器.

1)Newtonsoft.Json(作为Web.API的一部分)已经安装在您的解决方案中.所以你不必单独下载(nuget).它总是在你的packages文件夹中.因此,使用该属性只是添加引用.它在那里......

2)在保留POCO的同时,有一个小草案如何做属性的东西.正如我在此尝试解释的那样:POCO,行为和Peristance Igorance,为了保持POCO(例如我们从数据层上的NHibernate分层架构中获利),我们可以用a 替换属性Contract Resolver.我们的POCO库不需要引用任何东西

我们只需要扩展服务层:

public class MyResolver : DefaultContractResolver
{
    protected override JsonProperty CreateProperty(
         MemberInfo member,
         MemberSerialization memberSerialization)
    {

        var jProperty = base.CreateProperty(member, memberSerialization);

        var propertyInfo = member as PropertyInfo;
        if (propertyInfo == null)
        {
            return jProperty;
        }

        // just adjust in case if Property name is DefaultValue
        var isDefaultValueProeprty =
                  propertyInfo.Name.Equals("DefaultValue");

        if(isDefaultValueProeprty)
        {
            jProperty.PropertyName = "default";
        }

        return jProperty;
    }
    ...
Run Code Online (Sandbox Code Playgroud)

这样,我们所提供的相同的信息serailizer作为与[JsonPropertyAttribute].

现在,我们只需要使用它.有很多方法(例如全局),但我们只能为控制器执行此操作:

protected override void Initialize(HttpControllerContext context)
{
  base.Initialize(context);

  var jSettings = context.Configuration.Formatters.JsonFormatter.SerializerSettings;
  jSettings.ContractResolver = MyResolver;
}
Run Code Online (Sandbox Code Playgroud)