- 51Aspx源码必读.txt[9KB]
- .gitattributes[2KB]
- .gitignore[6KB]
- from .gif[4KB]
- 最新Asp.Net源码下载.url[123B]
源码介绍
源码参数
SSO 是指在多个应用系统中,只需登录一次,就可以访问其他互相信任的应用系统。
JWT 是 Json Web Token 的缩写,是一种认证机制。
OAuth2.0 是一个认证流程,一共有四种方式,这里用的是最常用的授权码方式,流程为:
1. 系统 A 向认证中心先获取一个授权码 code。
2. 系统 A 通过授权码 code 获取 token,refresh_token,expiry_time,scope。
token:系统 A 向认证方获取资源请求时带上的 token。
refresh_token:token 的有效期比较短,用来刷新 token 用。
expiry_time:token 过期时间。
scope:资源域,系统 A 所拥有的资源权限,比如 scope:["userinfo"],则表示系统 A 只拥有获取用户信息的权限。像平时网站接入微信登录也是只能授权获取微信用户基本信息。
这里的 SSO 都是公司自己的系统,都是获取用户信息,所以这个为空,第三方需要接入我们的登录时才需要 scope 来做资源权限判断。
二、功能介绍
我们的代码核心实现功能在于:
(一)一处登录,全部登录:
1. 浏览器访问 A 系统,发现 A 系统未登录,跳转到统一登录中心(SSO),带上 A 系统的回调地址:
地址为:https://sso.com/SSO/Login?redirectUrl=https://web1.com/Account/LoginRedirect&clientId=web1,输入用户名,密码,登录成功,生成授权码code,创建一个全局会话(cookie,redis),带着授权码跳转回A系统地址:https://web1.com/Account/LoginRedirect?AuthCode=xxxxxxxx。然后A系统的回调地址用这个AuthCode调用SSO获取token,获取到token,创建一个局部会话(cookie,redis),再跳转到https://web1.com。这样A系统就完成了登录。
2. 浏览器访问 B 系统,发现 B 系统没登录,跳转到统一登录中心(SSO),带上 B 系统的回调地址:
地址为:https://sso.com/SSO/Login?redirectUrl=https://web2.com/Account/LoginRedirect&clientId=web2,SSO有全局会话证明已经登录过,直接用全局会话code获取B系统的授权码code,
带着授权码跳转回B系统https://web2.com/Account/LoginRedirect?AuthCode=xxxxxxxx,然后B系统的回调地址用这个AuthCode调用SSO获取token,获取到token创建一个局部会话(cookie,redis),再跳转到https://web2.com。整个过程不用输入用户名密码,这些跳转基本是无感的,所以B就自动登录好了。
(二)一处退出,全部退出。
A系统退出,把自己的会话删除,然后跳转到SSO的退出登录地址:https://sso.com/SSO/Logout?redirectUrl=https://web1.com/Account/LoginRedirect&clientId=web1,SSO删除全局会话,然后调接口删除获取了token的系统,然后在跳转到登录页面,https://sso.com/SSO/Login?redirectUrl=https://web1.com/Account/LoginRedirect&clientId=web1,这样就实现了一处退出,全部退出了。
(三)双 token 机制。
也就是带刷新token,为什么要刷新token呢?因为基于token式的鉴权授权有着天生的缺陷:
token设置时间长,token泄露了,重放攻击。
token设置短了,老是要登录。问题还有很多,因为token本质决定,大部分是解决不了的。
所以就需要用到双Token机制,SSO返回token和refreshToken,token用来鉴权使用,refreshToken刷新token使用,
比喻token有效期10分钟,refreshToken有效期2天,这样就算token泄露了,最多10分钟就会过期,影响没那么大,系统定时9分钟刷新一次token,
这样系统就能让token滑动过期了,避免了频繁重新登录。
三、注意事项
建三个项目,SSO的项目,web1的项目,web2项目。
1. SSO.Demo.Web1:实现一处登录,全部登录。
这里的流程就是web1跳转SSO输用户名登录成功获取code,把会话写到SSO的cookie,然后跳转回来根据code跟SSO获取token登录成功;
然后访问web2跳转到SSO,SSO已经登录,自动获取code跳回web2根据code获取token。
能实现一处登录处处登录的关键是SSO的cookie。
然后这里有一个核心的问题,如果我们生成的token有效期都是24小时,那么web1登录成功,获取的token有效期是24小时,
等到过了12个小时,我访问web2,web2也得到一个24小时的token,这样再过12小时,web1的登录过期了,web2还没过期,
这样就是web2是登录状态,然而web1却不是登录状态需要重新登录,这样就违背了一处登录处处登录的理念。
所以后面获取的token,只能跟第一次登录的token的过期时间是一样的。怎么做呢,就是SSO第一次登录时过期时间缓存下来,后面根据SSO会话获取的code,
换到的token的过期时间都和第一次一样。
2. SSO.Demo.Web2:实现一处退出,全部退出。
一处退出,处处退出的流程像实现目标中的流程图,web1系统退出,跳转到SSO,让SSO发http请求退出其他的系统,跳转回登录页。
退出有个核心的问题就是,SSO只能让全部系统在当前浏览器上退出,比如用户A在电脑1的浏览器登录了,在电脑2的浏览器也登录了,在电脑1上退出只能退出电脑1浏览器的登录,
电脑2的登录不受影响,web1退出了,SSO中的http请求退出web2的时候是不经过浏览器请求的,web2怎么知道清除那个token呢?
这里需要在SSO登录的时候生成了一个全局会话,SSO的cookie这时可以生成一个全局code,每个系统登录的时候带过去作为token的缓存key,这样就能保证全部系统的局部会话缓存key是同一个了,
退出登录的时候只需要删除这个缓存key的token即可。
四、效果演示
项目的SSO地址是:https://localhost:7000 ,web1地址是:https://localhost:7001,web2地址是:https://localhost:7002
修改hosts文件,让他们在不同域名下,cookie不能共享。
win10路径:C:\Windows\System32\drivers\etc\hosts 在最后加入
127.0.0.1 sso.com
127.0.0.1 web1.com
127.0.0.1 web2.com
这样得到新的地址,SSO地址:https://sso.com:7000 ,web1地址是:https://web1.com:7001,web2地址是:https://web2.com:7002
1. 这里一开始,访问https://web2.com:7002,没登录跳转到https://sso.com:7000。
2. 然后访问https://web1.com:7001也没登录,也跳转到了https://sso.com:7000,证明web1,web2都没登录。
3. 然后在跳转的sso登录后跳转回web1,然后点https://web2.com:7002的连接跳转到https://web2.com:7002,自动登录了。
4. 然后在web1退出登录,web2刷新页面,也退出了登录。
下载记录(Only Recent 100)
用户名 | 推荐指数 | 下载时间 |
---|