ASP.NET Web API thực hiện thương lượng nội dung theo mặc định - sẽ trả về XML hoặc JSON hoặc kiểu khác dựa trên Accept
tiêu đề. Tôi không cần / muốn điều này, có cách nào (như thuộc tính hoặc thứ gì đó) để yêu cầu API Web luôn trả về JSON không?
ASP.NET Web API thực hiện thương lượng nội dung theo mặc định - sẽ trả về XML hoặc JSON hoặc kiểu khác dựa trên Accept
tiêu đề. Tôi không cần / muốn điều này, có cách nào (như thuộc tính hoặc thứ gì đó) để yêu cầu API Web luôn trả về JSON không?
Câu trả lời:
Chỉ hỗ trợ JSON trong API Web ASP.NET - CÁCH ĐÚNG
Thay thế IContentNegotiator bằng JsonContentNegotiator:
var jsonFormatter = new JsonMediaTypeFormatter();
//optional: set serializer settings here
config.Services.Replace(typeof(IContentNegotiator), new JsonContentNegotiator(jsonFormatter));
Triển khai JsonContentNegotiator:
public class JsonContentNegotiator : IContentNegotiator
{
private readonly JsonMediaTypeFormatter _jsonFormatter;
public JsonContentNegotiator(JsonMediaTypeFormatter formatter)
{
_jsonFormatter = formatter;
}
public ContentNegotiationResult Negotiate(
Type type,
HttpRequestMessage request,
IEnumerable<MediaTypeFormatter> formatters)
{
return new ContentNegotiationResult(
_jsonFormatter,
new MediaTypeHeaderValue("application/json"));
}
}
Accept
XML sẽ nhận được JSON và sẽ không nhận được 406 không?
Accept
tiêu đề.
GlobalConfiguration...Clear()
thực sự hoạt động.
Xóa tất cả các bộ định dạng và thêm lại bộ định dạng Json.
GlobalConfiguration.Configuration.Formatters.Clear();
GlobalConfiguration.Configuration.Formatters.Add(new JsonMediaTypeFormatter());
BIÊN TẬP
Tôi đã thêm nó vào Global.asax
bên trong Application_Start()
.
Philip W đã có câu trả lời đúng nhưng để rõ ràng và có giải pháp hoạt động hoàn chỉnh, hãy chỉnh sửa tệp Global.asax.cs của bạn để trông giống như sau: (Lưu ý rằng tôi phải thêm tham chiếu System.Net.Http.Formatting vào tệp được tạo sẵn)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http.Formatting;
using System.Web;
using System.Web.Http;
using System.Web.Mvc;
using System.Web.Optimization;
using System.Web.Routing;
namespace BoomInteractive.TrainerCentral.Server {
// Note: For instructions on enabling IIS6 or IIS7 classic mode,
// visit http://go.microsoft.com/?LinkId=9394801
public class WebApiApplication : System.Web.HttpApplication {
protected void Application_Start() {
AreaRegistration.RegisterAllAreas();
WebApiConfig.Register(GlobalConfiguration.Configuration);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
RouteConfig.RegisterRoutes(RouteTable.Routes);
BundleConfig.RegisterBundles(BundleTable.Bundles);
//Force JSON responses on all requests
GlobalConfiguration.Configuration.Formatters.Clear();
GlobalConfiguration.Configuration.Formatters.Add(new JsonMediaTypeFormatter());
}
}
}
GlobalConfiguration.Configuration.Formatters.XmlFormatter.SupportedMediaTypes.Clear();
Thao tác này sẽ xóa định dạng XML và do đó mặc định là định dạng JSON.
Lấy cảm hứng từ câu trả lời xuất sắc của Dmitry Pavlov, tôi đã sửa đổi nó một chút để có thể bổ sung bất kỳ định dạng nào mà tôi muốn thực thi.
Tín dụng cho Dmitry.
/// <summary>
/// A ContentNegotiator implementation that does not negotiate. Inspired by the film Taken.
/// </summary>
internal sealed class LiamNeesonContentNegotiator : IContentNegotiator
{
private readonly MediaTypeFormatter _formatter;
private readonly string _mimeTypeId;
public LiamNeesonContentNegotiator(MediaTypeFormatter formatter, string mimeTypeId)
{
if (formatter == null)
throw new ArgumentNullException("formatter");
if (String.IsNullOrWhiteSpace(mimeTypeId))
throw new ArgumentException("Mime type identifier string is null or whitespace.");
_formatter = formatter;
_mimeTypeId = mimeTypeId.Trim();
}
public ContentNegotiationResult Negotiate(Type type, HttpRequestMessage request, IEnumerable<MediaTypeFormatter> formatters)
{
return new ContentNegotiationResult(_formatter, new MediaTypeHeaderValue(_mimeTypeId));
}
}
Nếu bạn chỉ muốn làm điều đó cho một phương thức, hãy khai báo phương thức của bạn là trả về HttpResponseMessage
thay vì IEnumerable<Whatever>
và thực hiện:
public HttpResponseMessage GetAllWhatever()
{
return Request.CreateResponse(HttpStatusCode.OK, new List<Whatever>(), Configuration.Formatters.JsonFormatter);
}
mã này là khó khăn cho thử nghiệm đơn vị nhưng điều đó cũng có thể xảy ra như thế này:
sut = new WhateverController() { Configuration = new HttpConfiguration() };
sut.Configuration.Formatters.Add(new Mock<JsonMediaTypeFormatter>().Object);
sut.Request = new HttpRequestMessage();
Điều này đã được đặt đúng tiêu đề. Có vẻ thanh lịch hơn một chút.
public JsonResult<string> TestMethod()
{
return Json("your string or object");
}
cho những người sử dụng OWIN
GlobalConfiguration.Configuration.Formatters.Clear();
GlobalConfiguration.Configuration.Formatters.Add(new JsonMediaTypeFormatter());
trở thành (trong Startup.cs):
public void Configuration(IAppBuilder app)
{
OwinConfiguration = new HttpConfiguration();
ConfigureOAuth(app);
OwinConfiguration.Formatters.Clear();
OwinConfiguration.Formatters.Add(new DynamicJsonMediaTypeFormatter());
[...]
}
GlobalConfiguration.Configuration.Formatters