从web api 2帐户注册中返回错误

时间:2015-12-23 20:26:48

标签: c# asp.net json asp.net-mvc asp.net-web-api2

我正在尝试使用MVC项目中的帐户控制器来调用WebApi 2帐户控制器中的注册帐户方法。一切正常但我无法弄清楚如何将错误返回到MVC项目,例如:“密码必须包含大写和小写”等。

ASP.NET MVC帐户控制器注册:

//
    // POST: /Account/Register
    [HttpPost]
    [AllowAnonymous]
    [ValidateAntiForgeryToken]
    public async Task<ActionResult> Register(RegisterViewModel model)
    {
        if (ModelState.IsValid)
        {
            var response =
            await
                ApiRequest.PostAsync(String.Format("{0}/api/v1/account/register", "http://localhost:12345"), model);

            if (response.IsSuccessStatusCode)
            {
                return RedirectToAction("Index", "Home");

            }
            // Add errors

        }

        // If we got this far, something failed, redisplay form
        return View(model);
    }

ApiRequest类:

public static class ApiRequest
{
    public static async Task<HttpResponseMessage> PostAsync(string uri, object item)
    {
        StringContent content = new StringContent(await Json.SerializeAsync(item));
        content.Headers.ContentType = new MediaTypeHeaderValue("text/json");

        using (var client = new HttpClient())
        {
            client.DefaultRequestHeaders.Accept.Clear();
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

            return await client.PostAsync(new Uri(uri), content);
        }
    }

    public static async Task<HttpResponseMessage> GetAsync(string uri)
    {
        using (var client = new HttpClient())
        {
            client.DefaultRequestHeaders.Accept.Clear();
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

            return await client.GetAsync(new Uri(uri));
        }
    }

    public static async Task<HttpResponseMessage> PutAsync(string uri, object item)
    {
        StringContent content = new StringContent(await Json.SerializeAsync(item));
        content.Headers.ContentType = new MediaTypeHeaderValue("text/json");

        using (var client = new HttpClient())
        {
            client.DefaultRequestHeaders.Accept.Clear();
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

            return await client.PutAsync(new Uri(uri), content);
        }
    }

    public static async Task<HttpResponseMessage> DeleteAsync(string uri, object id)
    {
        using (var client = new HttpClient())
        {
            client.DefaultRequestHeaders.Accept.Clear();
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));

            return await client.DeleteAsync(new Uri(String.Format("{0}/{1}", uri, id)));
        }
    }
}

public static class HttpResponseMessageExtensions
{
    public static async Task<T> DeserialiseContentAsync<T>(this HttpResponseMessage message)
        where T : class
    {

        return await Json.DeserialiseAsync<T>(await message.Content.ReadAsStringAsync());
    }
}

Web API 2帐户控制器注册:

//
    // POST: /Account/Register
    [AllowAnonymous]
    [Route("Register")]
    [HttpPost]
    public async Task<IHttpActionResult> Register(RegisterViewModel model)
    {
        if (!ModelState.IsValid)
        {
            return BadRequest(ModelState);
        }

        var user = new ApplicationUser
        {
            UserName = model.Username,
            Email = model.Email,
            FirstName = model.FirstName,
            LastName = model.LastName
        };

        IdentityResult result = await UserManager.CreateAsync(user, model.Password);

        if (!result.Succeeded)
        {
            if (result.Errors != null)
            {
                foreach (string error in result.Errors)
                {
                    ModelState.AddModelError("", error);
                }
                return BadRequest(ModelState);
            }

            return BadRequest();
        }

        // Send email verification
        //string code = await UserManager.GenerateEmailConfirmationTokenAsync(user.Id);

        //var callbackUrl = new Uri(Url.Link("ConfirmEmail", new { userId = user.Id, code = code }));

        //await
        //    UserManager.SendEmailAsync(user.Id, "Confirm your account",
        //        "Please confirm your account by clicking <a href=\"" + callbackUrl + "\">here</a>");

        Uri locationHeader = new Uri(Url.Link("GetUserById", new { id = user.Id }));

        return Created(locationHeader, user);
    }

GetErrorResult代码:

private IHttpActionResult GetErrorResult(IdentityResult result)
    {
        if (result == null)
        {
            return InternalServerError();
        }

        if (!result.Succeeded)
        {
            if (result.Errors != null)
            {
                AddErrors(result);
            }

            if (ModelState.IsValid)
            {
                // No ModelState errors are available to send, so just return an empty BadRequest.
                return BadRequest();
            }

            return BadRequest(ModelState);
        }

        return null;
    }

    private void AddErrors(IdentityResult result)
    {
        foreach (string error in result.Errors)
        {
            ModelState.AddModelError("", error);
        }
    }

我是MVC和WebApi的新手并主要关注教程,这是基本的东西,但我无法在任何地方找到解决方案。我故意将WebApi与项目分开,这样我就可以了解这些过程如何更好地运作。

我希望解决方案不是在javascript中。

我假设所有后续请求都需要将一个持有者令牌附加到httpclient,但我认为这将是另一个问题。

提前感谢您对此的任何帮助

1 个答案:

答案 0 :(得分:0)

  

一切正常但我无法弄清楚如何将错误返回到MVC项目,例如:“密码必须包含大写和小写”等。

您可以在BadRequest()方法重载中发送自定义消息。在Model上执行自定义验证时,只返回自定义消息。

 if (ValidatePasswordPolicy(model.Password))
     {
        return BadRequest("password must contain Upper case and lower case.");
     }

更新

ModelStateAsp.net mvc app的{​​{1}}验证存在差异。当您使用WebAPI将错误放入ModelState时,您必须正确处理响应。正确处理意味着响应成功与否。如果没有则会出现WebAPI错误或其他错误。下面的代码段将向您展示如何将错误反序列化为ModelState并检查是否存在模型状态错误或其他错误。如果出现anonymous object错误,您只需将它们添加到ModelState并使用模型返回视图即可更新有错误的用户界面。

Asp.net mvc Model

有一篇关于在Asp.net mvc App here中处理WebAPI错误的详细文章。