本文我们将把关注Visual Studio用户认证模板中的 本地用户名/密码帐号特性。他们将其分为了两部分:帐户控制器具备如创建帐号和修改密码等功能;另一部分是在OAuth2认证服务器中进行的认证。我们从创建一个账户开始:

为了创建一个账户,我们需要Post到/api/account/register 节点,对应到帐号控制器的Register方法,这个方法允许匿名访问。

客户端可以这样做:


用户注册private async Task Register(string userName, string password)
{
var client = new HttpClient { BaseAddress = _baseAddress }; var data = new Dictionary<string, string>
{
{ “UserName”, userName },
{ “Password”, password },
{ “ConfirmPassword”, password }
}; var response = await client.PostAsync(
“api/account/register”,
new FormUrlEncodedContent(data));
response.EnsureSuccessStatusCode();
}

帐号控制器会使用ASP.NET的身份框架在本地数据库中创建一个新用户(在确认密码和确认密码相同的前提下)。

IdentityResult result = await UserManager.CreateAsync(user, model.Password);
IHttpActionResult errorResult = GetErrorResult(result); if (errorResult != null)
{
return errorResult;
} return Ok();

在真实的应用中你或许想要进行邮箱验证和其他的验证步骤,但那已经超出了例子的范围。客户端可以通过内建的OAuth2资源所有者节点为用户申请一个令牌,该节点为/token。更多的背景信息请参阅here.

客户端使用OAuth2Client 类似这样:

private async Task<TokenResponse> RequestToken(
string userName, string password)
{
var client = new OAuth2Client(
new Uri(_baseAddress.AbsoluteUri + “/token”));
return await client.RequestResourceOwnerPasswordAsync(userName, password);
}

微软提供的这个认证模板连接了一个所谓的提供商(ApplicationOAuthProvider.cs)作为认证服务器中间件。其中负责验证用户认证信息并创建一个认证“票”并将其转换为访问令牌返回的相关的方法是:calledGrantResourceOwnerCredentials 。

var user = await userManager.FindAsync(context.UserName, context.Password);

if (user == null)
{
context.SetError(
“invalid_grant”, “The user name or password is incorrect.”);
return;
} var oAuthIdentity = await userManager.CreateIdentityAsync(user,
context.Options.AuthenticationType);
var properties = CreateProperties(user.UserName);
var ticket = new AuthenticationTicket(oAuthIdentity, properties);
context.Validated(ticket);

注意:这个方法不仅进行了验证用户身份和创建令牌,它还将用户名作为了OAuth2返回中的一部分(作为一个额外的参数)。我猜测这仅仅是一个指导如何个性化的返回相关信息到客户端的示例,不需要强制进行一次额外的API访问来获取这些额外信息。由于这些信息没有签名,所以不要基于这个方法传输与安全相关的信息(对比OpenID连接身份令牌token

注意2:这个方法也可以设置一个应用Cookie。但我不觉得这是一个好的理由。

使用访问令牌,客户端下载将被允许访问帐号控制器中其他的管理功能(如:用户信息,修改密码,设置密码等)或者其他任何使用[Authorize] 标记的控制器。如:

private async Task<string> GetUserInfo(string token)
{
var client = new HttpClient { BaseAddress = _baseAddress };
client.SetBearerToken(token); var response = await client.GetStringAsync(“api/account/userInfo”);
return response;
}

最新文章

  1. LINUX 6.x 内核升级全过程
  2. 关于Java集合的小抄
  3. IPcamera
  4. Cucumber命令行接口
  5. [51单片机] EEPROM 24c02 [I2C代码封装-保存实现流水灯]
  6. PHP正则表达式基础入门
  7. Linux实时将所有输出重定向到文件
  8. Http请求的 HttpURLConnection 和 HttpClient
  9. python 笔记4-- 函数式编程
  10. js操作iframe框架时应该屡清楚的一些概念
  11. ASP.NET使用WebApi接口实现与Android客户端的交互(图片或字符串的接收与回传)
  12. shell之算数运算符、逻辑运算符、关系运算符、布尔运算符、文件测试运算符
  13. OO第四次博客作业!
  14. 2019.03.29 bzoj3323: [Scoi2013]多项式的运算(非旋treap)
  15. 【Spring】——声明式事务配置详解
  16. CF451E
  17. Python class NameError name &quot;xxx&quot; is not defined
  18. ViewpagerHandler
  19. Django之数据表增删改查
  20. Qt一步一步实现插件通信(附源码)

热门文章

  1. USB枚举过程(2)
  2. ucos创建任务的一般方法
  3. Unity3d:使用uWebKit插件嵌入网页,网页中的flv视频无法播放
  4. IIS7 “拒绝访问临时目录”
  5. CSS line-height 和 vertical-align 精解(上篇)
  6. android AChartEngine图标引擎
  7. 12.组合(Composition)
  8. NodeJs使用Mysql模块实现事务处理
  9. MyEclipse 编写 ExtJS 卡死问题解决方法
  10. Python学习入门基础教程(learning Python)--5.1 Python下文件处理基本过程