feat: article editor core
This commit is contained in:
1 parent
d493a181e1
commit
a4734b2c91
55 files changed
+4186
-496
No files matched your search
+40
-12
@@ -63,7 +63,8 @@ const passwordError = ref('')
|
||||
const submitting = ref(false)
|
||||
const passwordShown = ref(false)
|
||||
|
||||
const initialReason = typeof route.query.reason === 'string' ? route.query.reason : null
|
||||
const initialReason =
|
||||
typeof route.query.reason === 'string' ? route.query.reason : null
|
||||
|
||||
const alert = ref<AlertState | null>(
|
||||
initialReason === 'expired'
|
||||
@@ -73,7 +74,9 @@ const alert = ref<AlertState | null>(
|
||||
: null,
|
||||
)
|
||||
|
||||
const alertRole = computed(() => (alert.value?.tone === 'error' ? 'alert' : 'status'))
|
||||
const alertRole = computed(() =>
|
||||
alert.value?.tone === 'error' ? 'alert' : 'status',
|
||||
)
|
||||
|
||||
const submitLabel = computed(() => {
|
||||
if (submitting.value) {
|
||||
@@ -85,7 +88,9 @@ const submitLabel = computed(() => {
|
||||
return 'Log in'
|
||||
})
|
||||
|
||||
const submitDisabled = computed(() => submitting.value || retryAfter.active.value)
|
||||
const submitDisabled = computed(
|
||||
() => submitting.value || retryAfter.active.value,
|
||||
)
|
||||
|
||||
async function focusField(selector: string) {
|
||||
await nextTick()
|
||||
@@ -112,15 +117,18 @@ function focusFirstInvalid() {
|
||||
}
|
||||
|
||||
function validate() {
|
||||
usernameError.value = username.value.trim().length < 3 ? 'Use at least 3 characters.' : ''
|
||||
passwordError.value = password.value.length === 0 ? 'Enter your password.' : ''
|
||||
usernameError.value =
|
||||
username.value.trim().length < 3 ? 'Use at least 3 characters.' : ''
|
||||
passwordError.value =
|
||||
password.value.length === 0 ? 'Enter your password.' : ''
|
||||
return !usernameError.value && !passwordError.value
|
||||
}
|
||||
|
||||
async function afterLoginSuccess() {
|
||||
await session.retry()
|
||||
|
||||
const redirect = typeof route.query.redirect === 'string' ? route.query.redirect : null
|
||||
const redirect =
|
||||
typeof route.query.redirect === 'string' ? route.query.redirect : null
|
||||
if (redirect) {
|
||||
await router.push(redirect)
|
||||
return
|
||||
@@ -166,7 +174,10 @@ async function onSubmit() {
|
||||
await api.request('/v1/auth/login', {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({ username: username.value, password: password.value }),
|
||||
body: JSON.stringify({
|
||||
username: username.value,
|
||||
password: password.value,
|
||||
}),
|
||||
})
|
||||
await afterLoginSuccess()
|
||||
} catch (error) {
|
||||
@@ -182,7 +193,9 @@ onMounted(async () => {
|
||||
}
|
||||
|
||||
try {
|
||||
const status = await api.request<{ open: boolean }>('/v1/auth/registration')
|
||||
const status = await api.request<{ open: boolean }>(
|
||||
'/v1/auth/registration',
|
||||
)
|
||||
registrationOpen.value = status.open
|
||||
} catch {
|
||||
registrationOpen.value = false
|
||||
@@ -191,7 +204,10 @@ onMounted(async () => {
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<AuthShell title="Log in" description="Welcome back. Log in to manage your articles.">
|
||||
<AuthShell
|
||||
title="Log in"
|
||||
description="Welcome back. Log in to manage your articles."
|
||||
>
|
||||
<template v-if="alert" #notice>
|
||||
<UAlert
|
||||
:color="alert.tone"
|
||||
@@ -205,7 +221,11 @@ onMounted(async () => {
|
||||
</template>
|
||||
|
||||
<template #default="{ controlSize, controlClass, inputClass }">
|
||||
<UForm :state="{ username, password }" class="flex flex-col gap-4.5" @submit="onSubmit">
|
||||
<UForm
|
||||
:state="{ username, password }"
|
||||
class="flex flex-col gap-4.5"
|
||||
@submit="onSubmit"
|
||||
>
|
||||
<UFormField
|
||||
label="Username"
|
||||
name="username"
|
||||
@@ -275,13 +295,21 @@ onMounted(async () => {
|
||||
>
|
||||
<template #trailing>
|
||||
<UButton
|
||||
:icon="passwordShown ? 'i-lucide-eye-off' : 'i-lucide-eye'"
|
||||
:icon="
|
||||
passwordShown
|
||||
? 'i-lucide-eye-off'
|
||||
: 'i-lucide-eye'
|
||||
"
|
||||
variant="ghost"
|
||||
color="neutral"
|
||||
size="sm"
|
||||
square
|
||||
class="size-8 justify-center text-toned"
|
||||
:aria-label="passwordShown ? 'Hide password' : 'Show password'"
|
||||
:aria-label="
|
||||
passwordShown
|
||||
? 'Hide password'
|
||||
: 'Show password'
|
||||
"
|
||||
:aria-pressed="passwordShown"
|
||||
@click="passwordShown = !passwordShown"
|
||||
/>
|
||||
|
||||
Reference in new issue
Block a user