对 OpenID Connect 调用会话管理端点
会话管理端点允许 OpenID Connect 依赖方监视使用特定 OpenID Connect 提供程序 (OP) 的用户的登录状态,同时将网络流量降至最低。在会话管理端点的帮助下,依赖方 (RP) 可注销已从 OpenID Connect 提供程序注销的用户。
开始之前
关于此任务
为帮助确定用户的登录状态,RP 装入其 src 目标设置为 OP 的会话管理端点的 iframe。会话管理端点可访问用于存储用户的登录状态或浏览器状态的 cookie。此浏览器状态 cookie 在用户从 OP 注销时更新。然后,RP 可使用客户机端脚本调用 OP iframe 的 Window.postMessage() 函数,以在消息文本中发送客户机标识和当前已知会话状态。如果 RP 接收到从 OP 框架返回的 postMessage 且其值为 changed,那么 OP 上的用户的登录状态已更改,并且 RP 可决定是否注销该用户。如果返回的值为 unchanged,那么该用户在 OP 上仍处于已登录状态。
已启用 OpenID Connect 的 Liberty 服务器可访问位于以下 URL 的 OpenID Connect 会话管理端点:
https://server.example.com:443/oidc/endpoint/<provider_name>/check_session_iframe
过程
结果
示例
以下 HTML 示例显示一个使用 OpenID Connect 会话管理的完整 HTML 页面。OP iframe 的 src 属性设置为从 OP 获取的会话管理端点 URL。系统以 60 秒一次的频率自动调用 startChecking() 函数以检查用户的登录状态。此页面具有 message 事件侦听器,接收到 postMessage 时,此侦听器会调用 receiveMessage() 函数。此函数确保 postMessage 来自 OP 的预期域,并检查所返回消息的值以了解用户的登录状态是 changed 还是 unchanged。
<!DOCTYPE html>
<html>
<head>
<meta charset="ISO-8859-1">
<title>iFrame RP Page</title>
</head>
<body onload="javascript:startChecking()">
<iframe id="iframeOP" src="https://localhost:8999/oidc/endpoint/OidcConfigSample/check_session_iframe" frameborder="0" width="0" height="0"></iframe>
</body>
<script>
var targetOP = "https://server.example.com:443";
window.addEventListener("message", receiveMessage, false);
function startChecking() {
checkStatus();
// Check status every 60 seconds
setInterval("checkStatus()", 1000*60);
}
function getCookieValue(cookieName) {
var name = cookieName + "=";
var cookies = document.cookie.split(';');
if (!cookies) {
return null;
}
for (var i = 0; i < cookies.length; i++) {
var cookie = cookies[i].trim();
if (cookie.indexOf(name) == 0) {
return cookie.substring(name.length, cookie.length);
}
}
return null;
}
function checkStatus() {
var client = "client01";
var sessionState = getCookieValue("session_state");
var text = client + " " + sessionState;
var iframe = document.getElementById("iframeOP");
iframe.contentWindow.postMessage(text, targetOP);
}
function receiveMessage(event) {
if (event.origin !== targetOP) {
// Origin did not come from the OP; this message must be rejected
return;
}
if (event.data === "unchanged") {
// User is still logged in to the OP
} else {
// User has logged out of the OP
}
}
</script>
</html>