Skip to content

Commit

Permalink
refactor: enrich Plain page layout and simplify associated pages
Browse files Browse the repository at this point in the history
  • Loading branch information
kulmann committed Nov 2, 2022
1 parent 1263659 commit a501b04
Show file tree
Hide file tree
Showing 9 changed files with 330 additions and 299 deletions.
14 changes: 10 additions & 4 deletions packages/web-runtime/src/App.vue
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ import LayoutLoading from './layouts/Loading.vue'
import LayoutPlain from './layouts/Plain.vue'
import { getBackendVersion, getWebVersion } from './container/versions'
import { defineComponent } from '@vue/composition-api'
import { isPublicLinkContext, isUserContext, isAnonymousContext } from './router'
import { isPublicLinkContext, isUserContext } from './router'
import { additionalTranslations } from './helpers/additionalTranslations' // eslint-disable-line
import { eventBus } from 'web-pkg/src/services'
Expand All @@ -70,17 +70,23 @@ export default defineComponent({
...mapGetters(['configuration', 'capabilities', 'getSettingsValue']),
...mapGetters('runtime/auth', ['isUserContextReady', 'isPublicLinkContextReady']),
layout() {
if (!this.$route.name || isAnonymousContext(this.$router, this.$route)) {
const plainLayoutRoutes = [
'login',
'logout',
'oidcCallback',
'oidcSilentRedirect',
'resolvePublicLink',
'accessDenied'
]
if (!this.$route.name || plainLayoutRoutes.includes(this.$route.name)) {
return LayoutPlain
}
if (isPublicLinkContext(this.$router, this.$route)) {
return this.isPublicLinkContextReady ? LayoutApplication : LayoutLoading
}
if (isUserContext(this.$router, this.$route)) {
return this.isUserContextReady ? LayoutApplication : LayoutLoading
}
return LayoutApplication
},
favicon() {
Expand Down
28 changes: 25 additions & 3 deletions packages/web-runtime/src/layouts/Plain.vue
Original file line number Diff line number Diff line change
@@ -1,13 +1,35 @@
<template>
<div>
<div
class="oc-login oc-height-viewport"
:style="{ backgroundImage: 'url(' + backgroundImg + ')' }"
>
<h1 class="oc-invisible-sr" v-text="pageTitle" />
<router-view />
</div>
</template>

<script lang="ts">
import { defineComponent } from '@vue/composition-api'
import { computed, defineComponent, unref } from '@vue/composition-api'
import { useRouteMeta, useStore, useTranslations } from 'web-pkg'
export default defineComponent({
name: 'PlainLayout'
name: 'PlainLayout',
setup() {
const store = useStore()
const { $gettext } = useTranslations()
const title = useRouteMeta('title')
const pageTitle = computed(() => {
return $gettext(unref(title))
})
const backgroundImg = computed(() => {
return store.getters.configuration?.currentTheme?.loginPage?.backgroundImg
})
return {
pageTitle,
backgroundImg
}
}
})
</script>
98 changes: 49 additions & 49 deletions packages/web-runtime/src/pages/accessDenied.vue
Original file line number Diff line number Diff line change
@@ -1,63 +1,63 @@
<template>
<div
class="oc-login oc-height-viewport"
:style="{ backgroundImage: 'url(' + backgroundImg + ')' }"
>
<h1 class="oc-invisible-sr" v-text="pageTitle" />
<div class="oc-login-card-wrapper oc-height-viewport oc-flex oc-flex-center oc-flex-middle">
<div class="oc-login-card">
<img class="oc-login-logo" :src="logoImg" alt="" :aria-hidden="true" />
<div class="oc-login-card-body oc-width-medium">
<h2 class="oc-login-card-title" v-text="cardTitle" />
<p v-text="cardHint" />
</div>
<div class="oc-height-viewport oc-flex oc-flex-column oc-flex-center oc-flex-middle">
<div class="oc-login-card">
<img class="oc-login-logo" :src="logoImg" alt="" :aria-hidden="true" />
<div class="oc-login-card-body oc-width-medium">
<h2 class="oc-login-card-title" v-text="cardTitle" />
<p v-text="cardHint" />
</div>
<div class="oc-login-card-footer oc-pt-rm">
<p>
{{ footerSlogan }}
</p>
</div>
<oc-button
id="exitAnchor"
type="router-link"
class="oc-mt-m oc-width-medium"
:to="{ name: 'login' }"
size="large"
appearance="filled"
variation="primary"
v-text="navigateToLoginText"
/>
</div>
<oc-button
id="exitAnchor"
type="router-link"
class="oc-mt-m oc-width-medium"
:to="{ name: 'login' }"
size="large"
appearance="filled"
variation="primary"
v-text="navigateToLoginText"
/>
</div>
</template>

<script lang="ts">
import { defineComponent } from '@vue/composition-api'
import { mapGetters } from 'vuex'
import { computed, defineComponent } from '@vue/composition-api'
import { useStore, useTranslations } from 'web-pkg'
export default defineComponent({
name: 'AccessDeniedPage',
computed: {
...mapGetters(['configuration']),
pageTitle() {
return this.$gettext(this.$route.meta.title)
},
cardTitle() {
return this.$gettext('Logged out')
},
cardHint() {
return this.$gettext('You were automatically logged out for security reasons.')
},
navigateToLoginText() {
return this.$gettext('Log in again')
},
logoImg() {
return this.configuration.currentTheme.logo.login
},
backgroundImg() {
return this.configuration.currentTheme.loginPage.backgroundImg
setup() {
const store = useStore()
const { $gettext } = useTranslations()
const logoImg = computed(() => {
return store.getters.configuration.currentTheme.logo.login
})
const cardTitle = computed(() => {
return $gettext('Logged out')
})
const cardHint = computed(() => {
return $gettext('You were automatically logged out for security reasons.')
})
const footerSlogan = computed(() => {
return store.getters.configuration.currentTheme.general.slogan
})
const navigateToLoginText = computed(() => {
return $gettext('Log in again')
})
return {
logoImg,
cardTitle,
cardHint,
footerSlogan,
navigateToLoginText
}
}
})
</script>

<style lang="scss" scoped>
.oc-login-card-wrapper {
flex-flow: column;
}
</style>
129 changes: 57 additions & 72 deletions packages/web-runtime/src/pages/login.vue
Original file line number Diff line number Diff line change
@@ -1,91 +1,76 @@
<template>
<div
v-if="initialized"
class="oc-login oc-height-viewport"
:style="{ backgroundImage: 'url(' + backgroundImg + ')' }"
>
<h1 class="oc-invisible-sr">{{ pageTitle }}</h1>
<div class="oc-login-card oc-position-center">
<img class="oc-login-logo" :src="logoImg" alt="" :aria-hidden="true" />
<div class="oc-login-card-body">
<h2 class="oc-login-card-title">
<translate :translate-params="{ productName: $_productName }"
>Welcome to %{productName}</translate
>
</h2>
<p v-translate>
Please click the button below to authenticate and get access to your data.
</p>
<oc-button
id="authenticate"
size="large"
variation="primary"
appearance="filled"
class="oc-login-authorize-button"
@click="performLogin"
>
<translate>Login</translate>
</oc-button>
</div>
<div class="oc-login-card-footer">
<p>
{{ configuration.currentTheme.general.slogan }}
</p>
<div class="oc-width-1-1 oc-height-1-1">
<app-loading-spinner v-if="autoRedirect" />
<div v-else class="oc-height-viewport oc-flex oc-flex-column oc-flex-center oc-flex-middle">
<div class="oc-login-card">
<img class="oc-login-logo" :src="logoImg" alt="" :aria-hidden="true" />
<div class="oc-login-card-body oc-width-medium">
<h2 class="oc-login-card-title">
<translate :translate-params="{ productName }">Welcome to %{productName}</translate>
</h2>
<p v-translate>
Please click the button below to authenticate and get access to your data.
</p>
</div>
<div class="oc-login-card-footer oc-pt-rm">
<p>{{ footerSlogan }}</p>
</div>
</div>
<oc-button
id="authenticate"
size="large"
variation="primary"
appearance="filled"
class="oc-mt-m oc-width-medium oc-login-authorize-button"
@click="performLogin"
>
<translate>Login</translate>
</oc-button>
</div>
</div>
</template>

<script lang="ts">
import { mapGetters } from 'vuex'
import { authService } from '../services/auth'
import { queryItemAsString, useRouteQuery } from 'web-pkg/src/composables'
import { defineComponent } from '@vue/composition-api'
import { queryItemAsString, useRouteQuery, useStore } from 'web-pkg/src/composables'
import { computed, defineComponent, unref } from '@vue/composition-api'
import AppLoadingSpinner from 'web-pkg/src/components/AppLoadingSpinner.vue'
export default defineComponent({
name: 'LoginPage',
setup() {
return {
redirectUrl: useRouteQuery('redirectUrl')
}
components: {
AppLoadingSpinner
},
data() {
return {
loading: false,
initialized: false
}
},
computed: {
...mapGetters(['configuration']),
pageTitle() {
return this.$gettext(this.$route.meta.title)
},
$_productName() {
return this.configuration.currentTheme.general.name
},
logoImg() {
return this.configuration.currentTheme.logo.login
},
setup() {
const store = useStore()
backgroundImg() {
return this.configuration.currentTheme.loginPage.backgroundImg
const redirectUrl = useRouteQuery('redirectUrl')
const performLogin = () => {
authService.loginUser(queryItemAsString(unref(redirectUrl)))
}
},
created() {
if (this.configuration.currentTheme.loginPage.autoRedirect) {
this.performLogin()
} else {
this.initialized = true
const autoRedirect = computed(() => {
return store.getters.configuration.currentTheme.loginPage.autoRedirect
})
if (unref(autoRedirect)) {
performLogin()
}
},
methods: {
performLogin() {
authService.loginUser(queryItemAsString(this.redirectUrl))
const productName = computed(() => {
return store.getters.configuration.currentTheme.general.name
})
const logoImg = computed(() => {
return store.getters.configuration.currentTheme.logo.login
})
const footerSlogan = computed(() => {
return store.getters.configuration.currentTheme.general.slogan
})
return {
autoRedirect,
productName,
logoImg,
footerSlogan,
performLogin
}
}
})
Expand Down
55 changes: 46 additions & 9 deletions packages/web-runtime/src/pages/logout.vue
Original file line number Diff line number Diff line change
@@ -1,15 +1,52 @@
<template>
<div>
<p v-translate>Please wait while you're being logged out.</p>
<div class="oc-login-card oc-position-center">
<img class="oc-login-logo" :src="logoImg" alt="" :aria-hidden="true" />
<div class="oc-login-card-body oc-width-medium">
<h2 class="oc-login-card-title" v-text="cardTitle" />
<p v-text="cardHint" />
</div>
<div class="oc-login-card-footer oc-pt-rm">
<p>
{{ footerSlogan }}
</p>
</div>
</div>
</template>
<script>
import { authService } from '../services/auth'
export default {
<script lang="ts">
import { computed, defineComponent } from '@vue/composition-api'
import { useRouter, useStore, useTranslations } from 'web-pkg'
import { authService } from 'web-runtime/src/services/auth'
export default defineComponent({
name: 'LogoutPage',
async created() {
await authService.logoutUser()
this.router.push({ name: 'login' })
setup() {
const router = useRouter()
const store = useStore()
const { $gettext } = useTranslations()
authService.logoutUser().then(() => {
router.push({ name: 'login' })
})
const logoImg = computed(() => {
return store.getters.configuration.currentTheme.logo.login
})
const cardTitle = computed(() => {
return $gettext('Logout in progress')
})
const cardHint = computed(() => {
return $gettext("Please wait while you're being logged out.")
})
const footerSlogan = computed(() => {
return store.getters.configuration.currentTheme.general.slogan
})
return {
logoImg,
cardTitle,
cardHint,
footerSlogan
}
}
}
})
</script>
Loading

0 comments on commit a501b04

Please sign in to comment.