mirror of
https://github.com/open-webui/open-webui.git
synced 2026-10-07 02:58:21 +00:00
refac
This commit is contained in:
parent
8bd2671007
commit
bda14fe416
4 changed files with 74 additions and 36 deletions
|
|
@ -3,6 +3,7 @@
|
|||
import { mfaRequest, type MfaChallenge } from '$lib/apis/auths/mfa';
|
||||
import MfaRecoveryCodes from './MfaRecoveryCodes.svelte';
|
||||
import ChevronRight from '$lib/components/icons/ChevronRight.svelte';
|
||||
import Spinner from '$lib/components/common/Spinner.svelte';
|
||||
const i18n: any = getContext('i18n');
|
||||
export let challenge: MfaChallenge;
|
||||
export let onComplete: (result: any) => void | Promise<void>;
|
||||
|
|
@ -48,10 +49,10 @@
|
|||
recovery
|
||||
}
|
||||
);
|
||||
code = '';
|
||||
setup = null;
|
||||
if (response.recovery_codes) result = response;
|
||||
else await onComplete(response);
|
||||
code = '';
|
||||
setup = null;
|
||||
}
|
||||
} catch (e) {
|
||||
error = e instanceof Error ? e.message : String(e);
|
||||
|
|
@ -65,10 +66,10 @@
|
|||
{#if result}
|
||||
<MfaRecoveryCodes
|
||||
codes={result.recovery_codes}
|
||||
onContinue={() => {
|
||||
onContinue={async () => {
|
||||
const { recovery_codes, ...completed } = result;
|
||||
await onComplete(completed);
|
||||
result = null;
|
||||
onComplete(completed);
|
||||
}}
|
||||
/>
|
||||
{:else}
|
||||
|
|
@ -122,7 +123,9 @@
|
|||
on:click={loadSetup}>{$i18n.t('Retry setup')}</button
|
||||
>{/if}
|
||||
{/if}
|
||||
<label class="block text-[0.8125rem] leading-5 font-normal text-left text-gray-600 dark:text-gray-400">
|
||||
<label
|
||||
class="block text-[0.8125rem] leading-5 font-normal text-left text-gray-600 dark:text-gray-400"
|
||||
>
|
||||
{$i18n.t(
|
||||
challenge.next_step === 'recover'
|
||||
? 'Operator recovery token'
|
||||
|
|
@ -133,6 +136,7 @@
|
|||
<input
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
bind:value={code}
|
||||
readonly={busy}
|
||||
placeholder={$i18n.t(
|
||||
challenge.next_step === 'recover'
|
||||
? 'Enter your recovery token'
|
||||
|
|
@ -159,10 +163,14 @@
|
|||
<div class="flex justify-end text-gray-700 dark:text-gray-300">
|
||||
<button
|
||||
type="button"
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-gray-200 transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex justify-center"
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-gray-200 transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex items-center justify-center gap-1.5"
|
||||
disabled={busy || !code.trim() || (challenge.next_step === 'enroll' && !setup)}
|
||||
on:click={verify}>{$i18n.t(busy ? 'Verifying…' : 'Continue')}</button
|
||||
aria-busy={busy}
|
||||
on:click={verify}
|
||||
>
|
||||
{$i18n.t(busy ? 'Verifying…' : 'Continue')}
|
||||
{#if busy}<Spinner />{/if}
|
||||
</button>
|
||||
</div>
|
||||
<div
|
||||
class="flex flex-wrap items-center justify-between gap-2 text-[0.6875rem] text-gray-500 dark:text-gray-400"
|
||||
|
|
|
|||
|
|
@ -1,9 +1,25 @@
|
|||
<script lang="ts">
|
||||
import { getContext } from 'svelte';
|
||||
import Spinner from '$lib/components/common/Spinner.svelte';
|
||||
const i18n: any = getContext('i18n');
|
||||
export let codes: string[];
|
||||
export let onContinue: () => void;
|
||||
export let onContinue: () => void | Promise<void>;
|
||||
let saved = false;
|
||||
let busy = false;
|
||||
let error = '';
|
||||
|
||||
const continueHandler = async () => {
|
||||
if (busy || !saved) return;
|
||||
busy = true;
|
||||
error = '';
|
||||
try {
|
||||
await onContinue();
|
||||
} catch (e) {
|
||||
error = e instanceof Error ? e.message : String(e);
|
||||
} finally {
|
||||
busy = false;
|
||||
}
|
||||
};
|
||||
|
||||
const download = () => {
|
||||
const url = URL.createObjectURL(new Blob([codes.join('\n') + '\n'], { type: 'text/plain' }));
|
||||
|
|
@ -39,14 +55,22 @@
|
|||
class="size-3 rounded-sm accent-gray-900 dark:accent-gray-100"
|
||||
type="checkbox"
|
||||
bind:checked={saved}
|
||||
disabled={busy}
|
||||
/>{$i18n.t('I have saved my recovery codes')}</label
|
||||
>
|
||||
{#if error}<p role="alert" class="text-xs leading-4 text-red-600 dark:text-red-400">
|
||||
{error}
|
||||
</p>{/if}
|
||||
<div class="flex justify-end text-gray-700 dark:text-gray-300">
|
||||
<button
|
||||
type="button"
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-gray-200 transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex justify-center"
|
||||
disabled={!saved}
|
||||
on:click={onContinue}>{$i18n.t('Continue')}</button
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-gray-200 transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex items-center justify-center gap-1.5"
|
||||
disabled={busy || !saved}
|
||||
aria-busy={busy}
|
||||
on:click={continueHandler}
|
||||
>
|
||||
{$i18n.t('Continue')}
|
||||
{#if busy}<Spinner />{/if}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -54,9 +54,9 @@
|
|||
|
||||
<div class="space-y-2.5 text-xs">
|
||||
{#if codes.length}
|
||||
<div class="max-w-sm"><MfaRecoveryCodes {codes} onContinue={signIn} /></div>
|
||||
<div class="w-full sm:max-w-md"><MfaRecoveryCodes {codes} onContinue={signIn} /></div>
|
||||
{:else if challenge}
|
||||
<div class="max-w-sm">
|
||||
<div class="w-full sm:max-w-md">
|
||||
<MfaChallengeForm
|
||||
{challenge}
|
||||
onComplete={signIn}
|
||||
|
|
@ -86,7 +86,7 @@
|
|||
: $i18n.t('Managed by your administrator.')}
|
||||
</p>
|
||||
{#if show && status.required && status.enabled}
|
||||
<div class="max-w-sm space-y-2.5 py-1">
|
||||
<div class="w-full sm:max-w-md space-y-2.5 py-1">
|
||||
<p class="text-[0.6875rem] leading-4 text-gray-400 dark:text-gray-500">
|
||||
{$i18n.t('Verify with a fresh code. Changes sign out all devices.')}
|
||||
</p>
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@
|
|||
redirectPath = $page.url.searchParams.get('redirect') || '/';
|
||||
}
|
||||
|
||||
goto(redirectPath);
|
||||
await goto(redirectPath);
|
||||
localStorage.removeItem('redirectPath');
|
||||
}
|
||||
};
|
||||
|
|
@ -261,9 +261,7 @@
|
|||
>
|
||||
<div class="w-full px-6 min-h-screen flex flex-col text-center">
|
||||
{#if mfaChallenge}
|
||||
<div
|
||||
class="my-auto mx-auto w-full max-w-sm shrink-0 p-5"
|
||||
>
|
||||
<div class="my-auto mx-auto w-full sm:max-w-md shrink-0">
|
||||
<MfaChallengeForm
|
||||
challenge={mfaChallenge}
|
||||
onComplete={setSessionUser}
|
||||
|
|
@ -342,14 +340,16 @@
|
|||
<div class="flex flex-col mt-4">
|
||||
{#if mode === 'signup'}
|
||||
<div class="mb-2">
|
||||
<label for="name" class="text-sm font-normal text-left mb-1 block"
|
||||
<label
|
||||
for="name"
|
||||
class="text-[0.8125rem] leading-5 font-normal text-left mb-1 block"
|
||||
>{$i18n.t('Name')}</label
|
||||
>
|
||||
<input
|
||||
bind:value={name}
|
||||
type="text"
|
||||
id="name"
|
||||
class="my-0.5 w-full text-sm outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
autocomplete="name"
|
||||
placeholder={$i18n.t('Enter Your Full Name')}
|
||||
required
|
||||
|
|
@ -359,13 +359,15 @@
|
|||
|
||||
{#if mode === 'ldap'}
|
||||
<div class="mb-2">
|
||||
<label for="username" class="text-sm font-normal text-left mb-1 block"
|
||||
<label
|
||||
for="username"
|
||||
class="text-[0.8125rem] leading-5 font-normal text-left mb-1 block"
|
||||
>{$i18n.t('Username')}</label
|
||||
>
|
||||
<input
|
||||
bind:value={ldapUsername}
|
||||
type="text"
|
||||
class="my-0.5 w-full text-sm outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
autocomplete="username"
|
||||
name="username"
|
||||
id="username"
|
||||
|
|
@ -375,14 +377,16 @@
|
|||
</div>
|
||||
{:else}
|
||||
<div class="mb-2">
|
||||
<label for="email" class="text-sm font-normal text-left mb-1 block"
|
||||
<label
|
||||
for="email"
|
||||
class="text-[0.8125rem] leading-5 font-normal text-left mb-1 block"
|
||||
>{$i18n.t('Email')}</label
|
||||
>
|
||||
<input
|
||||
bind:value={email}
|
||||
type="email"
|
||||
id="email"
|
||||
class="my-0.5 w-full text-sm outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
autocomplete="email"
|
||||
name="email"
|
||||
placeholder={$i18n.t('Enter Your Email')}
|
||||
|
|
@ -392,14 +396,16 @@
|
|||
{/if}
|
||||
|
||||
<div>
|
||||
<label for="password" class="text-sm font-normal text-left mb-1 block"
|
||||
<label
|
||||
for="password"
|
||||
class="text-[0.8125rem] leading-5 font-normal text-left mb-1 block"
|
||||
>{$i18n.t('Password')}</label
|
||||
>
|
||||
<SensitiveInput
|
||||
bind:value={password}
|
||||
type="password"
|
||||
id="password"
|
||||
class="my-0.5 w-full text-sm outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent placeholder:text-gray-300 dark:placeholder:text-gray-600"
|
||||
placeholder={$i18n.t('Enter Your Password')}
|
||||
autocomplete={mode === 'signup' ? 'new-password' : 'current-password'}
|
||||
name="password"
|
||||
|
|
@ -413,14 +419,14 @@
|
|||
<div class="mt-2">
|
||||
<label
|
||||
for="confirm-password"
|
||||
class="text-sm font-normal text-left mb-1 block"
|
||||
class="text-[0.8125rem] leading-5 font-normal text-left mb-1 block"
|
||||
>{$i18n.t('Confirm Password')}</label
|
||||
>
|
||||
<SensitiveInput
|
||||
bind:value={confirmPassword}
|
||||
type="password"
|
||||
id="confirm-password"
|
||||
class="my-0.5 w-full text-sm outline-hidden bg-transparent"
|
||||
class="my-0.5 w-full text-[0.8125rem] leading-5 outline-hidden bg-transparent"
|
||||
placeholder={$i18n.t('Confirm Your Password')}
|
||||
autocomplete="new-password"
|
||||
name="confirm-password"
|
||||
|
|
@ -434,7 +440,7 @@
|
|||
{#if $config?.features.enable_login_form || $config?.features.enable_ldap || form}
|
||||
{#if mode === 'ldap'}
|
||||
<button
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5 disabled:opacity-50 flex justify-center"
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex justify-center"
|
||||
type="submit"
|
||||
disabled={submitting}
|
||||
>
|
||||
|
|
@ -448,7 +454,7 @@
|
|||
</button>
|
||||
{:else}
|
||||
<button
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5 disabled:opacity-50 flex justify-center"
|
||||
class="bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5 disabled:opacity-50 flex justify-center"
|
||||
type="submit"
|
||||
disabled={submitting}
|
||||
>
|
||||
|
|
@ -468,7 +474,7 @@
|
|||
</button>
|
||||
|
||||
{#if $config?.features.enable_signup && !($config?.onboarding ?? false)}
|
||||
<div class=" mt-4 text-sm text-center">
|
||||
<div class=" mt-4 text-[0.8125rem] leading-5 text-center">
|
||||
{mode === 'signin'
|
||||
? $i18n.t("Don't have an account?")
|
||||
: $i18n.t('Already have an account?')}
|
||||
|
|
@ -508,7 +514,7 @@
|
|||
<div class="flex flex-col space-y-2">
|
||||
{#if $config?.oauth?.providers?.google}
|
||||
<button
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5"
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5"
|
||||
on:click={() => {
|
||||
window.location.href = `${WEBUI_BASE_URL}/oauth/google/login`;
|
||||
}}
|
||||
|
|
@ -538,7 +544,7 @@
|
|||
{/if}
|
||||
{#if $config?.oauth?.providers?.microsoft}
|
||||
<button
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5"
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5"
|
||||
on:click={() => {
|
||||
window.location.href = `${WEBUI_BASE_URL}/oauth/microsoft/login`;
|
||||
}}
|
||||
|
|
@ -569,7 +575,7 @@
|
|||
{/if}
|
||||
{#if $config?.oauth?.providers?.github}
|
||||
<button
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5"
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5"
|
||||
on:click={() => {
|
||||
window.location.href = `${WEBUI_BASE_URL}/oauth/github/login`;
|
||||
}}
|
||||
|
|
@ -590,7 +596,7 @@
|
|||
{/if}
|
||||
{#if $config?.oauth?.providers?.oidc}
|
||||
<button
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5"
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5"
|
||||
on:click={() => {
|
||||
window.location.href = `${WEBUI_BASE_URL}/oauth/oidc/login`;
|
||||
}}
|
||||
|
|
@ -620,7 +626,7 @@
|
|||
{/if}
|
||||
{#if $config?.oauth?.providers?.feishu}
|
||||
<button
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-sm py-2.5"
|
||||
class="flex justify-center items-center bg-gray-700/5 hover:bg-gray-700/10 dark:bg-gray-100/5 dark:hover:bg-gray-100/10 dark:text-gray-300 dark:hover:text-white transition w-full rounded-full font-normal text-[0.8125rem] leading-5 py-2.5"
|
||||
on:click={() => {
|
||||
window.location.href = `${WEBUI_BASE_URL}/oauth/feishu/login`;
|
||||
}}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue