强制ASP.NET MVC中Json()的小写属性名称

鉴于以下class级,

public class Result { public bool Success { get; set; } public string Message { get; set; } } 

我在这样的控制器操作中返回其中的一个,

 return Json(new Result() { Success = true, Message = "test"}) 

但是,我的客户端框架期望这些属性是小写成功和消息。 没有实际上必须有小写属性名称是一种方法来实现这个想法正常的Json函数调用?

实现这个的方法是像这样实现一个自定义的JsonResult

用自定义的JsonResult创build一个自定义的ValueType和序列化 (原始链接已死)

并使用一个替代的序列化程序,如JSON.NET

http://json.codeplex.com/

哪些支持这种行为例如

 Product product = new Product { ExpiryDate = new DateTime(2010, 12, 20, 18, 1, 0, DateTimeKind.Utc), Name = "Widget", Price = 9.99m, Sizes = new[] {"Small", "Medium", "Large"} }; string json = JsonConvert.SerializeObject( product, Formatting.Indented, new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() } ); //{ // "name": "Widget", // "expiryDate": "\/Date(1292868060000)\/", // "price": 9.99, // "sizes": [ // "Small", // "Medium", // "Large" // ] //} 

如果使用Web API,更改序列化器很简单,但不幸的是,MVC本身使用JavaScriptSerializer而没有select将其更改为使用JSON.Net。

詹姆斯的答案和丹尼尔的答案给了你JSON.Net的灵活性,但意味着无论你通常会做什么return Json(obj)你必须改变return new JsonNetResult(obj)或类似的,如果你有一个大项目可以certificate一个问题,如果你改变你想要使用的序列化程序的想法也不是很灵活。


我决定走下ActionFilter路线。 下面的代码允许你使用JsonResult进行任何操作,并简单地使用一个属性来使用JSON.Net(具有小写属性):

 [JsonNetFilter] [HttpPost] public ActionResult SomeJson() { return Json(new { Hello = "world" }); } // outputs: { "hello": "world" } 

你甚至可以将它设置为自动适用于所有操作(只有is检查的次要性能):

FilterConfig.cs

 // ... filters.Add(new JsonNetFilterAttribute()); 

代码

 public class JsonNetFilterAttribute : ActionFilterAttribute { public override void OnActionExecuted(ActionExecutedContext filterContext) { if (filterContext.Result is JsonResult == false) return; filterContext.Result = new CustomJsonResult((JsonResult)filterContext.Result); } private class CustomJsonResult : JsonResult { public CustomJsonResult(JsonResult jsonResult) { this.ContentEncoding = jsonResult.ContentEncoding; this.ContentType = jsonResult.ContentType; this.Data = jsonResult.Data; this.JsonRequestBehavior = jsonResult.JsonRequestBehavior; this.MaxJsonLength = jsonResult.MaxJsonLength; this.RecursionLimit = jsonResult.RecursionLimit; } public override void ExecuteResult(ControllerContext context) { if (context == null) throw new ArgumentNullException("context"); if (this.JsonRequestBehavior == JsonRequestBehavior.DenyGet && String.Equals(context.HttpContext.Request.HttpMethod, "GET", StringComparison.OrdinalIgnoreCase)) throw new InvalidOperationException("GET not allowed! Change JsonRequestBehavior to AllowGet."); var response = context.HttpContext.Response; response.ContentType = String.IsNullOrEmpty(this.ContentType) ? "application/json" : this.ContentType; if (this.ContentEncoding != null) response.ContentEncoding = this.ContentEncoding; if (this.Data != null) { var json = JsonConvert.SerializeObject( this.Data, new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() }); response.Write(json); } } } } 

用我的解决scheme,你可以重命名每个你想要的属性。

我在这里find了解决scheme的一部分

 public class JsonNetResult : ActionResult { public Encoding ContentEncoding { get; set; } public string ContentType { get; set; } public object Data { get; set; } public JsonSerializerSettings SerializerSettings { get; set; } public Formatting Formatting { get; set; } public JsonNetResult(object data, Formatting formatting) : this(data) { Formatting = formatting; } public JsonNetResult(object data):this() { Data = data; } public JsonNetResult() { Formatting = Formatting.None; SerializerSettings = new JsonSerializerSettings(); } public override void ExecuteResult(ControllerContext context) { if (context == null) throw new ArgumentNullException("context"); var response = context.HttpContext.Response; response.ContentType = !string.IsNullOrEmpty(ContentType) ? ContentType : "application/json"; if (ContentEncoding != null) response.ContentEncoding = ContentEncoding; if (Data == null) return; var writer = new JsonTextWriter(response.Output) { Formatting = Formatting }; var serializer = JsonSerializer.Create(SerializerSettings); serializer.Serialize(writer, Data); writer.Flush(); } } 

所以在我的控制器中,我可以做到这一点

  return new JsonNetResult(result); 

在我的模型中,我现在可以有:

  [JsonProperty(PropertyName = "n")] public string Name { get; set; } 

请注意,现在,您必须将JsonPropertyAttribute设置为要序列化的每个属性。