ASP.NET Web API中的用户身份validation

这个话题对我来说令人难以置信的困惑。 我是HTTP应用程序的新手,但需要开发一个iPhone客户端,从某个地方使用JSON数据。 我从MSselect了Web API,因为它看起来很简单,但是当涉及到对用户进行身份validation时,事情变得非常令人沮丧。

我很惊讶我怎么能find一个清楚的例子,如何validation一个用户权限,从login屏幕到使用我的ApiController方法的Authorize属性几个小时的谷歌search后。

这不是一个问题,而是一个要求如何正确地做到这一点的例子。 我看了以下几页:

  • 使您的ASP.NET Web API的安全
  • 使用ASP.NET Web API的基本身份validation

尽pipe这些解释了如何处理未经授权的请求,但是这些并没有清楚地说明LoginController或类似的东西来请求用户凭证并validation它们。

任何人都愿意写一个很好的简单的例子或指向正确的方向吗?

谢谢。

我很惊讶我怎么能find一个清楚的例子,如何validation一个用户权限,从login屏幕到使用我的ApiController方法的授权属性几个小时的谷歌search后。

那是因为你对这两个概念感到困惑:

  • authentication是系统可以安全地识别用户的机制。 authentication系统提供了以下问题的答案:

    • 谁是用户?
    • 用户真正代表自己是谁吗?
  • 授权是系统确定特定authentication用户对系统控制的资源进行安全保护的机制。 例如,可以devise数据库pipe理系统,以便为某些指定的个人提供从数据库检索信息的能力,但不能改变存储在数据库中的数据,同时给予其他个人改变数据的能力。 授权系统提供了以下问题的答案:

    • 用户X是否有权访问资源R?
    • 用户X是否有权执行操作P?
    • 用户X是否被授权在资源R上执行操作P?

MVC中的Authorize属性用于应用访问规则,例如:

  [System.Web.Http.Authorize(Roles = "Admin, Super User")] public ActionResult AdministratorsOnly() { return View(); } 

上述规则将只允许AdminSuper Userangular色的用户访问该方法

这些规则也可以使用location元素在web.config文件中设置。 例:

  <location path="Home/AdministratorsOnly"> <system.web> <authorization> <allow roles="Administrators"/> <deny users="*"/> </authorization> </system.web> </location> 

但是,在执行这些授权规则之前,您必须对当前网站进行身份validation

尽pipe这些解释了如何处理未经授权的请求,但是这些并没有清楚地说明LoginController或类似的东西来请求用户凭证并validation它们。

从这里,我们可以把问题分成两部分:

  • 在同一Web应用程序中使用Web API服务时对用户进行身份validation

    这将是最简单的方法,因为您将依赖ASP.Net中的身份validation

    这是一个简单的例子:

    Web.config文件

     <authentication mode="Forms"> <forms protection="All" slidingExpiration="true" loginUrl="account/login" cookieless="UseCookies" enableCrossAppRedirects="false" name="cookieName" /> </authentication> 

    用户将被redirect到帐户/loginpath,在那里您将呈现自定义控件以要求用户凭据,然后您将使用以下设置身份validationCookie:

      if (ModelState.IsValid) { if (Membership.ValidateUser(model.UserName, model.Password)) { FormsAuthentication.SetAuthCookie(model.UserName, model.RememberMe); return RedirectToAction("Index", "Home"); } else { ModelState.AddModelError("", "The user name or password provided is incorrect."); } } // If we got this far, something failed, redisplay form return View(model); 
  • 跨平台authentication

    这种情况下,当您只在Web应用程序中公开Web API服务时 ,您将有另一个客户端使用服务,客户端可能是另一个Web应用程序或任何.Net应用程序(Win Forms,WPF,控制台,Windows服务,等等)

    例如,假设您将使用来自同一networking域(Int​​ranet内)的其他Web应用程序的Web API服务,在这种情况下,您可以依赖ASP.Net提供的Windows身份validation。

     <authentication mode="Windows" /> 

    如果您的服务在Internet上公开,那么您需要将经过身份validation的令牌传递给每个Web API服务。

    欲了解更多信息,请参阅以下文章:

如果您想要对用户名和密码进行身份validation并且没有授权cookie ,则MVC4 授权属性将无法正常工作。 但是,您可以将以下帮助程序方法添加到您的控制器以接受基本身份validation标头。 从你的控制器的方法开始调用它。

 void EnsureAuthenticated(string role) { string[] parts = UTF8Encoding.UTF8.GetString(Convert.FromBase64String(Request.Headers.Authorization.Parameter)).Split(':'); if (parts.Length != 2 || !Membership.ValidateUser(parts[0], parts[1])) throw new HttpResponseException(Request.CreateErrorResponse(HttpStatusCode.Unauthorized, "No account with that username and password")); if (role != null && !Roles.IsUserInRole(parts[0], role)) throw new HttpResponseException(Request.CreateErrorResponse(HttpStatusCode.Unauthorized, "An administrator account is required")); } 

从客户端,这个助手创build一个HttpClient的身份validation头:

 static HttpClient CreateBasicAuthenticationHttpClient(string userName, string password) { var client = new HttpClient(); client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", Convert.ToBase64String(UTF8Encoding.UTF8.GetBytes(userName + ':' + password))); return client; } 

我正在开发一个MVC5 / Web API项目,需要能够获得Web API方法的授权。 当我的索引视图第一次加载时,我调用了我认为是自动创build的'token'Web API方法。

客户端代码(CoffeeScript)获取令牌是:

 getAuthenticationToken = (username, password) -> dataToSend = "username=" + username + "&password=" + password dataToSend += "&grant_type=password" $.post("/token", dataToSend).success saveAccessToken 

如果成功,则调用以下内容,从而将身份validation令牌保存在本地:

 saveAccessToken = (response) -> window.authenticationToken = response.access_token 

然后,如果我需要对具有[Authorize]标签的Web API方法进行Ajax调用,则只需将以下标题添加到我的Ajax调用中:

 { "Authorization": "Bearer " + window.authenticationToken }