Skip to content

Commit

Permalink
feat(oidc-client): allow to take control on service-worker registrati…
Browse files Browse the repository at this point in the history
…on (release) (#1229)
  • Loading branch information
guillaume-chervet committed Dec 4, 2023
1 parent e51d30d commit 49c3d5e
Show file tree
Hide file tree
Showing 7 changed files with 20 additions and 11 deletions.
5 changes: 3 additions & 2 deletions packages/oidc-client/README.md
Expand Up @@ -194,9 +194,10 @@ const configuration = {
refresh_time_before_tokens_expiration_in_second: Number, // default is 120 seconds
service_worker_relative_url: String,
service_worker_keep_alive_path: String, // default is "/"
service_worker_only: Boolean, // default false
service_worker_activate: () => boolean, // you can take the control of the service worker default activation which use user agent string
service_worker_only: Boolean, // default false, if true, the user will not be able to login if the service worker is not available on its browser
service_worker_activate: () => boolean, // you can take the control of the service worker default activation which use user agent string, if return false, the service worker mode will not be used
service_worker_update_require_callback: (registration:any, stopKeepAlive:Function) => Promise<void>, // callback called when service worker need to be updated, you can take the control of the update process
service_worker_register: (url: string) => Promise<ServiceWorkerRegistration>, // Optional, you can take the control of the service worker registration
extras: StringMap | undefined, // ex: {'prompt': 'consent', 'access_type': 'offline'} list of key/value that is sent to the OIDC server (more info: https://github.com/openid/AppAuth-JS)
token_request_extras: StringMap | undefined, // ex: {'prompt': 'consent', 'access_type': 'offline'} list of key/value that is sent to the OIDC server during token request (more info: https://github.com/openid/AppAuth-JS)
authority_time_cache_wellknowurl_in_second: 60 * 60, // Time to cache in seconds of the openid well-known URL, default is 1 hour
Expand Down
13 changes: 9 additions & 4 deletions packages/oidc-client/src/initWorker.ts
Expand Up @@ -6,7 +6,7 @@ import {ILOidcLocation} from "./location";

let keepAliveServiceWorkerTimeoutId = null;
let keepAliveController;
export const sleepAsync = (milliseconds) => {
export const sleepAsync = ({milliseconds}: { milliseconds: any }) => {
return new Promise(resolve => timer.setTimeout(resolve, milliseconds));
};

Expand All @@ -16,7 +16,7 @@ const keepAlive = (service_worker_keep_alive_path='/') => {
keepAliveController = new AbortController();
const promise = fetch(`${service_worker_keep_alive_path}OidcKeepAliveServiceWorker.json?minSleepSeconds=${minSleepSeconds}`, { signal: keepAliveController.signal });
promise.catch(error => { console.log(error); });
sleepAsync(minSleepSeconds * 1000).then(keepAlive);
sleepAsync({milliseconds: minSleepSeconds * 1000}).then(keepAlive);
} catch (error) { console.log(error); }
};

Expand All @@ -41,7 +41,7 @@ export const defaultServiceWorkerUpdateRequireCallback = (location:ILOidcLocatio
await registration.update();
const isSuccess = await registration.unregister();
console.log(`Service worker unregistering ${isSuccess}`)
await sleepAsync(2000);
await sleepAsync({milliseconds: 2000});
location.reload();
}

Expand Down Expand Up @@ -72,7 +72,12 @@ export const initWorkerAsync = async(configuration, configurationName) => {
return null;
}

const registration = await navigator.serviceWorker.register(serviceWorkerRelativeUrl);
let registration = null;
if(configuration.register) {
registration = await configuration.service_worker_register(serviceWorkerRelativeUrl);
} else {
registration = await navigator.serviceWorker.register(serviceWorkerRelativeUrl);
}

try {
await navigator.serviceWorker.ready;
Expand Down
6 changes: 3 additions & 3 deletions packages/oidc-client/src/oidc.ts
Expand Up @@ -352,18 +352,18 @@ Please checkout that you are using OIDC hook inside a <OidcProvider configuratio

async synchroniseTokensAsync(refreshToken, index = 0, forceRefresh = false, extras:StringMap = null, updateTokens) {
while (!navigator.onLine && document.hidden) {
await sleepAsync(1000);
await sleepAsync({milliseconds: 1000});
this.publishEvent(eventNames.refreshTokensAsync, { message: 'wait because navigator is offline and hidden' });
}
let numberTryOnline = 6;
while (!navigator.onLine && numberTryOnline > 0) {
await sleepAsync(1000);
await sleepAsync({milliseconds: 1000});
numberTryOnline--;
this.publishEvent(eventNames.refreshTokensAsync, { message: `wait because navigator is offline try ${numberTryOnline}` });
}
let numberTryHidden = Math.floor(Math.random() * 15) + 10;
while (document.hidden && numberTryHidden > 0) {
await sleepAsync(1000);
await sleepAsync({milliseconds: 1000});
numberTryHidden--;
this.publishEvent(eventNames.refreshTokensAsync, { message: `wait because navigator is hidden try ${numberTryHidden}` });
}
Expand Down
2 changes: 1 addition & 1 deletion packages/oidc-client/src/parseTokens.ts
Expand Up @@ -173,7 +173,7 @@ export const getValidTokenAsync = async (oidc: OidcToken, waitMs = 200, numberWa
return null;
}
while (!isTokensValid(oidc.tokens) && numberWaitTemp > 0) {
await sleepAsync(waitMs);
await sleepAsync({milliseconds: waitMs});
numberWaitTemp = numberWaitTemp - 1;
}
const isValid = isTokensValid(oidc.tokens);
Expand Down
2 changes: 2 additions & 0 deletions packages/oidc-client/src/types.ts
Expand Up @@ -3,6 +3,7 @@ export type Fetch = typeof window.fetch;
export type LogoutToken = 'access_token' | 'refresh_token';

export type ServiceWorkerUpdateRequireCallback = (registration:any, stopKeepAlive:Function) => Promise<void>;
export type ServiceWorkerRegister = (serviceWorkerRelativeUrl:string) => Promise<ServiceWorkerRegistration>;
export type ServiceWorkerActivate = () => boolean;

export type OidcConfiguration = {
Expand All @@ -19,6 +20,7 @@ export type OidcConfiguration = {
refresh_time_before_tokens_expiration_in_second?: number;
token_request_timeout?: number;
service_worker_relative_url?:string;
service_worker_register?:ServiceWorkerRegister;
service_worker_keep_alive_path?:string;
service_worker_activate?:ServiceWorkerActivate;
service_worker_only?:boolean;
Expand Down
2 changes: 1 addition & 1 deletion packages/oidc-client/src/user.ts
Expand Up @@ -8,7 +8,7 @@ export const userInfoAsync = (oidc) => async (noCache = false) => {

// We wait the synchronisation before making a request
while (oidc.tokens && !isTokensValid(oidc.tokens)) {
await sleepAsync(200);
await sleepAsync({milliseconds: 200});
}

if (!oidc.tokens) {
Expand Down
1 change: 1 addition & 0 deletions packages/react-oidc/README.md
Expand Up @@ -191,6 +191,7 @@ const configuration = {
service_worker_only: Boolean, // default false
service_worker_activate: () => boolean, // you can take the control of the service worker default activation which use user agent string
service_worker_update_require_callback: (registration:any, stopKeepAlive:Function) => Promise<void>, // callback called when service worker need to be updated, you can take the control of the update process
service_worker_register: (url: string) => Promise<ServiceWorkerRegistration>, // Optional, you can take the control of the service worker registration
extras: StringMap | undefined, // ex: {'prompt': 'consent', 'access_type': 'offline'} list of key/value that is sent to the OIDC server (more info: https://github.com/openid/AppAuth-JS)
token_request_extras: StringMap | undefined, // ex: {'prompt': 'consent', 'access_type': 'offline'} list of key/value that is sent to the OIDC server during token request (more info: https://github.com/openid/AppAuth-JS)
withCustomHistory: Function, // Override history modification, return an instance with replaceState(url, stateHistory) implemented (like History.replaceState())
Expand Down

0 comments on commit 49c3d5e

Please sign in to comment.