feat (server, web): Implement Archive (#2225)

* feat (server, web): add archive

* chore: generate api

* feat (web): add empty placeholder for archive page

* chore: remove title on favorites page

Duplicates sidebar selection. Two pages (Archive and Favorites)
are consistent now

* refactor (web): create EmptyPlaceholder component for empty pages

* fixed menu close button not close:

* fix (web): remove not necessary store call

* test (web): simplify asset tests code

* test (web): simplify asset tests code

* chore (server): remove isArchived while uploading

* chore (server): remove isArchived from typesense schema

* chore: generate api

* fix (web): delete asset from archive page

* chore: change archive asset count endpoint

old endpoint: /asset/archived-count-by-user-id
new endpoint: /asset/stat/archive

* chore: generate api

---------

Co-authored-by: Alex Tran <alex.tran1502@gmail.com>
This commit is contained in:
Sergey Kondrikov 2023-04-12 18:37:52 +03:00 committed by GitHub
parent eb9481b668
commit d314805caf
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
39 changed files with 861 additions and 97 deletions

View file

@ -0,0 +1,28 @@
<script lang="ts">
import empty1Url from '$lib/assets/empty-1.svg';
export let actionHandler: undefined | (() => Promise<void>) = undefined;
export let text = '';
export let alt = '';
let hoverClasses =
'hover:bg-immich-primary/5 dark:hover:bg-immich-dark-primary/25 hover:cursor-pointer';
</script>
{#if actionHandler}
<div
on:click={actionHandler}
on:keydown={actionHandler}
class="border dark:border-immich-dark-gray {hoverClasses} p-5 w-[50%] m-auto mt-10 bg-gray-50 dark:bg-immich-dark-gray rounded-3xl flex flex-col place-content-center place-items-center"
>
<img src={empty1Url} {alt} width="500" draggable="false" />
<p class="text-center text-immich-text-gray-500 dark:text-immich-dark-fg">{text}</p>
</div>
{:else}
<div
class="border dark:border-immich-dark-gray p-5 w-[50%] m-auto mt-10 bg-gray-50 dark:bg-immich-dark-gray rounded-3xl flex flex-col place-content-center place-items-center"
>
<img src={empty1Url} {alt} width="500" draggable="false" />
<p class="text-center text-immich-text-gray-500 dark:text-immich-dark-fg">{text}</p>
</div>
{/if}

View file

@ -4,6 +4,7 @@
import AccountMultipleOutline from 'svelte-material-icons/AccountMultipleOutline.svelte';
import ImageAlbum from 'svelte-material-icons/ImageAlbum.svelte';
import ImageOutline from 'svelte-material-icons/ImageOutline.svelte';
import ArchiveArrowDownOutline from 'svelte-material-icons/ArchiveArrowDownOutline.svelte';
import Magnify from 'svelte-material-icons/Magnify.svelte';
import StarOutline from 'svelte-material-icons/StarOutline.svelte';
import { AppRoute } from '../../../constants';
@ -13,16 +14,17 @@
import { locale } from '$lib/stores/preferences.store';
const getAssetCount = async () => {
const { data: assetCount } = await api.assetApi.getAssetCountByUserId();
const { data: allAssetCount } = await api.assetApi.getAssetCountByUserId();
const { data: archivedCount } = await api.assetApi.getArchivedAssetCountByUserId();
return {
videos: assetCount.videos,
photos: assetCount.photos
videos: allAssetCount.videos - archivedCount.videos,
photos: allAssetCount.photos - archivedCount.photos
};
};
const getFavoriteCount = async () => {
const { data: assets } = await api.assetApi.getAllAssets(true);
const { data: assets } = await api.assetApi.getAllAssets(true, undefined);
return {
favorites: assets.length
@ -37,6 +39,15 @@
owned: albumCount.owned
};
};
const getArchivedAssetsCount = async () => {
const { data: assetCount } = await api.assetApi.getArchivedAssetCountByUserId();
return {
videos: assetCount.videos,
photos: assetCount.photos
};
};
</script>
<section id="sidebar" class="flex flex-col gap-1 pt-8 pr-6 bg-immich-bg dark:bg-immich-dark-bg">
@ -130,6 +141,24 @@
</svelte:fragment>
</SideBarButton>
</a>
<a data-sveltekit-preload-data="hover" href={AppRoute.ARCHIVE} draggable="false">
<SideBarButton
title="Archive"
logo={ArchiveArrowDownOutline}
isSelected={$page.route.id === '/(user)/archive'}
>
<svelte:fragment slot="moreInformation">
{#await getArchivedAssetsCount()}
<LoadingSpinner />
{:then data}
<div>
<p>{data.videos.toLocaleString($locale)} Videos</p>
<p>{data.photos.toLocaleString($locale)} Photos</p>
</div>
{/await}
</svelte:fragment>
</SideBarButton>
</a>
<!-- Status Box -->
<div class="mb-6 mt-auto">