Refactor: Switch Glance to use new JSON API

This commit is contained in:
Donatas Kirda 2024-05-17 16:28:22 +03:00
parent 72eb80c82c
commit 96a9f3971d
Signed by: bloodwiing
GPG Key ID: 63020D8D3F4A164F
4 changed files with 57 additions and 29 deletions

View File

@ -2,9 +2,10 @@
import { goto, replaceState } from '$app/navigation'; import { goto, replaceState } from '$app/navigation';
import { page } from '$app/stores'; import { page } from '$app/stores';
import { getNamedId } from '$lib/util'; import { getNamedId } from '$lib/util';
import { onMount } from 'svelte'; import { onMount, tick } from 'svelte';
import Post from '../post/post.svelte'; import Post from '../post/post.svelte';
import PostCard from './postcard.svelte'; import PostCard from './postcard.svelte';
import { parsePost } from '$lib/serialize/parse';
/** /**
* @type {number} * @type {number}
@ -29,7 +30,7 @@
/** /**
* @type {import('$types/base').Post | null} * @type {import('$types/base').Post | null}
*/ */
export let glancePost = null; let glancePost = null;
function getDefaultedUrl(/** @type {URL} */ url) { function getDefaultedUrl(/** @type {URL} */ url) {
const u = new URL(url); const u = new URL(url);
@ -38,40 +39,44 @@
return u; return u;
} }
const newUrl = getDefaultedUrl($page.url) /**
* @type {URL | undefined}
*/
let newUrl = undefined;
onMount(() => { onMount(async () => {
await tick();
newUrl = getDefaultedUrl($page.url);
replaceState(newUrl, {}); replaceState(newUrl, {});
}); });
/** @type {boolean[]} */ /** @type {boolean[]} */
$: hidden = Array(posts.length).fill(false); $: hidden = Array(posts.length).fill(false);
function previewPost(/** @type {CustomEvent<>} */ e) { async function previewPost(/** @type {CustomEvent<>} */ e) {
if (!newUrl) return;
/** @type {import("$types/base").Post} */ /** @type {import("$types/base").Post} */
const post = e.detail.post; glancePost = e.detail.post;
posts.forEach((p, index) => { posts.forEach((p, index) => {
hidden[index] = p == post; hidden[index] = p == glancePost;
}); });
newUrl.searchParams.set('glance', String(post.id)); const request = await fetch(`/api/post?id=${e.detail.post.id}&metrics=true`);
goto(newUrl, { const response = await request.json();
replaceState: true, glancePost = parsePost(response['post']);
noScroll: true console.log(glancePost);
});
} }
function dismiss(/** @type {MouseEvent | TouchEvent} */ e) { function dismiss(/** @type {MouseEvent | TouchEvent} */ e) {
if (!newUrl) return;
glancePost = null;
e.stopPropagation(); e.stopPropagation();
hidden = Array(posts.length).fill(false); hidden = Array(posts.length).fill(false);
newUrl.searchParams.delete('glance');
goto(newUrl, {
replaceState: true,
noScroll: true
});
} }
function expand(/** @type {MouseEvent | TouchEvent} */ e) { function expand(/** @type {MouseEvent | TouchEvent} */ e) {
@ -144,9 +149,9 @@
</div> </div>
<button class="postPreview" data-visible={glancePost != null || null} on:click={dismiss}> <button class="postPreview" data-visible={glancePost != null || null} on:click={dismiss}>
{#if glancePost}
<button class="preview" on:click={expand}> <button class="preview" on:click={expand}>
{#if glancePost} <Post post={glancePost} showMetrics={true}></Post>
<Post post={glancePost} commentTree={null} showMetrics={true}></Post>
{/if}
</button> </button>
{/if}
</button> </button>

View File

@ -16,13 +16,8 @@ export async function load({ url }) {
offset: pageSize * page, offset: pageSize * page,
}); });
const glance = parseIntNull(url.searchParams.get('glance'));
const glancePost = glance ? await getPost(glance, { withMetrics: true }) : null;
return { return {
posts: result, posts: result,
glancePost: glancePost,
itemsCount: pageSize, itemsCount: pageSize,
pageIndex: page, pageIndex: page,
totalResultCount: count, totalResultCount: count,

View File

@ -1,12 +1,11 @@
<script> <script>
import { page } from "$app/stores"; import { page } from "$app/stores";
import Card from "$comp/card.svelte"; import Card from "$comp/card.svelte";
import Postlist from "$comp/page/posts/postlist.svelte"; import Postlist from "$comp/page/posts/postlist.svelte";
/** /**
* @type {{ * @type {{
* posts: import("$types/base").Post[], * posts: import("$types/base").Post[],
* glancePost: import("$types/base").Post | null,
* itemsCount: number, * itemsCount: number,
* pageIndex: number, * pageIndex: number,
* totalResultCount: number, * totalResultCount: number,
@ -33,5 +32,5 @@
<img class="icon" src="waving-hand-sign.png" alt="wave"> <img class="icon" src="waving-hand-sign.png" alt="wave">
<span>Welcome to ECHO</span> <span>Welcome to ECHO</span>
</Card> </Card>
<Postlist posts={data.posts} glancePost={data.glancePost} itemsCount={data.itemsCount} pageIndex={data.pageIndex} totalResultCount={data.totalResultCount}></Postlist> <Postlist posts={data.posts} itemsCount={data.itemsCount} pageIndex={data.pageIndex} totalResultCount={data.totalResultCount}></Postlist>
</main> </main>

View File

@ -0,0 +1,29 @@
import { jsonSerialize } from "$lib/serialize/base";
import { getCommentsForPost } from "$lib/server/db/comment";
import { getPost } from "$lib/server/db/post";
import { getIdFromName, parseIntNull } from "$lib/util";
import { error } from "@sveltejs/kit";
/** @type {import("@sveltejs/kit").Action} */
export async function GET({ url }) {
const post_id = parseIntNull(url.searchParams.get('id'));
if (post_id === null) {
error(404, `No Post of ID ${url.searchParams.get('id')}`);
}
const getComments = !!url.searchParams.get('comments');
const showMetrics = !!url.searchParams.get('metrics');
const post = await getPost(post_id, {
withMetrics: showMetrics,
});
const comments = getComments ? await getCommentsForPost(post_id) : null;
return new Response(jsonSerialize({
post: post,
comments: comments,
showMetrics: showMetrics,
}));
}