我正在寻找在我的 .NET Core Web API Controller 中返回带有 HTTP 状态代码的 JSON 的正确方法。我以前是这样使用的:
public IHttpActionResult GetResourceData()
{
return this.Content(HttpStatusCode.OK, new { response = "Hello"});
}
这是在 4.6 MVC 应用程序中,但现在使用 .NET Core 我似乎没有这个 IHttpActionResult
我有 ActionResult
并像这样使用:
public ActionResult IsAuthenticated()
{
return Ok(Json("123"));
}
但是服务器的响应很奇怪,如下图:
我只希望 Web API Controller 返回带有 HTTP 状态代码的 JSON,就像我在 Web API 2 中所做的那样。
最佳答案
以 JsonResult
响应的最基本版本是:
// GET: api/authors
[HttpGet]
public JsonResult Get()
{
return Json(_authorRepository.List());
}
但是,这对您的问题没有帮助,因为您无法明确处理自己的响应代码。
The way to get control over the status results, is you need to return a
ActionResult
which is where you can then take advantage of theStatusCodeResult
type.
例如:
// GET: api/authors/search?namelike=foo
[HttpGet("Search")]
public IActionResult Search(string namelike)
{
var result = _authorRepository.GetByNameSubstring(namelike);
if (!result.Any())
{
return NotFound(namelike);
}
return Ok(result);
}
请注意,以上两个示例均来自 Microsoft 文档中的一个很好的指南:Formatting Response Data
我经常遇到的问题是,我希望对我的 WebAPI 进行更精细的控制,而不是仅仅使用 VS 中“新项目”模板中的默认配置。
让我们确保您掌握了一些基础知识...
为了让您的 ASP.NET Core WebAPI 响应 JSON 序列化对象以及对状态代码的完全控制,您应该首先确保已包含 AddMvc()
ConfigureServices
方法中的服务,通常在 Startup.cs
中找到。
It's important to note that
AddMvc()
will automatically include the Input/Output Formatter for JSON along with responding to other request types.
如果您的项目需要完全控制并且您想严格定义您的服务,例如您的 WebAPI 将如何处理各种请求类型,包括 application/json
并且不响应对于其他请求类型(例如标准浏览器请求),您可以使用以下代码手动定义:
public void ConfigureServices(IServiceCollection services)
{
// Build a customized MVC implementation, without using the default AddMvc(), instead use AddMvcCore().
// https://github.com/aspnet/Mvc/blob/dev/src/Microsoft.AspNetCore.Mvc/MvcServiceCollectionExtensions.cs
services
.AddMvcCore(options =>
{
options.RequireHttpsPermanent = true; // does not affect api requests
options.RespectBrowserAcceptHeader = true; // false by default
//options.OutputFormatters.RemoveType<HttpNoContentOutputFormatter>();
//remove these two below, but added so you know where to place them...
options.OutputFormatters.Add(new YourCustomOutputFormatter());
options.InputFormatters.Add(new YourCustomInputFormatter());
})
//.AddApiExplorer()
//.AddAuthorization()
.AddFormatterMappings()
//.AddCacheTagHelper()
//.AddDataAnnotations()
//.AddCors()
.AddJsonFormatters(); // JSON, or you can build your own custom one (above)
}
您会注意到,我还提供了一种方法让您添加自己的自定义输入/输出格式化程序,以备您可能想要响应另一种序列化格式(protobuf、thrift 等)时使用。
上面的代码块大部分是 AddMvc()
方法的副本。但是,我们通过定义每一项服务来自行实现每项“默认”服务,而不是使用带有模板的预发布服务。我已经在代码块中添加了存储库链接,或者您可以查看 AddMvc()
from the GitHub repository. .
请注意,有一些指南会尝试通过“撤消”默认设置来解决这个问题,而不是一开始就不实现它...如果您考虑到这一点,我们现在正在使用 Open来源,这是多余的工作,糟糕的代码,坦率地说,这是一个很快就会消失的旧习惯。
我将向您展示一个非常直截了当的问题,只是为了解决您的问题。
public class FooController
{
[HttpPost]
public async Task<IActionResult> Create([FromBody] Object item)
{
if (item == null) return BadRequest();
var newItem = new Object(); // create the object to return
if (newItem != null) return Ok(newItem);
else return NotFound();
}
}
Content-Type
和 Accept
您需要确保您的 request 中的 Content-Type
和 Accept
header 设置正确。在您的情况下(JSON),您需要将其设置为 application/json
。
如果您希望 WebAPI 默认以 JSON 响应,无论请求 header 指定什么,您都可以通过几种方式来实现。
方式 1 如我之前推荐的文章 (Formatting Response Data) 所示,您可以在 Controller /操作级别强制使用特定格式。我个人不喜欢这种方法......但这里是为了完整性:
Forcing a Particular Format If you would like to restrict the response formats for a specific action you can, you can apply the [Produces] filter. The [Produces] filter specifies the response formats for a specific action (or controller). Like most Filters, this can be applied at the action, controller, or global scope.
[Produces("application/json")] public class AuthorsController
The
[Produces]
filter will force all actions within theAuthorsController
to return JSON-formatted responses, even if other formatters were configured for the application and the client provided anAccept
header requesting a different, available format.
方式 2 我的首选方法是让 WebAPI 以请求的格式响应所有请求。但是,如果它不接受请求的格式,则回退到默认(即 JSON)
首先,您需要在选项中注册它(我们需要修改默认行为,如前所述)
options.RespectBrowserAcceptHeader = true; // false by default
最后,通过简单地重新排序服务构建器中定义的格式化程序列表,网络主机将默认使用您位于列表顶部的格式化程序(即位置 0)。
更多信息可以在这里找到.NET Web Development and Tools Blog entry
https://stackoverflow.com/questions/42360139/