gpt4 book ai didi

c# - .Net Core API Controller 接受表单或正文数据

转载 作者:行者123 更新时间:2023-11-30 21:30:01 24 4
gpt4 key购买 nike

我有一个 API 操作,我希望它接受表单数据或原始 JSON。

这是我的功能

    [HttpPost]
public async Task<IActionResult> ExternalLogin([FromForm]ExternalLoginModel formModel, [FromBody]ExternalLoginModel bodyModel)
{

所以我希望他们能够以两种不同的方式发送相同的数据,当我用表单数据尝试这种方法时,我得到了 415 错误。当我尝试使用原始 JSON 时,它工作正常。

我希望能够将它保留在一个函数中,但如果我必须将它分成两个,那就这样吧。

最佳答案

不幸的是,如果主体模型绑定(bind)器无法解析请求主体,它会将请求短路,而不是简单地跳过对操作参数的绑定(bind)。

如果您真的想在一个操作中处理这两种内容类型,您可以为绕过此行为的 body 模型 Binder 实现一个输入格式化程序。如果请求具有表单内容类型,它可以通过假装绑定(bind)成功来实现。

格式化程序本身很简单:

/// <summary>
/// This input formatter bypasses the <see cref="BodyModelBinder"/> by returning a null result, when the request has a form content type.
/// When registered, both <see cref="FromBodyAttribute"/> and <see cref="FromFormAttribute"/> can be used in the same method.
/// </summary>
public class BypassFormDataInputFormatter : IInputFormatter
{
public bool CanRead(InputFormatterContext context)
{
return context.HttpContext.Request.HasFormContentType;
}

public Task<InputFormatterResult> ReadAsync(InputFormatterContext context)
{
return InputFormatterResult.SuccessAsync(null);
}
}

在你的启动类中,需要添加格式化程序:

services.AddMvc(options =>
{
options.InputFormatters.Add(new BypassFormDataInputFormatter());
});

在您的操作中,您仍然需要检查实际填充了两个参数中的哪一个:

[HttpPost]    
public async Task<IActionResult> ExternalLogin([FromForm] ExternalLoginModel formModel, [FromBody] ExternalLoginModel bodyModel)
{
ExternalLoginModel model;

// need to check if it is actually a form content type, as formModel may be bound to an empty instance
if (Request.HasFormContentType && formModel != null)
{
model = formModel;
}
else if (bodyModel != null)
{
model = bodyModel;
}

...

关于c# - .Net Core API Controller 接受表单或正文数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54886644/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com