前言
这里主要记录阐述了我们针对 SAAS、OP端,不同domain登录,第三方登录的解决方案,核心知识点是跨域读cookie,概念类的就不过多阐述了。
先来点凉菜
(账户中心:account.a.com/login)
用于账户的管理和认证,建议作为一个单独项目去开发
1.登录
(支持普通登录和临时令牌,临时令牌为一次性交换真实token的key)
2.登出
3.注册
4.忘记密码
5.跨域登录iframe嵌套
(登录表单的抽离封装,针对iframe作postMessage处理)
6.中转页面
(用于第三方登录,调用接口把url参数全部传给后端处理逻辑,如是否手动跳转,跳转地址,当前html 设置cookie等)
另:根据产品增加各种主题色等等
classDiagram
Account <|-- self_same_domain_App
Account <|-- self_dif_domain_App
Account <|-- out_App
Account : 账户中心
Account :login()
class self_same_domain_App{
与账户中心同domain产品
login()
}
class self_dif_domain_App{
与账户中心不同domain产品
run()
}
class out_App{
第三方中转页面
redirect()
}
重点说下登录接口的Response Headers
p3p: CP='CURa ADMa DEVa PSAo PSDo OUR BUS UNI PUR INT DEM STA PRE COM NAV OTC NOI DSP COR'
set-cookie: token=xxx; Path=/; Domain=a.com; Expires=some time; Secure;HttpOnly; SameSite=None
以上就是登录时调用的登录接口,登录状态放在了cookie。HttpOnly纯由后端去控制
临时令牌模式data里返回一个一次性的令牌key
p3p固定写法,查了资料发现这玩意是为了兼容ie浏览器
Secure; SameSite=None 是https时兼容chrom的跨域读cookie 如果你没有不同domian登录的场景可以不加
主菜(拿天猫举个例子)
同domain
cookie是共享的,登录状态是保持
也有些特殊场景,比如我们有其他环境,和线上环境同domain,比如x.a.com 和y.a.com 我们就可以约束token的key为x_token和y_token,让后端自己去找对应的key去校验token的值
不同domain跨域读cookie (www.b.com)
页面html的heard
<script type="text/javascript" src="account.a.com/账户中心前端网关/ap…" />
src是后端的一个接口地址 后端可以拿到a.com的cookie信息并且返回js
如var info={'token':'xxx','userId’:’xxx,’username':'xxx'};window.run&& window.run();
ps:这时候你在控制台看到的其他域的cookie 然后这些并不能通过代码去获取到,而且根据该域cookie状态即时更新
b.com(www.b.com)的登录
登录iframe嵌套
由于safari浏览器不支持跨域读cookie 包括天猫现在也没做兼容
需要针对浏览器分开处理
非safari 接受postMessage登录成功后走业务跳转,编写上述的run设置 登录状态
safari需要把iframe的src url传入的临时令牌模式,postMessage登录成功后获取临时令牌通过b的后端向a的后端换取真实token并返回设置在cookie上
const init = () => {
// 监听接收
window.addEventListener('message', async function (e) {
const { action, info } = e.data;
switch (action) {
// 跳转
case 'redirect':
break;
case 'button':
break;
case 'login':
if (isSafari) {
} else {
}
break;
// 本地调试设置cookie
case 'localhost':
break;
// 获取href
case 'getTopUrl':
if (ref.current) {
ref.current.contentWindow?.postMessage(
{ action: 'getTopUrl', info: { msg: window.location.href } },
'*',
);
}
break;
default:
}
});
};
饭后甜点
登出
用a标签后端写个get请求的二次跳转 接受前端的重定向地址和默认重定向
如: https://账户中心地址/登出网关/xx?redirect=xxxx
环境部署是否为http(s)?
1.账户中心: 如果有非同域产品单点登录 则必须为https
2.同域产品(与账户中心domain相同):与 该环境 账户中心 保持一致
3.非同域产品: http(s)都可
方案a: sso单点登录,相关的账户中心一定为https
方案b: 用临时票据ticket调用,相关的账户中心http(s)都可
中转页面的应用
场景:SAAS第三方登录,OP环境同步登录
拿我们的举个例子,前端的环境变量consif.json
中转地址内逻辑:
config.json:
environment:"OP",
OPLoginConfig.enabledRedirect:true
场景:使用客户登录->票据(ticket或者cookie)->后端控制跳转(去登录或者设置cookie进入页面)
1.校验配置项
2.读配置:OPLoginApiUrl >> 请求接口 >> 处理参数
返回值:
a. error走后端公共抛错
b. 接口返回Data为参数:
manualHandler:booble 选填,当为true时手动模式,不进行跳转
html:string 选填,替换当前页面html,配合manualHandler使用
redirect:选填,重定向的产品地址 undefined =>默认跳转'/', ("url 地址") => 绝对路径或url,地址需encodeURIComponent 转码
其他key会以url参数形式跟随跳转