【问题标题】:ASP.NET Core 3.1 - PostAsync/PostAsJsonAsync method in Integration Test always returns Bad RequestASP.NET Core 3.1 - 集成测试中的 PostAsync/PostAsJsonAsync 方法总是返回错误请求
【发布时间】:2020-04-08 12:33:10
【问题描述】:

这是我在 AuthController 中的注册方法。

[HttpPost(ApiRoutes.Auth.Register)]
public async Task<IActionResult> Register(UserRegistrationRequest request)
{
    var authResponse = await _authService.RegisterAsync(request.Email, request.Password);

    if (!authResponse.Success)
    {
        return BadRequest(new AuthFailedResponse
        {
            Errors = authResponse.Errors
        });
    }

    return Ok(new AuthSuccessResponse
    {
        Token = authResponse.Token,
        RefreshToken = authResponse.RefreshToken
    });
}

我正在尝试使用TestClient.PostAsync() 方法调用此方法,不幸的是它总是返回错误请求。我已经尝试通过导入Microsoft.AspNet.WebApi.Client包调用TestClient.PostAsJsonAsync(ApiRoutes.Auth.Register, user)方法,结果是一样的。

var user = new UserRegistrationRequest
    {
        Email = "user1@testtest.com",
        Password = "P@ssw0rd1!!!!!"
    };

var response = await TestClient.PostAsync(
        ApiRoutes.Auth.Register,
        new StringContent(JsonConvert.SerializeObject(user), Encoding.UTF8)
        {
            Headers = { ContentType = new MediaTypeHeaderValue("application/json") }
        });

【问题讨论】:

  • 如果 authResponse 不成功,或者如果您设置了 [ApiController] 属性并且它正在执行自动模型验证,则您提供的信息不清楚 400 是否来自您自己对 BadRequest 的调用并在它到达您的方法之前返回 400 。如果您对此进行调试,它是否会触发您对 RegisterAsync() 的调用?
  • 我对它进行了更多调查,你是对的,它甚至没有达到 RegisterAsync()。我注意到输出窗口中出现“无法确定重定向集成测试的 https 端口”警告,所以我通过设置 HttpClient 的 BaseAddress 属性来修复它,警告消失了,测试仍然无法正常工作。困扰我的是这个控制器在招摇和邮递员中按预期工作。我还可以使用 GetAsync() 和 PostAsAsync() 方法在其他控制器中测试其他 get 和 post 调用。
  • 您没有提供 UserRegistrationRequest 的实现,但我们可以假设它只有您显示的两个属性(电子邮件和密码)吗?它没有遗漏任何会导致 400 的东西吗?另外,您实际上是否在此控制器上使用了 [ApiController] 属性?
  • 是的,它只有电子邮件和密码。我想知道问题是否与错误的对象序列化有关,因为它在这个线程https://stackoverflow.com/questions/33680203/httpclient-postasjsonasync)

标签: asp.net-core asp.net-web-api .net-core dotnet-httpclient


【解决方案1】:

您的操作参数中缺少FromBody 属性。当您将 json 数据发送到将成为请求正文的一部分的控制器时。您可以告诉控制器如何绑定传入的数据,在您的情况下是从正文。所以你的代码应该是这样的:

public async Task<IActionResult> Register([FromBody]UserRegistrationRequest request)
{
    …
}

您可以在official documentation 中阅读有关绑定的更多信息。

【讨论】:

    猜你喜欢
    • 2020-08-02
    • 2019-09-28
    • 2018-04-23
    • 1970-01-01
    • 2020-08-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多