Simplified My Profile authentication flows, fixed some UX issues with reauth cancelled/accepted leading to incorrect states.
This commit is contained in:
+19
-72
@@ -13,8 +13,7 @@
|
||||
<script setup>
|
||||
import { computed, onMounted, onUnmounted, ref } from 'vue'
|
||||
import { useAuthStore } from '@/stores/auth'
|
||||
import { apiJson, SessionValidator, createAuthIframe, removeAuthIframe } from 'paskia'
|
||||
import { getAuthIframeUrl } from '@/utils/api'
|
||||
import { apiJson, SessionValidator } from 'paskia'
|
||||
import { updateThemeFromSession } from '@/utils/theme'
|
||||
import StatusMessage from '@/components/StatusMessage.vue'
|
||||
import ProfileView from '@/components/ProfileView.vue'
|
||||
@@ -49,19 +48,29 @@ const isHostMode = computed(() => {
|
||||
return currentHost !== configuredHost
|
||||
})
|
||||
|
||||
function terminateSession() {
|
||||
function onSessionLost(e) {
|
||||
store.userInfo = null
|
||||
viewState.value = 'terminal'
|
||||
store.ctx = null
|
||||
if (e?.name === 'AuthCancelledError') {
|
||||
viewState.value = 'terminal'
|
||||
} else {
|
||||
store.showMessage(e?.message || 'Session lost', 'error', 5000)
|
||||
viewState.value = 'terminal'
|
||||
}
|
||||
}
|
||||
|
||||
const userUuidGetter = () => store.ctx?.user.uuid
|
||||
const sessionValidator = new SessionValidator(userUuidGetter, terminateSession)
|
||||
const sessionValidator = new SessionValidator(userUuidGetter, onSessionLost)
|
||||
|
||||
onMounted(() => sessionValidator.start())
|
||||
onUnmounted(() => sessionValidator.stop())
|
||||
|
||||
async function loadUserInfo() {
|
||||
viewState.value = 'loading'
|
||||
loadingMessage.value = 'Loading...'
|
||||
try {
|
||||
// apiJson handles 401/403 with auth.iframe automatically:
|
||||
// shows overlay iframe, waits for auth, retries the request.
|
||||
const [validateData, userInfoData] = await Promise.all([
|
||||
apiJson('/auth/api/validate', { method: 'POST' }),
|
||||
apiJson('/auth/api/user-info', { method: 'GET' })
|
||||
@@ -73,67 +82,15 @@ async function loadUserInfo() {
|
||||
if (store.userInfo.user.uuid !== store.ctx.user.uuid) {
|
||||
console.error('User UUID mismatch between user-info and validate responses')
|
||||
window.location.reload()
|
||||
return false
|
||||
return
|
||||
}
|
||||
viewState.value = 'profile'
|
||||
return true
|
||||
} catch {
|
||||
store.userInfo = null
|
||||
store.ctx = null
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
async function showAuthIframe() {
|
||||
const url = await getAuthIframeUrl('login')
|
||||
createAuthIframe(url)
|
||||
loadingMessage.value = 'Authentication required...'
|
||||
}
|
||||
|
||||
function handleAuthMessage(event) {
|
||||
const data = event.data
|
||||
if (!data?.type) return
|
||||
|
||||
switch (data.type) {
|
||||
case 'auth-success':
|
||||
// Authentication successful - reload user info
|
||||
removeAuthIframe()
|
||||
viewState.value = 'loading'
|
||||
loadingMessage.value = 'Loading user profile...'
|
||||
loadUserInfo()
|
||||
break
|
||||
|
||||
case 'auth-error':
|
||||
// Authentication failed - keep iframe open so user can retry
|
||||
if (data.cancelled) {
|
||||
console.log('Authentication cancelled by user')
|
||||
} else {
|
||||
store.showMessage(data.message || 'Authentication failed', 'error', 5000)
|
||||
}
|
||||
break
|
||||
|
||||
case 'auth-cancelled':
|
||||
// Legacy support - treat as auth-error with cancelled flag
|
||||
console.log('Authentication cancelled')
|
||||
break
|
||||
|
||||
case 'auth-back':
|
||||
// User clicked Back - show terminal state
|
||||
removeAuthIframe()
|
||||
terminateSession()
|
||||
break
|
||||
|
||||
case 'auth-close-request':
|
||||
// Legacy support - treat as back
|
||||
removeAuthIframe()
|
||||
break
|
||||
} catch (e) {
|
||||
onSessionLost(e)
|
||||
}
|
||||
}
|
||||
|
||||
onMounted(async () => {
|
||||
// Listen for postMessage from auth iframe
|
||||
window.addEventListener('message', handleAuthMessage)
|
||||
|
||||
// Load settings
|
||||
await store.loadSettings()
|
||||
|
||||
@@ -147,17 +104,7 @@ onMounted(async () => {
|
||||
document.title = inHostMode ? `${rpName} · Account summary` : rpName
|
||||
}
|
||||
|
||||
// Try to load user info
|
||||
const success = await loadUserInfo()
|
||||
|
||||
if (!success) {
|
||||
// Need authentication - show login iframe
|
||||
showAuthIframe()
|
||||
}
|
||||
})
|
||||
|
||||
onUnmounted(() => {
|
||||
window.removeEventListener('message', handleAuthMessage)
|
||||
removeAuthIframe()
|
||||
// Load user info (apiJson handles auth iframe if needed)
|
||||
await loadUserInfo()
|
||||
})
|
||||
</script>
|
||||
|
||||
Reference in New Issue
Block a user