假设您有一个基于用户的应用程序的.net Web API服务器。用户使用用户名和密码登录应用程序,该用户名和密码将发送到服务器,并为应用程序提供访问令牌。
现在,应用程序想要显示用户信息(存储在数据库中的服务器上)。因此它向服务器发出http请求,并在标头中包含访问令牌。
如何限制服务器只向该应用程序发送该特定用户的相关信息,而不是其他任何人的信息。
有没有办法,当我收到他们的用户名和密码并创建一个令牌以便发回时,将他们的userId与该令牌相关联?所以现在当我收到/ GetUserFoodPreferences之类的请求时,我可以从令牌中获取userId并根据该ID查询我的数据库。
这是正确的方法吗?
答案 0 :(得分:10)
试试这个:
在您的项目中,转到Providers/ApplicationOAuthProvider.cs
,搜索方法public override Task TokenEndpoint(OAuthTokenEndpointContext context)
,然后在foreach
之后添加此行:
context.AdditionalResponseParameters.Add ("userID" context.Identity.GetUserId());
您的代码如下:
public override Task TokenEndpoint(OAuthTokenEndpointContext context)
{
foreach (KeyValuePair<string, string> property in context.Properties.Dictionary)
{
context.AdditionalResponseParameters.Add(property.Key, property.Value);
}
context.AdditionalResponseParameters.Add("userID",context.Identity.GetUserId());
return Task.FromResult<object>(null);
}
答案 1 :(得分:8)
将最常用的存储方式是将用户ID或与该用户连接的其他类型的ID存储在cookie中。然后,您可以检查该cookie(Request.Cookies [&#34; name&#34;];)以确认该用户身份。
编辑:如果您正在使用API控制器并正确验证您的用户,您可以使用:
HttpContext.Current.User.Identity.GetUserId();
注意:不要忘记import Microsoft.AspNet.Identity
库。
答案 2 :(得分:2)
我有一个类似的问题,我通过创建自定义的OAuthProvider来解决。
public class ApplicationOAuthProvider : OAuthAuthorizationServerProvider
{
private readonly IYourLoginLogic _loginLogic;
/// <summary>
/// Constructor
/// </summary>
public ApplicationOAuthProvider(IYourLoginLogic loginLogic)
{
_loginLogic = loginLogic;
}
public override Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
{
context.Validated();
return Task.FromResult<object>(null);
}
/// <summary>
/// Login the user with username and password.
/// </summary>
/// <param name="context">OAuthGrantResourceOwnerCredentialsContext</param>
/// <returns>Not used</returns>
public override Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
{
bool loginRst = _loginLogic.Login(context.UserName, context.Password);
if(!loginRst)
{
context.SetError("invalid_grant", "The user name or password is incorrect.");
}
else
{
var identity = new ClaimsIdentity(context.Options.AuthenticationType);
identity.AddClaim(new Claim(ClaimTypes.Name, context.UserName));
identity.AddClaim(new Claim("role", "user"));
context.Validated(identity);
}
return Task.FromResult<object>(null);
}
这样,用户名将包含在返回给客户端的令牌中。当客户端使用令牌发回请求时,您可以从请求的上下文中获取用户名,如下所示:
public class CustomizedAuthorizeAttribute : AuthorizeAttribute
{
public override void OnAuthorization(HttpActionContext actionContext)
{
base.OnAuthorization(actionContext);
string username = actionContext.RequestContext.Principal.Identity.Name;
// do something with the username
}
}
您需要为要保护的控制器或操作使用CustomizedAuthrize属性。
在我的情况下,它就像:
[CustomizedAuthorize]
public sealed class MyController : ApiController {......}