Skip to content
Snippets Groups Projects
Commit 6e2e7457 authored by Reiter, Christoph's avatar Reiter, Christoph :snake:
Browse files

Merge branch 'auth-token-refresh' into 'master'

auth-keycloak: make sure the token is always valid for at least 20 seconds

See merge request !6
parents 895589a6 74444969
No related branches found
No related tags found
1 merge request!6auth-keycloak: make sure the token is always valid for at least 20 seconds
Pipeline #14109 passed
...@@ -229,6 +229,7 @@ export class AuthKeycloak extends LitElement { ...@@ -229,6 +229,7 @@ export class AuthKeycloak extends LitElement {
} }
disconnectedCallback() { disconnectedCallback() {
this._kcwrapper.close();
this._kcwrapper.removeEventListener('changed', this._onKCChanged); this._kcwrapper.removeEventListener('changed', this._onKCChanged);
this._bus.close(); this._bus.close();
......
...@@ -55,6 +55,15 @@ const ensureURL = function(urlOrPath) { ...@@ -55,6 +55,15 @@ const ensureURL = function(urlOrPath) {
*/ */
export class KeycloakWrapper extends EventTarget { export class KeycloakWrapper extends EventTarget {
/* Minimum validity of the token in seconds */
MIN_VALIDITY = 20;
/* Interval at which the token validity is checked, in seconds */
CHECK_INTERVAL = 10;
/* Enables extra debug logging */
DEBUG = false;
constructor(baseURL, realm, clientId, silentCheckSsoUri, idpHint) { constructor(baseURL, realm, clientId, silentCheckSsoUri, idpHint) {
super(); super();
...@@ -65,6 +74,24 @@ export class KeycloakWrapper extends EventTarget { ...@@ -65,6 +74,24 @@ export class KeycloakWrapper extends EventTarget {
this._initDone = false; this._initDone = false;
this._silentCheckSsoUri = silentCheckSsoUri; this._silentCheckSsoUri = silentCheckSsoUri;
this._idpHint = idpHint; this._idpHint = idpHint;
this._checkId = null;
this._onVisibilityChanged = this._onVisibilityChanged.bind(this);
document.addEventListener("visibilitychange", this._onVisibilityChanged);
}
/**
* This needs to be called or the instance will leak;
*/
close() {
document.removeEventListener("visibilitychange", this._onVisibilityChanged);
}
_onVisibilityChanged() {
let isVisible = (document.visibilityState === 'visible');
if (isVisible && this._keycloak.authenticated) {
this._checkTokeHasExpired();
}
} }
_onChanged() { _onChanged() {
...@@ -97,6 +124,44 @@ export class KeycloakWrapper extends EventTarget { ...@@ -97,6 +124,44 @@ export class KeycloakWrapper extends EventTarget {
console.assert(refreshed, "token should have been refreshed"); console.assert(refreshed, "token should have been refreshed");
} }
async _checkTokeHasExpired() {
let refreshed;
let minValidity = this.MIN_VALIDITY + this.CHECK_INTERVAL;
if (this.DEBUG) {
console.log(`Updating token if not valid for at least ${minValidity}s`);
}
try {
refreshed = await this._keycloak.updateToken(minValidity);
} catch (error) {
console.log('Failed to refresh the token', error);
}
if (this.DEBUG && refreshed)
console.log("token has been refreshed");
}
async _onAuthSuccess() {
// We check every once in a while if the token is still valid and
// and refresh it if needed.
if (this._checkId !== null) {
clearInterval(this._checkId);
this._checkId = null;
}
this._checkId = setInterval(this._checkTokeHasExpired.bind(this), this.CHECK_INTERVAL * 1000);
this._onChanged();
}
async _onAuthLogout() {
if (this._checkId !== null) {
clearInterval(this._checkId);
this._checkId = null;
}
this._onChanged();
}
async _ensureInstance() { async _ensureInstance() {
if (this._keycloak !== null) if (this._keycloak !== null)
return; return;
...@@ -112,8 +177,8 @@ export class KeycloakWrapper extends EventTarget { ...@@ -112,8 +177,8 @@ export class KeycloakWrapper extends EventTarget {
this._keycloak.onTokenExpired = this._onTokenExpired.bind(this); this._keycloak.onTokenExpired = this._onTokenExpired.bind(this);
this._keycloak.onAuthRefreshSuccess = this._onChanged.bind(this); this._keycloak.onAuthRefreshSuccess = this._onChanged.bind(this);
this._keycloak.onAuthRefreshError = this._onChanged.bind(this); this._keycloak.onAuthRefreshError = this._onChanged.bind(this);
this._keycloak.onAuthLogout = this._onChanged.bind(this); this._keycloak.onAuthLogout = this._onAuthLogout.bind(this);
this._keycloak.onAuthSuccess = this._onChanged.bind(this); this._keycloak.onAuthSuccess = this._onAuthSuccess.bind(this);
this._keycloak.onAuthError = this._onChanged.bind(this); this._keycloak.onAuthError = this._onChanged.bind(this);
this._keycloak.onReady = this._onReady.bind(this); this._keycloak.onReady = this._onReady.bind(this);
} }
...@@ -139,6 +204,9 @@ export class KeycloakWrapper extends EventTarget { ...@@ -139,6 +204,9 @@ export class KeycloakWrapper extends EventTarget {
pkceMethod: 'S256', pkceMethod: 'S256',
}; };
if (this.DEBUG) {
options['enableLogging'] = true;
}
if (this._silentCheckSsoUri) { if (this._silentCheckSsoUri) {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment