ASP.NET Core Identity 系列之七

在这节中我们主要介绍在ASP.NET Core Identity如何使用Claims,ASP.NET Core Identity Claims是颁发给用户键值对(name=value)表示用户允许做什么。例如,驾驶执照颁发机构给个人颁发驾驶执照,如果驾照上的DOB是1990年12月21日,那么在这种情况下,claim name 是DOB,claim value是1990年12月21日,签发人是驾驶执照当局。这意味着用户是由驾驶执照当局授权驾驶汽车

在前面的Identity例子可以看到认证用户是基于用户邮箱和密码,我们也可以授权一个用户访问特定资源。注意Identity的Role是Claims,但不是所有Claims都是Role,ASP.NET Core Identity 通过使用claims 做授权和认证,这节我们将覆盖更详细细节。Identity Claims 授权,最简单的方法是检查claim value,并允许基于该值访问资源
创建一个ClaimsController控制器,修改Index方法返回 User.Claims,代码如下:
public class ClaimsController : Controller{ public ClaimsController() { } public IActionResult Index() { return View(User.Claims); }}
在ASP.NET Identity中如何获取用户的Claims呢? 我们可以通过HttpContext对象的User属性,它返回当前用户的ClaimsPrincipal对象,该对象包含用户的所有claims,我们将该对象通过View展示到浏览器,创建一个Index.cshtml在 Views->Claims 文件夹下,代码如下:
@model IEnumerable<System.Security.Claims.Claim>@{ ViewData["Title"] = "Claims";}<p class="container"> <p class="row mb-3"> <p class="col-sm"> <table class="table table-bordered align-middle"> <thead> <tr> <th>名称th> <th>颁发机构th> <th>类型th> <th>th> tr> thead> <tbody> @foreach (var claim in Model.OrderBy(x => x.Type)) { <tr> <td>@claim?.Subject?.Nametd> <td>@claim?.Issuertd> <td>@claim?.Typetd> <td>@claim?.Valuetd> tr> } tbody> table> p> p>p>

我们运行应用程序使用并使用如下邮箱和密码进行登陆(如果没有可以自行添加)

邮箱:tom@yahoo.com
密码:Coder77@

导航到 https://localhost:7296/Claims

1、创建和删除Claims

对一个用户创建和删除Identity Claims,首先创建一个新的Create.cshtml,在Views -> Claims 目录下,代码如下:

@{ ViewData["Title"] = "新增Claim";}"All" class="text-danger">p>
"post"> <p class="mb-3 row align-items-center"> <p class="col-sm-1"> <label for="ClaimType" class="control-label">Claim 类型:label> p> <p class="col-sm-11"> <input name="ClaimType" class="form-control" /> p> p> <p class="mb-3 row align-items-center"> <p class="col-sm-1"> <label for="ClaimValue">Claim 值:label> p> <p class="col-sm-11"> <input name="ClaimValue" class="form-control" /> p> p> <p class="mb-3 row align-items-center"> <p class="col-sm-11 offset-sm-1"> <button type="submit" class="btn btn-primary">保存button> <button asp-action="Index" class="btn btn-secondary"> 返回 button> p> p>form>
接下来,更新Index.cshtml并添加新增按钮和删除按钮
@model IEnumerable@{ ViewData["Title"] = "Claims";}class="container"> <p class="row mb-3"> <p class="col-sm-3"> <a asp-action="Create" class="btn btn-primary">新增a> p> <p class="col-sm-3">p> <p class="col-sm-3">p> <p class="col-sm-3">p> p> class="row mb-3"> <p class="col-sm"> <table class="table table-bordered align-middle"> <thead> <tr> <th>名称th> <th>颁发机构th> <th>类型th> <th>th> <td>删除td> tr> thead> <tbody> @foreach (var claim in Model.OrderBy(x => x.Type)) { <tr> <td>@claim?.Subject?.Nametd> <td>@claim?.Issuertd> <td>@claim?.Typetd> <td>@claim?.Valuetd> <td> <form asp-action="Delete" method="post"> <input type="hidden" name="claimValues" value="@claim?.Type;@claim?.Value;@claim?.Issuer" /> <button type="submit" class="btn btn-sm btn-danger"> 删除 button> form> td> tr> } tbody> table> p> p></p>
最后我们在ClaimsController添加新增和删除方法,与此同时我们将UserManager类通过构造函数依赖注入进去
public class ClaimsController : Controller{ private UserManager _userManager; public ClaimsController(UserManager userManager) { _userManager = userManager; } public IActionResult Index() { return View(User.Claims); } public IActionResult Create() => View(); [HttpPost] public async Task Create(string claimType, string claimValue) { var user = await _userManager.GetUserAsync(HttpContext.User); Claim claim = new Claim(claimType, claimValue, ClaimValueTypes.String); IdentityResult result = await _userManager.AddClaimAsync(user ?? new AppUser(), claim); if (result.Succeeded) return RedirectToAction("Index"); else Errors(result); return View(); } [HttpPost] public async Task Delete(string claimValues) { var user = await _userManager.GetUserAsync(HttpContext.User); string[] claimValuesArray = claimValues.Split(";"); string claimType = claimValuesArray[0], claimValue = claimValuesArray[1], claimIssuer = claimValuesArray[2]; Claim? claim = User.Claims.Where(x => x.Type == claimType && x.Value == claimValue && x.Issuer == claimIssuer).FirstOrDefault(); IdentityResult result = await _userManager.RemoveClaimAsync(user ?? new AppUser(), claim); if (result.Succeeded) return RedirectToAction("Index"); else  Errors(result); return View("Index"); } void Errors(IdentityResult result) { foreach (IdentityError error in result.Errors) ModelState.AddModelError("", error.Description); }}
新增方法

首先我们从_userManager.GetUserAsync()获取当前用户,接着我们添加Claim对象,最后我们将Claim对象添加到用户中。_userManager.AddClaimAsync()可以为用户创建claim

删除方法
删除方法获取Claim值,切割字符串之后我们获取到了claim type, claim value and claim issuer 对应的值,使用Linq获取选择的Claim
Claim claim = User.Claims.Where(x => x.Type == claimType && x.Value == claimValue && x.Issuer == claimIssuer).FirstOrDefault();
通过调用_userManager.RemoveClaimAsync()将用户Claim删除
2、测试

测试这个特性,运行应用程序并且使用tom用户进行登录,进入https://localhost:7296/Claims 页面,点击新增按钮:

我们在新增页面输入下面值:

每次创建完一个Claim,我们都需要重新登录,为了看到新的Claim我们必须重新登录一次:

现在我们通过点击删除按钮删除刚才创建的claim。每次删除完成之后我们需要重新登录一下,才能看到最新的数据状态

总结
这一节我们主要介绍什么是Claims,针对当前用户如何创建和删除Claims,以及在表格内显示用户当前登录用户所有Claims。下一节我们将介绍如何使用Claims创建相应的策略进行用户认证,

源代码地址:

https://github.com/bingbing-gui/Asp.Net-Core-Skill/tree/master/AspNetCore.Identity/Identity

展开阅读全文

页面更新:2024-03-29

标签:当局   应用程序   按钮   对象   邮箱   密码   代码   机构   方法   用户

1 2 3 4 5

上滑加载更多 ↓
推荐阅读:
友情链接:
更多:

本站资料均由网友自行发布提供,仅用于学习交流。如有版权问题,请与我联系,QQ:4156828  

© CopyRight 2008-2024 All Rights Reserved. Powered By bs178.com 闽ICP备11008920号-3
闽公网安备35020302034844号

Top