From 1e4c7a88d80e255308d1d666342ef8c0fed64a75 Mon Sep 17 00:00:00 2001 From: James Date: Thu, 17 Oct 2024 14:13:36 -0400 Subject: [PATCH 1/9] [ALS-7506] Show error message when the user times out --- src/lib/api.ts | 4 ++-- src/lib/components/Navigation.svelte | 2 +- src/lib/stores/User.ts | 16 ++++++++++++++-- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src/lib/api.ts b/src/lib/api.ts index e1514df9..16b2e8aa 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -75,8 +75,8 @@ async function handleResponse(res: Response) { return text; //TODO: Change this } } else if (res.status === 401) { - logout(); - throw error(401, 'Unauthorized'); + logout(undefined, true); + return; } throw error(res.status as NumericRange<400, 599>, await res.text()); diff --git a/src/lib/components/Navigation.svelte b/src/lib/components/Navigation.svelte index 44d93138..0fa382db 100644 --- a/src/lib/components/Navigation.svelte +++ b/src/lib/components/Navigation.svelte @@ -132,7 +132,7 @@ id="user-logout-btn" class="btn variant-ringed-primary" title="Logout" - on:click={() => logout(providerInstance)}>Logout logout(providerInstance, false)}>Logout {:else} diff --git a/src/lib/stores/User.ts b/src/lib/stores/User.ts index 5489d994..7708caa2 100644 --- a/src/lib/stores/User.ts +++ b/src/lib/stores/User.ts @@ -8,6 +8,10 @@ import { routes, features, resources } from '$lib/configuration'; import { goto } from '$app/navigation'; import type { QueryInterface } from '$lib/models/query/Query'; import type AuthProvider from '$lib/models/AuthProvider.ts'; +import { page } from '$app/stores'; +import { getToastStore } from '@skeletonlabs/skeleton'; + +let toastStore = getToastStore(); export const user: Writable = writable(restoreUser()); @@ -134,7 +138,7 @@ export async function login(token: string) { } } -export async function logout(authProvider: AuthProvider | undefined) { +export async function logout(authProvider?: AuthProvider, redirect = false) { if (browser) { const token = localStorage.getItem('token'); token && api.get('/psama/logout'); @@ -161,7 +165,15 @@ export async function logout(authProvider: AuthProvider | undefined) { }); } else { user.set({}); - goto('/login'); + if (redirect) { + toastStore.trigger({ + message: 'Your session has timed out. Please log in.', + background: 'variant-filled-error', + }); + goto(`/login?redirectTo=${encodeURIComponent(get(page).url.pathname)}`); + } else { + goto('/login') + } } } From e001085d89c76b2aad6956a8468f18d3c67ceb7c Mon Sep 17 00:00:00 2001 From: James Date: Fri, 18 Oct 2024 08:35:12 -0400 Subject: [PATCH 2/9] try session storage --- src/lib/api.ts | 2 ++ src/lib/stores/User.ts | 15 +++------------ src/routes/(authentication)/login/+page.svelte | 16 +++++++++++++++- 3 files changed, 20 insertions(+), 13 deletions(-) diff --git a/src/lib/api.ts b/src/lib/api.ts index 16b2e8aa..a6246ed6 100644 --- a/src/lib/api.ts +++ b/src/lib/api.ts @@ -75,6 +75,8 @@ async function handleResponse(res: Response) { return text; //TODO: Change this } } else if (res.status === 401) { + browser && + sessionStorage.setItem('logout-reason', 'Your session has timed out. Please log in.'); logout(undefined, true); return; } diff --git a/src/lib/stores/User.ts b/src/lib/stores/User.ts index 7708caa2..2d8a88b4 100644 --- a/src/lib/stores/User.ts +++ b/src/lib/stores/User.ts @@ -9,9 +9,6 @@ import { goto } from '$app/navigation'; import type { QueryInterface } from '$lib/models/query/Query'; import type AuthProvider from '$lib/models/AuthProvider.ts'; import { page } from '$app/stores'; -import { getToastStore } from '@skeletonlabs/skeleton'; - -let toastStore = getToastStore(); export const user: Writable = writable(restoreUser()); @@ -165,15 +162,9 @@ export async function logout(authProvider?: AuthProvider, redirect = false) { }); } else { user.set({}); - if (redirect) { - toastStore.trigger({ - message: 'Your session has timed out. Please log in.', - background: 'variant-filled-error', - }); - goto(`/login?redirectTo=${encodeURIComponent(get(page).url.pathname)}`); - } else { - goto('/login') - } + redirect + ? goto(`/login?redirectTo=${encodeURIComponent(get(page).url.pathname)}`) + : goto('/login'); } } diff --git a/src/routes/(authentication)/login/+page.svelte b/src/routes/(authentication)/login/+page.svelte index ea479cdf..9017bf7f 100644 --- a/src/routes/(authentication)/login/+page.svelte +++ b/src/routes/(authentication)/login/+page.svelte @@ -6,11 +6,25 @@ import type { AuthData } from '$lib/models/AuthProvider'; import { branding, features } from '$lib/configuration'; import { fly } from 'svelte/transition'; - + import { browser } from '$app/environment'; + import { getToastStore } from '@skeletonlabs/skeleton'; + const toastStore = getToastStore(); const redirectTo = $page.url.searchParams.get('redirectTo') || '/'; const siteName = branding?.applicationName; const description = branding?.login.description; const openPicsureLinkText = branding?.login.openPicsureLinkText; + let logoutReason: string | null; + + if (browser) { + logoutReason = sessionStorage.getItem('logout-reason'); + if (logoutReason) { + sessionStorage.removeItem('logout-reason'); + toastStore.trigger({ + message: logoutReason, + background: 'variant-filled-error', + }); + } + } let selected: string; From 3a374e5dc7012ebd85b0c383a910b399e6dbd7d5 Mon Sep 17 00:00:00 2001 From: James Date: Fri, 18 Oct 2024 14:23:02 -0400 Subject: [PATCH 3/9] Handle auth errors --- src/lib/services/dictionary.ts | 24 ++++++++++-------------- src/lib/stores/User.ts | 8 ++++++-- 2 files changed, 16 insertions(+), 16 deletions(-) diff --git a/src/lib/services/dictionary.ts b/src/lib/services/dictionary.ts index 3a64c91f..3f4f0794 100644 --- a/src/lib/services/dictionary.ts +++ b/src/lib/services/dictionary.ts @@ -49,16 +49,6 @@ export function searchDictionary( ); } -export async function getAllFacets(): Promise { - let request: DictionarySearchRequest = { facets: [], search: '' }; - if (!get(page).url.pathname.includes('/discover')) { - request = addConsents(request); - } - const response: DictionaryFacetResult[] = await api.post(`${dictionaryUrl}facets/`, request); - initializeHiddenFacets(response); - return response; -} - function initializeHiddenFacets(response: DictionaryFacetResult[]) { // facets that have a count of zero should never be shown in the UI // this happens because of consent filters @@ -87,11 +77,17 @@ export async function updateFacetsFromSearch( request = addConsents(request); } - const response: DictionaryFacetResult[] = await api.post(`${dictionaryUrl}facets/`, request); - if (facets.length === 0 && search.length === 0) { - initializeHiddenFacets(response); + try { + const response: DictionaryFacetResult[] = await api.post(`${dictionaryUrl}facets/`, request); + if (facets.length === 0 && search.length === 0) { + initializeHiddenFacets(response); + } + return response; + } catch (error) { + console.error('Failed to update facets from search:', error); + // You might want to throw the error or return a default value depending on your use case + return []; } - return response; } export async function getConceptDetails( diff --git a/src/lib/stores/User.ts b/src/lib/stores/User.ts index 2d8a88b4..6e7e0dcf 100644 --- a/src/lib/stores/User.ts +++ b/src/lib/stores/User.ts @@ -138,8 +138,12 @@ export async function login(token: string) { export async function logout(authProvider?: AuthProvider, redirect = false) { if (browser) { const token = localStorage.getItem('token'); - token && api.get('/psama/logout'); - token && localStorage.removeItem('token'); + if (token) { + api.get('/psama/logout').catch((error) => { + console.error('Error logging out: ' + error); + }); + localStorage.removeItem('token'); + } } // get the auth provider From afa794112996694bd7d6978b8c99408aa778a408 Mon Sep 17 00:00:00 2001 From: James Date: Fri, 18 Oct 2024 14:38:01 -0400 Subject: [PATCH 4/9] Update dictionary.ts --- src/lib/services/dictionary.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/lib/services/dictionary.ts b/src/lib/services/dictionary.ts index 3f4f0794..09f9ab33 100644 --- a/src/lib/services/dictionary.ts +++ b/src/lib/services/dictionary.ts @@ -86,7 +86,7 @@ export async function updateFacetsFromSearch( } catch (error) { console.error('Failed to update facets from search:', error); // You might want to throw the error or return a default value depending on your use case - return []; + throw error; } } From 39363594b506bfa2244f124063e45e6d80f09494 Mon Sep 17 00:00:00 2001 From: James Date: Tue, 22 Oct 2024 11:52:10 -0400 Subject: [PATCH 5/9] put in onmount --- .../(authentication)/login/+page.svelte | 22 +++++++++++-------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/src/routes/(authentication)/login/+page.svelte b/src/routes/(authentication)/login/+page.svelte index 9017bf7f..a6a5837b 100644 --- a/src/routes/(authentication)/login/+page.svelte +++ b/src/routes/(authentication)/login/+page.svelte @@ -8,6 +8,7 @@ import { fly } from 'svelte/transition'; import { browser } from '$app/environment'; import { getToastStore } from '@skeletonlabs/skeleton'; + import { onMount } from 'svelte'; const toastStore = getToastStore(); const redirectTo = $page.url.searchParams.get('redirectTo') || '/'; const siteName = branding?.applicationName; @@ -15,16 +16,19 @@ const openPicsureLinkText = branding?.login.openPicsureLinkText; let logoutReason: string | null; - if (browser) { - logoutReason = sessionStorage.getItem('logout-reason'); - if (logoutReason) { - sessionStorage.removeItem('logout-reason'); - toastStore.trigger({ - message: logoutReason, - background: 'variant-filled-error', - }); + + onMount(() => { + if (browser) { + logoutReason = sessionStorage.getItem('logout-reason'); + if (logoutReason) { + sessionStorage.removeItem('logout-reason'); + toastStore.trigger({ + message: logoutReason, + background: 'variant-filled-error', + }); + } } - } + }); let selected: string; From 7561b145715cda15d99e0a18b0da77420cf91f69 Mon Sep 17 00:00:00 2001 From: James Date: Tue, 22 Oct 2024 13:08:25 -0400 Subject: [PATCH 6/9] lint --- src/routes/(authentication)/login/+page.svelte | 1 - 1 file changed, 1 deletion(-) diff --git a/src/routes/(authentication)/login/+page.svelte b/src/routes/(authentication)/login/+page.svelte index a6a5837b..5c31741a 100644 --- a/src/routes/(authentication)/login/+page.svelte +++ b/src/routes/(authentication)/login/+page.svelte @@ -16,7 +16,6 @@ const openPicsureLinkText = branding?.login.openPicsureLinkText; let logoutReason: string | null; - onMount(() => { if (browser) { logoutReason = sessionStorage.getItem('logout-reason'); From bda2c445fdb61b9c701145abf75f0a14428e14f0 Mon Sep 17 00:00:00 2001 From: James Date: Tue, 22 Oct 2024 13:22:15 -0400 Subject: [PATCH 7/9] try timeout --- src/routes/(authentication)/login/+page.svelte | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/src/routes/(authentication)/login/+page.svelte b/src/routes/(authentication)/login/+page.svelte index 5c31741a..7288a8cc 100644 --- a/src/routes/(authentication)/login/+page.svelte +++ b/src/routes/(authentication)/login/+page.svelte @@ -20,11 +20,13 @@ if (browser) { logoutReason = sessionStorage.getItem('logout-reason'); if (logoutReason) { - sessionStorage.removeItem('logout-reason'); - toastStore.trigger({ - message: logoutReason, - background: 'variant-filled-error', - }); + setTimeout(() => { + toastStore.trigger({ + message: logoutReason!, + background: 'variant-filled-error', + }); + sessionStorage.removeItem('logout-reason'); + }, 1000); } } }); From a8a4008c9d46d581df71fe66cdabbf752e58eec2 Mon Sep 17 00:00:00 2001 From: James Date: Tue, 22 Oct 2024 13:59:51 -0400 Subject: [PATCH 8/9] Fix toast --- src/routes/(authentication)/login/+layout.svelte | 2 ++ src/routes/(authentication)/login/+page.svelte | 12 +++++------- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/routes/(authentication)/login/+layout.svelte b/src/routes/(authentication)/login/+layout.svelte index 8ef023d8..6b98ce61 100644 --- a/src/routes/(authentication)/login/+layout.svelte +++ b/src/routes/(authentication)/login/+layout.svelte @@ -4,6 +4,7 @@ import { onMount } from 'svelte'; import Footer from '$lib/components/Footer.svelte'; import Dots from '$lib/components/Dots.svelte'; + import { Toast } from '@skeletonlabs/skeleton'; onMount(() => { if ($user && $user.token) { @@ -12,6 +13,7 @@ }); +
diff --git a/src/routes/(authentication)/login/+page.svelte b/src/routes/(authentication)/login/+page.svelte index 7288a8cc..1e45f4c5 100644 --- a/src/routes/(authentication)/login/+page.svelte +++ b/src/routes/(authentication)/login/+page.svelte @@ -20,13 +20,11 @@ if (browser) { logoutReason = sessionStorage.getItem('logout-reason'); if (logoutReason) { - setTimeout(() => { - toastStore.trigger({ - message: logoutReason!, - background: 'variant-filled-error', - }); - sessionStorage.removeItem('logout-reason'); - }, 1000); + toastStore.trigger({ + message: logoutReason!, + background: 'variant-filled-error', + }); + sessionStorage.removeItem('logout-reason'); } } }); From f42fe226f0517e3dce1cbe2c5fad3c60f15267cc Mon Sep 17 00:00:00 2001 From: James Date: Tue, 22 Oct 2024 14:48:12 -0400 Subject: [PATCH 9/9] Update dictionary.ts --- src/lib/services/dictionary.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/src/lib/services/dictionary.ts b/src/lib/services/dictionary.ts index 09f9ab33..be5181a7 100644 --- a/src/lib/services/dictionary.ts +++ b/src/lib/services/dictionary.ts @@ -85,7 +85,6 @@ export async function updateFacetsFromSearch( return response; } catch (error) { console.error('Failed to update facets from search:', error); - // You might want to throw the error or return a default value depending on your use case throw error; } }