讓 Web API 預設傳回 JSON 字串
ASP.NET MVC 4 Beta 版是採用 .NET 自家的 DataContractJsonSerializer 來處理 JSON 的序列化工作,不是那麼好用,而正式版已經改用 Json.NET 作為預設的序列化工具,也就不再需要額外寫 media type formatter 來取代預設的序列化工具了。
可是 Web API 會因為瀏覽器送出的 Accept 標頭而傳回不同的格式,例如 IE 會取得 JSON,並詢問要開啟檔案還是另存檔案;Chrome 則會取得 XML 格式的回應。其中原委可參考保哥的文章:如何讓 ASP.NET Web API 無論任何要求都回應 JSON 格式。文中也有提到解法,是在 Global.asax 裡面的 Application_Start 事件中動手腳。另一種類似的解法是在 App_Start\WebApiConfig.cs 中處理,例如:
關鍵在後面兩行 code。
這解法是在 stackoverflow.com 上爬來的,其優點是依然保有傳回 XML 格式的能力,亦即預設傳回 JSON,但如果前端發出的 HTTP request 的 Accept 標頭是 "text/xml",就會傳回 XML。
範例程式
前面的手腳做完以後,底下的範例程式就能順利傳回 JSON 字串了。
你可以看到,TestJsonController 傳回的型別是 Dictionary<string, string>,但前端收到的會是已經自動幫你序列化的 JSON 字串,如下圖:
所以在寫 ASP.NET Web API 時,就不用自己寫 code 去處理 JSON 序列化的動作。如果像下面這樣畫蛇添足:
前端瀏覽器看到的 JSON 就會有一堆多餘的反斜線:
可是 Web API 會因為瀏覽器送出的 Accept 標頭而傳回不同的格式,例如 IE 會取得 JSON,並詢問要開啟檔案還是另存檔案;Chrome 則會取得 XML 格式的回應。其中原委可參考保哥的文章:如何讓 ASP.NET Web API 無論任何要求都回應 JSON 格式。文中也有提到解法,是在 Global.asax 裡面的 Application_Start 事件中動手腳。另一種類似的解法是在 App_Start\WebApiConfig.cs 中處理,例如:
public static class WebApiConfig { public static void Register(HttpConfiguration config) { config.Routes.MapHttpRoute( name: "DefaultApi", routeTemplate: "api/{controller}/{id}", defaults: new { id = RouteParameter.Optional } ); var appXmlType = config.Formatters.XmlFormatter.SupportedMediaTypes.FirstOrDefault(t => t.MediaType == "application/xml"); config.Formatters.XmlFormatter.SupportedMediaTypes.Remove(appXmlType); } }
關鍵在後面兩行 code。
這解法是在 stackoverflow.com 上爬來的,其優點是依然保有傳回 XML 格式的能力,亦即預設傳回 JSON,但如果前端發出的 HTTP request 的 Accept 標頭是 "text/xml",就會傳回 XML。
範例程式
前面的手腳做完以後,底下的範例程式就能順利傳回 JSON 字串了。
using System.Collections.Generic; using System.Web.Http; namespace MvcAppDemo1.Controllers.Api { public class TestJsonController : ApiController { public Dictionary<string, string> Get() { var result = new Dictionary<string, string>() { {"001", "Banana"}, {"002", "Apple"}, {"003", "Orange"} }; return result; } } }
你可以看到,TestJsonController 傳回的型別是 Dictionary<string, string>,但前端收到的會是已經自動幫你序列化的 JSON 字串,如下圖:
所以在寫 ASP.NET Web API 時,就不用自己寫 code 去處理 JSON 序列化的動作。如果像下面這樣畫蛇添足:
using System.Collections.Generic; using System.Web.Http; using NewtonSoft.Json; namespace MvcAppDemo1.Controllers.Api { public class TestJsonController : ApiController { public Dictionary<string, string> HandMadeJson() { var result = new Dictionary<string, string>() { {"001", "Banana"}, {"002", "Apple"}, {"003", "Orange"} }; return JsonConvert.SerializeObject(result); } } }
前端瀏覽器看到的 JSON 就會有一堆多餘的反斜線:
圖中網址列的紅色框不是框錯位置,而是跟後面的 Tip 5 要討論的議題有關。
資料來源: https://www.huanlintalk.com/2013/01/aspnet-web-api-and-json.html
留言
張貼留言