HTML5技术

ASP.NET Core 认证与授权[2]:Cookie认证 - 雨の夜(3)

字号+ 作者:H5之家 来源:H5之家 2017-09-29 16:04 我要评论( )

退出则直接调用SignOutAsync方法即可: app.Map(/Account/Logout, builder = builder.Run(async context ={await context.SignOutAsync();context.Response.Redirect(/);}));首页 最后,添加一个简单的首页,方便测

退出则直接调用SignOutAsync方法即可:

app.Map("/Account/Logout", builder => builder.Run(async context => { await context.SignOutAsync(); context.Response.Redirect("/"); })); 首页

最后,添加一个简单的首页,方便测试:

app.Run(async context => { await context.Response.WriteHtmlAsync(async res => { await res.WriteAsync($"<h2>Hello Cookie Authentication</h2>"); await res.WriteAsync("<a class=\"btn btn-default\" href=\"/profile\">我的信息</a>"); }); }); 运行

在浏览器中打开:5000/,显示 "Hello Cookie Authentication",点击 “我的信息” 按钮:

请求: GET :5000/profile HTTP/1.1 Host: localhost:5000 响应: HTTP/1.1 302 Found Location: :5000/Account/Login?ReturnUrl=%2Fprofile

因为我们没有登录,会在授权中间件中会执行context.ChallengeAsync();方法,最终会跳转到登录页面,然后输入用户名密码(alice/alice),登录成功:

请求: POST :5000/Account/Login?ReturnUrl=%2Fprofile HTTP/1.1 Host: localhost:5000 Content-Type: application/x-www-form-urlencoded returnUrl=%2Fprofile&userName=alice&password=alice 响应: HTTP/1.1 302 Found Location: /profile Set-Cookie: .AspNetCore.Cookies=CfDJ8B4XRZETkRhMt3mT9VduB8KTzFhbcuszdNDXZpaQI3zSOcOD8uAzjr-iHzNCPVgXrKqxfK-MrP5d5r9X1zfKOgg2_j54t0ccAQ5nshSmXnRvjIZ6id3GD5fDP9v2x1iV0JE7X9IdoA458DZjx6qm6971GeY5HYVnT7odwgQR8eRaHo0-Wacmt95QuC9IVSapqsShHOeu5ZowFmDAPXrlUHOSwBPAjiLkf8mNbu8U4ZcWFlaBXC9-H-2_ts5wyi-90zw6jGxX3o7tRiQB4qq8IDmIJbZtN4Nl8TKHHcTbyFl5Z__MrgrjJ7s4cGdnIoDJWB9ENw1IGRgF3Rib8KmhkwhlUyO2VMnuVI8vSP2PcwrkUGtudJwHMHrA8cuS021xpmIhkhgW3e82r_0_jxAh1nqG4zwTP5i8iLU6FsOLLWatveSWB441Ntqw-L-pYczsBAYFRT0Hh56ofUAxGd7aaGtDx0jvuuxW5gK245Pf0TKG-4G46yDwLrFtjNcN_GREbpwtHAz-I7XqiDZgS3nbzjik5s05NxB7d6X3aOFc5JHCwFxW-i-xW-ToJLZrp3Jo8W0bAxVwxZIW2PwZlVtyeYSkqByFRaDS4qcBywE2Bmar_TyJm9UpVWaL2s9KxpU_DHN6meYne5E5dH4-k1DoABl6FyNPn6xYfMWxzu0_7ZFhVJjCycScy1jggCv4Hk5nkltj9A3QrFpNb_HCk21Uek9g-7Zi150EKfDzhGjMto5_hbWcmQtUsHuLbZlnYTHXZ-7zELZOepAUts2ZGoUnEaI; path=/; samesite=lax; httponly

可以看到,响应报文在Cookie中附加了身份令牌,并会跳转到之前未登录时访问的页面/profile,跳转后显示如下:

cookie_profile

如上,因为浏览器会自动附带上刚才写入的Cookie,所以授权通过,并展示出我们在登录时设置的Claim。

最后,点击 “退出” ,响应报文中会将Cookie设置为空(清除Cookie):

请求: GET :5000/Account/Logout HTTP/1.1 Host: localhost:5000 响应: HTTP/1.1 302 Found Location: / Set-Cookie: .AspNetCore.Cookies=; expires=Thu, 01 Jan 1970 00:00:00 GMT; path=/; samesite=lax 补充 JwtClaimTypes

