diff --git a/strr-platform-web/.env.example b/strr-platform-web/.env.example index 7a0124a3..308d8df7 100644 --- a/strr-platform-web/.env.example +++ b/strr-platform-web/.env.example @@ -19,6 +19,7 @@ NUXT_REGISTRY_HOME_URL="https://dev.bcregistry.gov.bc.ca/" NUXT_PAYMENT_PORTAL_URL="https://dev.account.bcregistry.gov.bc.ca/makepayment/" NUXT_AUTH_WEB_URL="https://dev.account.bcregistry.gov.bc.ca/" NUXT_BASE_URL="http://localhost:3000/" # app base url +NUXT_HOUSING_STRR_URL="" # TODO: add housing strr base url here for redirects #vaults keycloak NUXT_KEYCLOAK_AUTH_URL="https://dev.loginproxy.gov.bc.ca/auth" diff --git a/strr-platform-web/app/composables/useStrrModals.ts b/strr-platform-web/app/composables/useStrrModals.ts index fdd4c5dc..a50e108b 100644 --- a/strr-platform-web/app/composables/useStrrModals.ts +++ b/strr-platform-web/app/composables/useStrrModals.ts @@ -5,6 +5,7 @@ export const useStrrModals = () => { const modal = useModal() const { t } = useI18n() const connectNav = useConnectNav() + const config = useRuntimeConfig().public function openAppSubmitError (e: any) { modal.open(ModalBase, { @@ -37,6 +38,20 @@ export const useStrrModals = () => { }) } + function openConfirmDeclineTosModal () { + modal.open(ModalBase, { + title: 'Decline Terms of Use?', + content: 'By declining the Terms of Use, you won’t be able to access this service. Do you wish to proceed?', + actions: [ + { label: t('btn.cancel'), variant: 'outline', handler: () => close() }, + { + label: 'Decline Terms of Use', + handler: () => navigateTo(config.declineTosRedirectUrl as string, { external: true }) + } + ] + }) + } + function close () { modal.close() } @@ -44,6 +59,7 @@ export const useStrrModals = () => { return { openAppSubmitError, openCreateAccountModal, + openConfirmDeclineTosModal, close } } diff --git a/strr-platform-web/app/middleware/auth.ts b/strr-platform-web/app/middleware/auth.ts index 8bb61bbf..07f19245 100644 --- a/strr-platform-web/app/middleware/auth.ts +++ b/strr-platform-web/app/middleware/auth.ts @@ -1,7 +1,19 @@ -export default defineNuxtRouteMiddleware(() => { +export default defineNuxtRouteMiddleware(async (to) => { const { isAuthenticated } = useKeycloak() + const tosStore = useTosStore() + const localePath = useLocalePath() if (!isAuthenticated.value) { - return navigateTo({ path: useLocalePath()('/auth/login') }) + return navigateTo(localePath('/auth/login')) + } + + // check if tos exists or is not accepted + if (tosStore.tos.isTermsOfUseAccepted === undefined || !tosStore.tos.isTermsOfUseAccepted) { + await tosStore.getTermsOfUse() // load latest tos if no tos found in store or not accepted + + // return to tos page if not accepted + if (!tosStore.tos.isTermsOfUseAccepted) { + return navigateTo({ path: localePath('/auth/tos'), query: { return: to.fullPath } }) + } } }) diff --git a/strr-platform-web/app/pages/auth/tos.vue b/strr-platform-web/app/pages/auth/tos.vue new file mode 100644 index 00000000..c9153148 --- /dev/null +++ b/strr-platform-web/app/pages/auth/tos.vue @@ -0,0 +1,127 @@ + + diff --git a/strr-platform-web/app/stores/terms-of-service.ts b/strr-platform-web/app/stores/terms-of-service.ts new file mode 100644 index 00000000..82923407 --- /dev/null +++ b/strr-platform-web/app/stores/terms-of-service.ts @@ -0,0 +1,63 @@ +interface TOSPatchResponse { + isTermsOfUseAccepted: boolean + termsOfUseAcceptedVersion: string +} + +interface TOSGetResponse { + isTermsOfUseAccepted: boolean + termsOfUseAcceptedVersion: string | null + termsOfUseCurrentVersion: string + termsOfUse: string +} + +// TODO: make this generic for the core layer? +// will require the following api calls +// await $authApi('/users/@me') <-- this is breaking for Sergey, will need to fix this before adding to core layer +// await $authApi('/documents/termsofuse') + +export const useTosStore = defineStore('strr/terms-of-service', () => { + const { $strrApi } = useNuxtApp() + const loading = ref(false) + const tos = ref({} as TOSGetResponse) + + async function getTermsOfUse ():Promise { + try { + loading.value = true + tos.value = await $strrApi('/users/tos') + } catch { + // TODO: handle errors + } finally { + loading.value = false + } + } + + // form submit event + async function patchTermsOfUse () { + const res = await $strrApi('/users/tos', { + method: 'PATCH', + body: { + istermsaccepted: true, + termsversion: tos.value.termsOfUseCurrentVersion + } + }) + + // update tos accepted to match patch response or middleware will run again + tos.value.isTermsOfUseAccepted = res.isTermsOfUseAccepted + } + + function $reset () { + sessionStorage.removeItem('strr/terms-of-service') // required to reset store on logout + loading.value = false + tos.value = {} as TOSGetResponse + } + + return { + loading, + tos, + getTermsOfUse, + patchTermsOfUse, + $reset + } +}, +{ persist: true } // this will persist in session storage so we only load the tos once per session +) diff --git a/strr-platform-web/nuxt.config.ts b/strr-platform-web/nuxt.config.ts index 9aae988d..af27bac3 100644 --- a/strr-platform-web/nuxt.config.ts +++ b/strr-platform-web/nuxt.config.ts @@ -89,7 +89,10 @@ export default defineNuxtConfig({ paymentPortalUrl: process.env.NUXT_PAYMENT_PORTAL_URL, baseUrl: process.env.NUXT_BASE_URL, environment: process.env.NUXT_ENVIRONMENT_HEADER || '', - version: `STRR Platform UI v${process.env.npm_package_version}` + version: `STRR Platform UI v${process.env.npm_package_version}`, + housingStrrUrl: process.env.NUXT_REGISTRY_HOME_URL, // TODO: update to NUXT_HOUSING_STRR_URL once we get the housing strr url set + // TODO: move to app config for core layer ? + declineTosRedirectUrl: process.env.NUXT_REGISTRY_HOME_URL // TODO: update to NUXT_HOUSING_STRR_URL once we get the housing strr url set // set by layer - still required in .env // keycloakAuthUrl - NUXT_KEYCLOAK_AUTH_URL // keycloakClientId - NUXT_KEYCLOAK_CLIENTID