我使用基本身份验证来传递凭据进行授权。这将把凭据放在头部中。通过使用JQuery ajax函数的beforeSend事件处理程序,这样做非常简单。以下是如何执行此操作的示例。
getAuthorizationHeader = function (username, password) {
var authType;
var up = $.base64.encode(username + ":" + password);
authType = "Basic " + up;
};
return authType;
};
$.ajax({
url: _url,
data: _data,
type: _type,
beforeSend: function (xhr) {
xhr.setRequestHeader("Authorization", getAuthorizationHeader(username, password));
},
success: ajaxSuccessHandler,
error: ajaxErrHandler
});
这个编码了在头部发送的用户名/密码。请注意,仅仅使用编码是不够安全的,因为它很容易被解码。您仍然需要使用HTTPS/SSL来确保通过网络发送的信息是安全的。
在Web API方面,您可以创建一个自定义的AuthorizeAttribute,从头部获取凭据,对其进行解码,并执行授权过程。与控制器不同,Web API使用单独的AuthorizeAttribute。在创建自定义AuthorizeAttribute时,请确保使用System.Web.Http.AuthorizeAttribute作为基类。它们有不同的行为。控制器的AuthorizeAttribute将要重定向到登录页面,而Web API的AuthorizeAttribute则返回表示成功或失败的HTTP代码。如果授权失败,则我会返回HTTP代码Forbidden,以区分由于授权而不是身份验证导致的失败,以便客户端可以相应地做出反应。
以下是一个示例方法,用于从头部获取凭据,可用于自定义AuthorizeAttribute。
private bool GetUserNameAndPassword(HttpActionContext actionContext, out string username, out string password)
{
bool gotIt = false;
username = string.Empty;
password = string.Empty;
IEnumerable<string> headerVals;
if (actionContext.Request.Headers.TryGetValues("Authorization", out headerVals))
{
try
{
string authHeader = headerVals.FirstOrDefault();
char[] delims = { ' ' };
string[] authHeaderTokens = authHeader.Split(new char[] { ' ' });
if (authHeaderTokens[0].Contains("Basic"))
{
string decodedStr = SecurityHelper.DecodeFrom64(authHeaderTokens[1]);
string[] unpw = decodedStr.Split(new char[] { ':' });
username = unpw[0];
password = unpw[1];
}
gotIt = true;
}
catch { gotIt = false; }
}
return gotIt;
}
这里是用于解码此方法中使用的头数据的代码。
public static string DecodeFrom64(string encodedData)
{
byte[] encodedDataAsBytes
= System.Convert.FromBase64String(encodedData);
string returnValue =
System.Text.Encoding.ASCII.GetString(encodedDataAsBytes);
return returnValue;
}
一旦您拥有用户名和密码,您可以执行授权过程并返回适当的HTTP代码以供客户端处理。
更新于2013年3月8日
我写了一篇博客文章,详细介绍了如何使用SimpleMembership(MVC 4互联网应用程序的默认成员资格提供程序)实现此功能。它还包括一个可下载的VS 2012项目来实现这一点。