在上面的演示中,我们可以看到Cookie中的值非常的长,而我们设置的Claim并不多,这是因为微软内置的ClaimTypes都是一大串的ULR地址。而对于 ASP.NET Core 本身来说,它并不关心你使用的ClaimType是什么,只要你读取与保存时使用的ClaimType保持一致就没有问题。我们可以使用简短的字符串name来代替ClaimTypes.Name,但是推荐的做法是直接使用JwtClaimTypes,因为它够简短而且通用。

首先添加ClaimTypes的Package引用:

dotnet add package IdentityModel --version 2.12.0

然后,将之前的添加Claim的代码修改如下:

var claimIdentity = new ClaimsIdentity("Cookie", JwtClaimTypes.Name, JwtClaimTypes.Role); claimIdentity.AddClaim(new Claim(JwtClaimTypes.Id, user.Id.ToString())); claimIdentity.AddClaim(new Claim(JwtClaimTypes.Name, user.Name)); claimIdentity.AddClaim(new Claim(JwtClaimTypes.Email, user.Email)); claimIdentity.AddClaim(new Claim(JwtClaimTypes.PhoneNumber, user.PhoneNumber)); claimIdentity.AddClaim(new Claim(JwtClaimTypes.BirthDate, user.Birthday.ToString()));

需要注意的是在创建ClaimsIdentity时需要手动指定它的NameType和RoleType,否则它将会使用默认的ClaimTypes.Name和ClaimTypes.Role,这样会导致我们从ClaimsPrincipal中获取Identity.Name属性和执行IsInRole检查时失败。

运行,重新登录,看看效果如何:

请求: POST :5000/Account/Login?ReturnUrl=%2Fprofile HTTP/1.1 Host: localhost:5000 Content-Type: application/x-www-form-urlencoded returnUrl=%2Fprofile&userName=alice&password=alice 响应: HTTP/1.1 302 Found Date: Sun, 24 Sep 2017 06:04:28 GMT Location: /profile Set-Cookie: .AspNetCore.Cookies=CfDJ8B4XRZETkRhMt3mT9VduB8JV9NE2zJ9YVQmTpAU3E9Op9rQHvJ7WvdcrarbTGWE7c_e2aLpoZCdDJ7-0fTFZGUwuLVMC0vD_eeE9ct2Vj7gHCPCVeK3qQPsQ2lNmKvPwPf82-CURFXGgFC1y-N17tXdT7RoZhLHskIHx7qNcxeicS7wiSDhQD3l3mgOgq0bdjWJTk3LnpHk8zS0fDhKp6Vd6vFvCyzzRJu1ax5Y27Bg3dZp4Zsa3I9HAp5wXmyp51de8scS25nyaV0FEd1YUWgC1LsuwOODrSPqMkokv7XQXQc8W212O2dHbuuJ1xYEr1i5_Gl1syIX3ZuPj1_wqcnAKu5keY0ZVJz45iGYIRC09hd4n8j1SEA8dDlhbslCtyZ6xMt6MdRFv1D7fhbt_g4RGDk7ZkjpnT6z9q3dTWNzkS3gSd9AekBNbUNw9ojZmTWoCFhZgxz-6Wwtcp9z7vIo; path=/; samesite=lax; httponly

是不是短了很多?好吧,其实感觉还是有点长,没关系,下面再介绍一种更加彻底的优化方式。

而最终页面上展示的Claims信息如下:

cookie_jwt_profile

SessionStore

 

1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,请转载时务必注明文章作者和来源,不尊重原创的行为我们将追究责任;3.作者投稿可能会经我们编辑修改或补充。

相关文章
  • ASP.NET Core Web服务器 Kestrel和Http.sys 特性详解 - 行动派Xdpie

    ASP.NET Core Web服务器 Kestrel和Http.sys 特性详解 - 行动派Xdpie

    2017-09-15 17:05

  • Entity Framework Core Like 查询揭秘 - Sweet-Tang

    Entity Framework Core Like 查询揭秘 - Sweet-Tang

    2017-09-13 12:05

  • ASP.NET Core 运行原理解剖[5]:Authentication - 雨の夜

    ASP.NET Core 运行原理解剖[5]:Authentication - 雨の夜

    2017-09-11 11:16

  • 【ASP.NET MVC】View与Controller之间传递数据 - Alan_beijing

    【ASP.NET MVC】View与Controller之间传递数据 - Alan_beijing

    2017-09-10 08:02

网友点评
a