0
Fork 0
mirror of https://github.com/immich-app/immich.git synced 2024-12-31 00:43:56 -05:00

fix: reduce the number of API requests when changing route (#14666)

* fix: reduce the number of API requests when changing route

* fix: reset `userInteraction` after sign out
This commit is contained in:
martin 2024-12-16 15:45:01 +01:00 committed by GitHub
parent 6b0f9ec46c
commit 8945a5d862
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 63 additions and 20 deletions

View file

@ -1,7 +1,7 @@
<script lang="ts">
import FullScreenModal from '$lib/components/shared-components/full-screen-modal.svelte';
import { featureFlags } from '$lib/stores/server-config.store';
import { serverInfo } from '$lib/stores/server-info.store';
import { userInteraction } from '$lib/stores/user.svelte';
import { ByteUnit, convertToBytes } from '$lib/utils/byte-units';
import { handleError } from '$lib/utils/handle-error';
import { createUserAdmin } from '@immich/sdk';
@ -34,7 +34,9 @@
let isCreatingUser = $state(false);
let quotaSizeInBytes = $derived(quotaSize ? convertToBytes(quotaSize, ByteUnit.GiB) : null);
let quotaSizeWarning = $derived(quotaSizeInBytes && quotaSizeInBytes > $serverInfo.diskSizeRaw);
let quotaSizeWarning = $derived(
quotaSizeInBytes && userInteraction.serverInfo && quotaSizeInBytes > userInteraction.serverInfo.diskSizeRaw,
);
$effect(() => {
if (password !== confirmPassword && confirmPassword.length > 0) {

View file

@ -1,7 +1,7 @@
<script lang="ts">
import FullScreenModal from '$lib/components/shared-components/full-screen-modal.svelte';
import { AppRoute } from '$lib/constants';
import { serverInfo } from '$lib/stores/server-info.store';
import { userInteraction } from '$lib/stores/user.svelte';
import { handleError } from '$lib/utils/handle-error';
import { updateUserAdmin, type UserAdminResponseDto } from '@immich/sdk';
import { mdiAccountEditOutline } from '@mdi/js';
@ -37,7 +37,8 @@
let quotaSizeWarning = $derived(
previousQutoa !== convertToBytes(Number(quotaSize), ByteUnit.GiB) &&
!!quotaSize &&
convertToBytes(Number(quotaSize), ByteUnit.GiB) > $serverInfo.diskSizeRaw,
userInteraction.serverInfo &&
convertToBytes(Number(quotaSize), ByteUnit.GiB) > userInteraction.serverInfo.diskSizeRaw,
);
const editUser = async () => {

View file

@ -7,6 +7,7 @@
import Icon from '$lib/components/elements/icon.svelte';
import { featureFlags } from '$lib/stores/server-config.store';
import { user } from '$lib/stores/user.store';
import { userInteraction } from '$lib/stores/user.svelte';
import { handleLogout } from '$lib/utils/auth';
import { getAboutInfo, logout, type ServerAboutResponseDto } from '@immich/sdk';
import { mdiHelpCircleOutline, mdiMagnify, mdiTrayArrowUp } from '@mdi/js';
@ -38,17 +39,17 @@
await handleLogout(redirectUri);
};
let aboutInfo: ServerAboutResponseDto | undefined = $state();
let info: ServerAboutResponseDto | undefined = $state();
onMount(async () => {
aboutInfo = await getAboutInfo();
info = userInteraction.aboutInfo ?? (await getAboutInfo());
});
</script>
<svelte:window bind:innerWidth />
{#if shouldShowHelpPanel && aboutInfo}
<HelpAndFeedbackModal onClose={() => (shouldShowHelpPanel = false)} info={aboutInfo} />
{#if shouldShowHelpPanel && info}
<HelpAndFeedbackModal onClose={() => (shouldShowHelpPanel = false)} {info} />
{/if}
<section id="dashboard-navbar" class="fixed z-[900] h-[var(--navbar-height)] w-screen text-sm">

View file

@ -4,13 +4,19 @@
import { getAllAlbums, type AlbumResponseDto } from '@immich/sdk';
import { handleError } from '$lib/utils/handle-error';
import { t } from 'svelte-i18n';
import { userInteraction } from '$lib/stores/user.svelte';
let albums: AlbumResponseDto[] = $state([]);
onMount(async () => {
if (userInteraction.recentAlbums) {
albums = userInteraction.recentAlbums;
return;
}
try {
const allAlbums = await getAllAlbums({});
albums = allAlbums.sort((a, b) => (a.updatedAt > b.updatedAt ? -1 : 1)).slice(0, 3);
userInteraction.recentAlbums = albums;
} catch (error) {
handleError(error, $t('failed_to_load_assets'));
}

View file

@ -12,17 +12,24 @@
} from '@immich/sdk';
import Icon from '$lib/components/elements/icon.svelte';
import { mdiAlert } from '@mdi/js';
import { userInteraction } from '$lib/stores/user.svelte';
const { serverVersion, connected } = websocketStore;
let isOpen = $state(false);
let info: ServerAboutResponseDto | undefined = $state();
let versions: ServerVersionHistoryResponseDto[] = $state([]);
onMount(async () => {
if (userInteraction.aboutInfo && userInteraction.versions && $serverVersion) {
info = userInteraction.aboutInfo;
versions = userInteraction.versions;
return;
}
await requestServerInfo();
[info, versions] = await Promise.all([getAboutInfo(), getVersionHistory()]);
userInteraction.aboutInfo = info;
userInteraction.versions = versions;
});
let isMain = $derived(info?.sourceRef === 'main' && info.repository === 'immich-app/immich');
let version = $derived(

View file

@ -1,18 +1,18 @@
<script lang="ts">
import { locale } from '$lib/stores/preferences.store';
import { serverInfo } from '$lib/stores/server-info.store';
import { user } from '$lib/stores/user.store';
import { requestServerInfo } from '$lib/utils/auth';
import { onMount } from 'svelte';
import { t } from 'svelte-i18n';
import { getByteUnitString } from '../../../utils/byte-units';
import { getByteUnitString } from '$lib/utils/byte-units';
import LoadingSpinner from '../loading-spinner.svelte';
import { userInteraction } from '$lib/stores/user.svelte';
let usageClasses = $state('');
let hasQuota = $derived($user?.quotaSizeInBytes !== null);
let availableBytes = $derived((hasQuota ? $user?.quotaSizeInBytes : $serverInfo?.diskSizeRaw) || 0);
let usedBytes = $derived((hasQuota ? $user?.quotaUsageInBytes : $serverInfo?.diskUseRaw) || 0);
let availableBytes = $derived((hasQuota ? $user?.quotaSizeInBytes : userInteraction.serverInfo?.diskSizeRaw) || 0);
let usedBytes = $derived((hasQuota ? $user?.quotaUsageInBytes : userInteraction.serverInfo?.diskUseRaw) || 0);
let usedPercentage = $derived(Math.min(Math.round((usedBytes / availableBytes) * 100), 100));
const onUpdate = () => {
@ -38,6 +38,9 @@
});
onMount(async () => {
if (userInteraction.serverInfo && $user) {
return;
}
await requestServerInfo();
});
</script>
@ -54,7 +57,7 @@
<div class="hidden group-hover:sm:block md:block">
<p class="font-medium text-immich-dark-gray dark:text-white mb-2">{$t('storage')}</p>
{#if $serverInfo}
{#if userInteraction.serverInfo}
<p class="text-gray-500 dark:text-gray-300">
{$t('storage_usage', {
values: {

View file

@ -1,4 +0,0 @@
import type { ServerStorageResponseDto } from '@immich/sdk';
import { writable } from 'svelte/store';
export const serverInfo = writable<ServerStorageResponseDto>();

View file

@ -0,0 +1,26 @@
import type {
AlbumResponseDto,
ServerAboutResponseDto,
ServerStorageResponseDto,
ServerVersionHistoryResponseDto,
} from '@immich/sdk';
interface UserInteractions {
recentAlbums?: AlbumResponseDto[];
versions?: ServerVersionHistoryResponseDto[];
aboutInfo?: ServerAboutResponseDto;
serverInfo?: ServerStorageResponseDto;
}
const defaultUserInteraction: UserInteractions = {
recentAlbums: undefined,
versions: undefined,
aboutInfo: undefined,
serverInfo: undefined,
};
export const resetUserInteraction = () => {
Object.assign(userInteraction, defaultUserInteraction);
};
export const userInteraction = $state<UserInteractions>(defaultUserInteraction);

View file

@ -2,8 +2,8 @@ import { browser } from '$app/environment';
import { goto } from '$app/navigation';
import { foldersStore } from '$lib/stores/folders.svelte';
import { purchaseStore } from '$lib/stores/purchase.store';
import { serverInfo } from '$lib/stores/server-info.store';
import { preferences as preferences$, resetSavedUser, user as user$ } from '$lib/stores/user.store';
import { resetUserInteraction, userInteraction } from '$lib/stores/user.svelte';
import { getAboutInfo, getMyPreferences, getMyUser, getStorage } from '@immich/sdk';
import { redirect } from '@sveltejs/kit';
import { DateTime } from 'luxon';
@ -72,7 +72,7 @@ export const authenticate = async (options?: AuthOptions) => {
export const requestServerInfo = async () => {
if (get(user$)) {
const data = await getStorage();
serverInfo.set(data);
userInteraction.serverInfo = data;
}
};
@ -99,6 +99,7 @@ export const handleLogout = async (redirectUri: string) => {
}
} finally {
resetSavedUser();
resetUserInteraction();
foldersStore.clearCache();
}
};