forked from open-webui/open-webui
		
	frontend support api key
This commit is contained in:
		
							parent
							
								
									81e928030f
								
							
						
					
					
						commit
						b4b56f9c85
					
				
					 3 changed files with 276 additions and 65 deletions
				
			
		|  | @ -318,3 +318,78 @@ export const updateJWTExpiresDuration = async (token: string, duration: string) | ||||||
| 
 | 
 | ||||||
| 	return res; | 	return res; | ||||||
| }; | }; | ||||||
|  | 
 | ||||||
|  | export const createApiKey = async (token: string) => { | ||||||
|  | 	let error = null; | ||||||
|  | 
 | ||||||
|  | 	const res = await fetch(`${WEBUI_API_BASE_URL}/auths/api_key`, { | ||||||
|  | 		method: 'POST', | ||||||
|  | 		headers: { | ||||||
|  | 			'Content-Type': 'application/json', | ||||||
|  | 			Authorization: `Bearer ${token}` | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 		.then(async (res) => { | ||||||
|  | 			if (!res.ok) throw await res.json(); | ||||||
|  | 			return res.json(); | ||||||
|  | 		}) | ||||||
|  | 		.catch((err) => { | ||||||
|  | 			console.log(err); | ||||||
|  | 			error = err.detail; | ||||||
|  | 			return null; | ||||||
|  | 		}); | ||||||
|  | 	if (error) { | ||||||
|  | 		throw error; | ||||||
|  | 	} | ||||||
|  | 	return res; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | export const getApiKey = async (token: string) => { | ||||||
|  | 	let error = null; | ||||||
|  | 
 | ||||||
|  | 	const res = await fetch(`${WEBUI_API_BASE_URL}/auths/api_key`, { | ||||||
|  | 		method: 'GET', | ||||||
|  | 		headers: { | ||||||
|  | 			'Content-Type': 'application/json', | ||||||
|  | 			Authorization: `Bearer ${token}` | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 		.then(async (res) => { | ||||||
|  | 			if (!res.ok) throw await res.json(); | ||||||
|  | 			return res.json(); | ||||||
|  | 		}) | ||||||
|  | 		.catch((err) => { | ||||||
|  | 			console.log(err); | ||||||
|  | 			error = err.detail; | ||||||
|  | 			return null; | ||||||
|  | 		}); | ||||||
|  | 	if (error) { | ||||||
|  | 		throw error; | ||||||
|  | 	} | ||||||
|  | 	return res; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | export const deleteApiKey = async (token: string) => { | ||||||
|  | 	let error = null; | ||||||
|  | 
 | ||||||
|  | 	const res = await fetch(`${WEBUI_API_BASE_URL}/auths/api_key`, { | ||||||
|  | 		method: 'DELETE', | ||||||
|  | 		headers: { | ||||||
|  | 			'Content-Type': 'application/json', | ||||||
|  | 			Authorization: `Bearer ${token}` | ||||||
|  | 		} | ||||||
|  | 	}) | ||||||
|  | 		.then(async (res) => { | ||||||
|  | 			if (!res.ok) throw await res.json(); | ||||||
|  | 			return res.json(); | ||||||
|  | 		}) | ||||||
|  | 		.catch((err) => { | ||||||
|  | 			console.log(err); | ||||||
|  | 			error = err.detail; | ||||||
|  | 			return null; | ||||||
|  | 		}); | ||||||
|  | 	if (error) { | ||||||
|  | 		throw error; | ||||||
|  | 	} | ||||||
|  | 	return res; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | @ -3,7 +3,7 @@ | ||||||
| 	import { onMount, getContext } from 'svelte'; | 	import { onMount, getContext } from 'svelte'; | ||||||
| 
 | 
 | ||||||
| 	import { user } from '$lib/stores'; | 	import { user } from '$lib/stores'; | ||||||
| 	import { updateUserProfile } from '$lib/apis/auths'; | 	import { updateUserProfile, createApiKey } from '$lib/apis/auths'; | ||||||
| 
 | 
 | ||||||
| 	import UpdatePassword from './Account/UpdatePassword.svelte'; | 	import UpdatePassword from './Account/UpdatePassword.svelte'; | ||||||
| 	import { getGravatarUrl } from '$lib/apis/utils'; | 	import { getGravatarUrl } from '$lib/apis/utils'; | ||||||
|  | @ -17,6 +17,9 @@ | ||||||
| 	let name = ''; | 	let name = ''; | ||||||
| 	let showJWTToken = false; | 	let showJWTToken = false; | ||||||
| 	let JWTTokenCopied = false; | 	let JWTTokenCopied = false; | ||||||
|  | 	let showApiKey= false; | ||||||
|  | 	let ApiKeyCopied = false; | ||||||
|  | 	let localApiKey = localStorage.apiKey; | ||||||
| 	let profileImageInputElement: HTMLInputElement; | 	let profileImageInputElement: HTMLInputElement; | ||||||
| 
 | 
 | ||||||
| 	const submitHandler = async () => { | 	const submitHandler = async () => { | ||||||
|  | @ -33,6 +36,18 @@ | ||||||
| 		return false; | 		return false; | ||||||
| 	}; | 	}; | ||||||
| 
 | 
 | ||||||
|  | 	const createApiKeyHandler = async () => { | ||||||
|  | 		const apiKey = await createApiKey(localStorage.token); | ||||||
|  | 		if (apiKey) { | ||||||
|  | 			localApiKey = apiKey["api_key"]; | ||||||
|  | 			localStorage.apiKey = localApiKey; | ||||||
|  | 			toast.success($i18n.t('API Key created.')); | ||||||
|  | 		} else { | ||||||
|  | 			toast.error($i18n.t('Failed to create API Key.')); | ||||||
|  | 		 | ||||||
|  | 		} | ||||||
|  | 	}; | ||||||
|  | 
 | ||||||
| 	onMount(() => { | 	onMount(() => { | ||||||
| 		name = $user.name; | 		name = $user.name; | ||||||
| 		profileImageUrl = $user.profile_image_url; | 		profileImageUrl = $user.profile_image_url; | ||||||
|  | @ -170,41 +185,83 @@ | ||||||
| 
 | 
 | ||||||
| 		<hr class=" dark:border-gray-700 my-4" /> | 		<hr class=" dark:border-gray-700 my-4" /> | ||||||
| 
 | 
 | ||||||
| 		<div class=" w-full justify-between"> | 		<div class="flex flex-col gap-4"> | ||||||
| 			<div class="flex w-full justify-between"> | 			<div class="justify-between w-full "> | ||||||
| 				<div class=" self-center text-xs font-medium">{$i18n.t('JWT Token')}</div> | 				<div class="flex justify-between w-full"> | ||||||
| 			</div> | 					<div class="self-center text-xs font-medium ">{$i18n.t('JWT Token')}</div> | ||||||
|  | 				</div> | ||||||
| 
 | 
 | ||||||
| 			<div class="flex mt-2"> | 				<div class="flex mt-2"> | ||||||
| 				<div class="flex w-full"> | 					<div class="flex w-full"> | ||||||
| 					<input | 						<input | ||||||
| 						class="w-full rounded-l-lg py-1.5 pl-4 text-sm dark:text-gray-300 dark:bg-gray-800 outline-none" | 							class="w-full rounded-l-lg py-1.5 pl-4 text-sm dark:text-gray-300 dark:bg-gray-800 outline-none" | ||||||
| 						type={showJWTToken ? 'text' : 'password'} | 							type={showJWTToken ? 'text' : 'password'} | ||||||
| 						value={localStorage.token} | 							value={localStorage.token} | ||||||
| 						disabled | 							disabled | ||||||
| 					/> | 						/> | ||||||
|  | 
 | ||||||
|  | 						<button | ||||||
|  | 							class="px-2 transition rounded-r-lg dark:bg-gray-800" | ||||||
|  | 							on:click={() => { | ||||||
|  | 								showJWTToken = !showJWTToken; | ||||||
|  | 							}} | ||||||
|  | 						> | ||||||
|  | 							{#if showJWTToken} | ||||||
|  | 								<svg | ||||||
|  | 									xmlns="http://www.w3.org/2000/svg" | ||||||
|  | 									viewBox="0 0 16 16" | ||||||
|  | 									fill="currentColor" | ||||||
|  | 									class="w-4 h-4" | ||||||
|  | 								> | ||||||
|  | 									<path | ||||||
|  | 										fill-rule="evenodd" | ||||||
|  | 										d="M3.28 2.22a.75.75 0 0 0-1.06 1.06l10.5 10.5a.75.75 0 1 0 1.06-1.06l-1.322-1.323a7.012 7.012 0 0 0 2.16-3.11.87.87 0 0 0 0-.567A7.003 7.003 0 0 0 4.82 3.76l-1.54-1.54Zm3.196 3.195 1.135 1.136A1.502 1.502 0 0 1 9.45 8.389l1.136 1.135a3 3 0 0 0-4.109-4.109Z" | ||||||
|  | 										clip-rule="evenodd" | ||||||
|  | 									/> | ||||||
|  | 									<path | ||||||
|  | 										d="m7.812 10.994 1.816 1.816A7.003 7.003 0 0 1 1.38 8.28a.87.87 0 0 1 0-.566 6.985 6.985 0 0 1 1.113-2.039l2.513 2.513a3 3 0 0 0 2.806 2.806Z" | ||||||
|  | 									/> | ||||||
|  | 								</svg> | ||||||
|  | 							{:else} | ||||||
|  | 								<svg | ||||||
|  | 									xmlns="http://www.w3.org/2000/svg" | ||||||
|  | 									viewBox="0 0 16 16" | ||||||
|  | 									fill="currentColor" | ||||||
|  | 									class="w-4 h-4" | ||||||
|  | 								> | ||||||
|  | 									<path d="M8 9.5a1.5 1.5 0 1 0 0-3 1.5 1.5 0 0 0 0 3Z" /> | ||||||
|  | 									<path | ||||||
|  | 										fill-rule="evenodd" | ||||||
|  | 										d="M1.38 8.28a.87.87 0 0 1 0-.566 7.003 7.003 0 0 1 13.238.006.87.87 0 0 1 0 .566A7.003 7.003 0 0 1 1.379 8.28ZM11 8a3 3 0 1 1-6 0 3 3 0 0 1 6 0Z" | ||||||
|  | 										clip-rule="evenodd" | ||||||
|  | 									/> | ||||||
|  | 								</svg> | ||||||
|  | 							{/if} | ||||||
|  | 						</button> | ||||||
|  | 					</div> | ||||||
| 
 | 
 | ||||||
| 					<button | 					<button | ||||||
| 						class="dark:bg-gray-800 px-2 transition rounded-r-lg" | 						class="ml-1.5 px-1.5 py-1 hover:bg-gray-800 transition rounded-lg" | ||||||
| 						on:click={() => { | 						on:click={() => { | ||||||
| 							showJWTToken = !showJWTToken; | 							copyToClipboard(localStorage.token); | ||||||
|  | 							JWTTokenCopied = true; | ||||||
|  | 							setTimeout(() => { | ||||||
|  | 								JWTTokenCopied = false; | ||||||
|  | 							}, 2000); | ||||||
| 						}} | 						}} | ||||||
| 					> | 					> | ||||||
| 						{#if showJWTToken} | 						{#if JWTTokenCopied} | ||||||
| 							<svg | 							<svg | ||||||
| 								xmlns="http://www.w3.org/2000/svg" | 								xmlns="http://www.w3.org/2000/svg" | ||||||
| 								viewBox="0 0 16 16" | 								viewBox="0 0 20 20" | ||||||
| 								fill="currentColor" | 								fill="currentColor" | ||||||
| 								class="w-4 h-4" | 								class="w-4 h-4" | ||||||
| 							> | 							> | ||||||
| 								<path | 								<path | ||||||
| 									fill-rule="evenodd" | 									fill-rule="evenodd" | ||||||
| 									d="M3.28 2.22a.75.75 0 0 0-1.06 1.06l10.5 10.5a.75.75 0 1 0 1.06-1.06l-1.322-1.323a7.012 7.012 0 0 0 2.16-3.11.87.87 0 0 0 0-.567A7.003 7.003 0 0 0 4.82 3.76l-1.54-1.54Zm3.196 3.195 1.135 1.136A1.502 1.502 0 0 1 9.45 8.389l1.136 1.135a3 3 0 0 0-4.109-4.109Z" | 									d="M16.704 4.153a.75.75 0 01.143 1.052l-8 10.5a.75.75 0 01-1.127.075l-4.5-4.5a.75.75 0 011.06-1.06l3.894 3.893 7.48-9.817a.75.75 0 011.05-.143z" | ||||||
| 									clip-rule="evenodd" | 									clip-rule="evenodd" | ||||||
| 								/> | 								/> | ||||||
| 								<path |  | ||||||
| 									d="m7.812 10.994 1.816 1.816A7.003 7.003 0 0 1 1.38 8.28a.87.87 0 0 1 0-.566 6.985 6.985 0 0 1 1.113-2.039l2.513 2.513a3 3 0 0 0 2.806 2.806Z" |  | ||||||
| 								/> |  | ||||||
| 							</svg> | 							</svg> | ||||||
| 						{:else} | 						{:else} | ||||||
| 							<svg | 							<svg | ||||||
|  | @ -213,60 +270,127 @@ | ||||||
| 								fill="currentColor" | 								fill="currentColor" | ||||||
| 								class="w-4 h-4" | 								class="w-4 h-4" | ||||||
| 							> | 							> | ||||||
| 								<path d="M8 9.5a1.5 1.5 0 1 0 0-3 1.5 1.5 0 0 0 0 3Z" /> |  | ||||||
| 								<path | 								<path | ||||||
| 									fill-rule="evenodd" | 									fill-rule="evenodd" | ||||||
| 									d="M1.38 8.28a.87.87 0 0 1 0-.566 7.003 7.003 0 0 1 13.238.006.87.87 0 0 1 0 .566A7.003 7.003 0 0 1 1.379 8.28ZM11 8a3 3 0 1 1-6 0 3 3 0 0 1 6 0Z" | 									d="M11.986 3H12a2 2 0 0 1 2 2v6a2 2 0 0 1-1.5 1.937V7A2.5 2.5 0 0 0 10 4.5H4.063A2 2 0 0 1 6 3h.014A2.25 2.25 0 0 1 8.25 1h1.5a2.25 2.25 0 0 1 2.236 2ZM10.5 4v-.75a.75.75 0 0 0-.75-.75h-1.5a.75.75 0 0 0-.75.75V4h3Z" | ||||||
|  | 									clip-rule="evenodd" | ||||||
|  | 								/> | ||||||
|  | 								<path | ||||||
|  | 									fill-rule="evenodd" | ||||||
|  | 									d="M3 6a1 1 0 0 0-1 1v7a1 1 0 0 0 1 1h7a1 1 0 0 0 1-1V7a1 1 0 0 0-1-1H3Zm1.75 2.5a.75.75 0 0 0 0 1.5h3.5a.75.75 0 0 0 0-1.5h-3.5ZM4 11.75a.75.75 0 0 1 .75-.75h3.5a.75.75 0 0 1 0 1.5h-3.5a.75.75 0 0 1-.75-.75Z" | ||||||
| 									clip-rule="evenodd" | 									clip-rule="evenodd" | ||||||
| 								/> | 								/> | ||||||
| 							</svg> | 							</svg> | ||||||
| 						{/if} | 						{/if} | ||||||
| 					</button> | 					</button> | ||||||
| 				</div> | 				</div> | ||||||
|  | 			</div> | ||||||
|  | 			<div class="justify-between w-full "> | ||||||
|  | 				<div class="flex justify-between w-full"> | ||||||
|  | 					<div class="self-center text-xs font-medium ">{$i18n.t('API Key')}</div> | ||||||
|  | 				</div> | ||||||
| 
 | 
 | ||||||
| 				<button | 				<div class="flex mt-2"> | ||||||
| 					class="ml-1.5 px-1.5 py-1 hover:bg-gray-800 transition rounded-lg" | 					<div class="flex w-full"> | ||||||
| 					on:click={() => { | 						<input | ||||||
| 						copyToClipboard(localStorage.token); | 							class="w-full rounded-l-lg py-1.5 pl-4 text-sm dark:text-gray-300 dark:bg-gray-800 outline-none" | ||||||
| 						JWTTokenCopied = true; | 							type={showApiKey ? 'text' : 'password'} | ||||||
| 						setTimeout(() => { | 							value={localApiKey} | ||||||
| 							JWTTokenCopied = false; | 							disabled | ||||||
| 						}, 2000); | 						/> | ||||||
| 					}} | 
 | ||||||
| 				> | 						<button | ||||||
| 					{#if JWTTokenCopied} | 							class="ml-1.5 px-1.5 py-1 hover:bg-gray-800 transition rounded-lg" | ||||||
| 						<svg | 							on:click={() => {createApiKeyHandler()}} | ||||||
| 							xmlns="http://www.w3.org/2000/svg" |  | ||||||
| 							viewBox="0 0 20 20" |  | ||||||
| 							fill="currentColor" |  | ||||||
| 							class="w-4 h-4" |  | ||||||
| 						> | 						> | ||||||
| 							<path | 						<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16" fill="currentColor" class="w-4 h-4"><path d="M8.75 3.75a.75.75 0 0 0-1.5 0v3.5h-3.5a.75.75 0 0 0 0 1.5h3.5v3.5a.75.75 0 0 0 1.5 0v-3.5h3.5a.75.75 0 0 0 0-1.5h-3.5v-3.5Z"></path></svg> | ||||||
| 								fill-rule="evenodd" | 							 | ||||||
| 								d="M16.704 4.153a.75.75 0 01.143 1.052l-8 10.5a.75.75 0 01-1.127.075l-4.5-4.5a.75.75 0 011.06-1.06l3.894 3.893 7.48-9.817a.75.75 0 011.05-.143z" | 						</button> | ||||||
| 								clip-rule="evenodd" | 
 | ||||||
| 							/> | 						<button | ||||||
| 						</svg> | 							class="px-2 transition rounded-r-lg dark:bg-gray-800" | ||||||
| 					{:else} | 							on:click={() => { | ||||||
| 						<svg | 								showApiKey = !showApiKey; | ||||||
| 							xmlns="http://www.w3.org/2000/svg" | 							}} | ||||||
| 							viewBox="0 0 16 16" |  | ||||||
| 							fill="currentColor" |  | ||||||
| 							class="w-4 h-4" |  | ||||||
| 						> | 						> | ||||||
| 							<path | 							{#if showApiKey} | ||||||
| 								fill-rule="evenodd" | 								<svg | ||||||
| 								d="M11.986 3H12a2 2 0 0 1 2 2v6a2 2 0 0 1-1.5 1.937V7A2.5 2.5 0 0 0 10 4.5H4.063A2 2 0 0 1 6 3h.014A2.25 2.25 0 0 1 8.25 1h1.5a2.25 2.25 0 0 1 2.236 2ZM10.5 4v-.75a.75.75 0 0 0-.75-.75h-1.5a.75.75 0 0 0-.75.75V4h3Z" | 									xmlns="http://www.w3.org/2000/svg" | ||||||
| 								clip-rule="evenodd" | 									viewBox="0 0 16 16" | ||||||
| 							/> | 									fill="currentColor" | ||||||
| 							<path | 									class="w-4 h-4" | ||||||
| 								fill-rule="evenodd" | 								> | ||||||
| 								d="M3 6a1 1 0 0 0-1 1v7a1 1 0 0 0 1 1h7a1 1 0 0 0 1-1V7a1 1 0 0 0-1-1H3Zm1.75 2.5a.75.75 0 0 0 0 1.5h3.5a.75.75 0 0 0 0-1.5h-3.5ZM4 11.75a.75.75 0 0 1 .75-.75h3.5a.75.75 0 0 1 0 1.5h-3.5a.75.75 0 0 1-.75-.75Z" | 									<path | ||||||
| 								clip-rule="evenodd" | 										fill-rule="evenodd" | ||||||
| 							/> | 										d="M3.28 2.22a.75.75 0 0 0-1.06 1.06l10.5 10.5a.75.75 0 1 0 1.06-1.06l-1.322-1.323a7.012 7.012 0 0 0 2.16-3.11.87.87 0 0 0 0-.567A7.003 7.003 0 0 0 4.82 3.76l-1.54-1.54Zm3.196 3.195 1.135 1.136A1.502 1.502 0 0 1 9.45 8.389l1.136 1.135a3 3 0 0 0-4.109-4.109Z" | ||||||
| 						</svg> | 										clip-rule="evenodd" | ||||||
| 					{/if} | 									/> | ||||||
| 				</button> | 									<path | ||||||
|  | 										d="m7.812 10.994 1.816 1.816A7.003 7.003 0 0 1 1.38 8.28a.87.87 0 0 1 0-.566 6.985 6.985 0 0 1 1.113-2.039l2.513 2.513a3 3 0 0 0 2.806 2.806Z" | ||||||
|  | 									/> | ||||||
|  | 								</svg> | ||||||
|  | 							{:else} | ||||||
|  | 								<svg | ||||||
|  | 									xmlns="http://www.w3.org/2000/svg" | ||||||
|  | 									viewBox="0 0 16 16" | ||||||
|  | 									fill="currentColor" | ||||||
|  | 									class="w-4 h-4" | ||||||
|  | 								> | ||||||
|  | 									<path d="M8 9.5a1.5 1.5 0 1 0 0-3 1.5 1.5 0 0 0 0 3Z" /> | ||||||
|  | 									<path | ||||||
|  | 										fill-rule="evenodd" | ||||||
|  | 										d="M1.38 8.28a.87.87 0 0 1 0-.566 7.003 7.003 0 0 1 13.238.006.87.87 0 0 1 0 .566A7.003 7.003 0 0 1 1.379 8.28ZM11 8a3 3 0 1 1-6 0 3 3 0 0 1 6 0Z" | ||||||
|  | 										clip-rule="evenodd" | ||||||
|  | 									/> | ||||||
|  | 								</svg> | ||||||
|  | 							{/if} | ||||||
|  | 						</button> | ||||||
|  | 					</div> | ||||||
|  | 
 | ||||||
|  | 					<button | ||||||
|  | 						class="ml-1.5 px-1.5 py-1 hover:bg-gray-800 transition rounded-lg" | ||||||
|  | 						on:click={() => { | ||||||
|  | 							copyToClipboard(localApiKey); | ||||||
|  | 							ApiKeyCopied = true; | ||||||
|  | 							setTimeout(() => { | ||||||
|  | 								ApiKeyCopied = false; | ||||||
|  | 							}, 2000); | ||||||
|  | 						}} | ||||||
|  | 					> | ||||||
|  | 						{#if ApiKeyCopied} | ||||||
|  | 							<svg | ||||||
|  | 								xmlns="http://www.w3.org/2000/svg" | ||||||
|  | 								viewBox="0 0 20 20" | ||||||
|  | 								fill="currentColor" | ||||||
|  | 								class="w-4 h-4" | ||||||
|  | 							> | ||||||
|  | 								<path | ||||||
|  | 									fill-rule="evenodd" | ||||||
|  | 									d="M16.704 4.153a.75.75 0 01.143 1.052l-8 10.5a.75.75 0 01-1.127.075l-4.5-4.5a.75.75 0 011.06-1.06l3.894 3.893 7.48-9.817a.75.75 0 011.05-.143z" | ||||||
|  | 									clip-rule="evenodd" | ||||||
|  | 								/> | ||||||
|  | 							</svg> | ||||||
|  | 						{:else} | ||||||
|  | 							<svg | ||||||
|  | 								xmlns="http://www.w3.org/2000/svg" | ||||||
|  | 								viewBox="0 0 16 16" | ||||||
|  | 								fill="currentColor" | ||||||
|  | 								class="w-4 h-4" | ||||||
|  | 							> | ||||||
|  | 								<path | ||||||
|  | 									fill-rule="evenodd" | ||||||
|  | 									d="M11.986 3H12a2 2 0 0 1 2 2v6a2 2 0 0 1-1.5 1.937V7A2.5 2.5 0 0 0 10 4.5H4.063A2 2 0 0 1 6 3h.014A2.25 2.25 0 0 1 8.25 1h1.5a2.25 2.25 0 0 1 2.236 2ZM10.5 4v-.75a.75.75 0 0 0-.75-.75h-1.5a.75.75 0 0 0-.75.75V4h3Z" | ||||||
|  | 									clip-rule="evenodd" | ||||||
|  | 								/> | ||||||
|  | 								<path | ||||||
|  | 									fill-rule="evenodd" | ||||||
|  | 									d="M3 6a1 1 0 0 0-1 1v7a1 1 0 0 0 1 1h7a1 1 0 0 0 1-1V7a1 1 0 0 0-1-1H3Zm1.75 2.5a.75.75 0 0 0 0 1.5h3.5a.75.75 0 0 0 0-1.5h-3.5ZM4 11.75a.75.75 0 0 1 .75-.75h3.5a.75.75 0 0 1 0 1.5h-3.5a.75.75 0 0 1-.75-.75Z" | ||||||
|  | 									clip-rule="evenodd" | ||||||
|  | 								/> | ||||||
|  | 							</svg> | ||||||
|  | 						{/if} | ||||||
|  | 					</button> | ||||||
|  | 				</div> | ||||||
| 			</div> | 			</div> | ||||||
| 		</div> | 		</div> | ||||||
| 	</div> | 	</div> | ||||||
|  |  | ||||||
|  | @ -1,6 +1,6 @@ | ||||||
| <script> | <script> | ||||||
| 	import { goto } from '$app/navigation'; | 	import { goto } from '$app/navigation'; | ||||||
| 	import { userSignIn, userSignUp } from '$lib/apis/auths'; | 	import { userSignIn, userSignUp, getApiKey } from '$lib/apis/auths'; | ||||||
| 	import { WEBUI_API_BASE_URL, WEBUI_BASE_URL } from '$lib/constants'; | 	import { WEBUI_API_BASE_URL, WEBUI_BASE_URL } from '$lib/constants'; | ||||||
| 	import { WEBUI_NAME, config, user } from '$lib/stores'; | 	import { WEBUI_NAME, config, user } from '$lib/stores'; | ||||||
| 	import { onMount, getContext } from 'svelte'; | 	import { onMount, getContext } from 'svelte'; | ||||||
|  | @ -20,11 +20,23 @@ | ||||||
| 			console.log(sessionUser); | 			console.log(sessionUser); | ||||||
| 			toast.success($i18n.t(`You're now logged in.`)); | 			toast.success($i18n.t(`You're now logged in.`)); | ||||||
| 			localStorage.token = sessionUser.token; | 			localStorage.token = sessionUser.token; | ||||||
|  | 			await setApiKey(sessionUser.token); | ||||||
| 			await user.set(sessionUser); | 			await user.set(sessionUser); | ||||||
| 			goto('/'); | 			goto('/'); | ||||||
| 		} | 		} | ||||||
| 	}; | 	}; | ||||||
| 
 | 
 | ||||||
|  | 	const setApiKey = async (token) => { | ||||||
|  | 		const apiKey = await getApiKey(token).catch((error) => { | ||||||
|  | 			toast.error(error); | ||||||
|  | 			return null; | ||||||
|  | 		}); | ||||||
|  | 
 | ||||||
|  | 		if (apiKey) { | ||||||
|  | 			localStorage.apiKey = apiKey['api-key']; | ||||||
|  | 		} | ||||||
|  | 	}; | ||||||
|  | 
 | ||||||
| 	const signInHandler = async () => { | 	const signInHandler = async () => { | ||||||
| 		const sessionUser = await userSignIn(email, password).catch((error) => { | 		const sessionUser = await userSignIn(email, password).catch((error) => { | ||||||
| 			toast.error(error); | 			toast.error(error); | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 liu.vaayne
						liu.vaayne