64 lines
1.8 KiB
Text
64 lines
1.8 KiB
Text
---
|
|
import icons from "@cdransf/astro-tabler-icons";
|
|
import { fetchAllPosts } from "@data/posts.js";
|
|
import Layout from "@layouts/Layout.astro";
|
|
import Paginator from "@components/nav/Paginator.astro";
|
|
import { md } from "@utils/helpers/general.js";
|
|
import { parseISO, format } from "date-fns";
|
|
|
|
export const prerender = true;
|
|
export const getStaticPaths = async ({ paginate }) => {
|
|
const posts = await fetchAllPosts();
|
|
const sortedPosts = posts.sort((a, b) => new Date(b.date) - new Date(a.date));
|
|
|
|
return paginate(sortedPosts, {
|
|
pageSize: 15,
|
|
});
|
|
};
|
|
|
|
const { IconStar } = icons;
|
|
const { page } = Astro.props;
|
|
const paginatedPosts = page.data;
|
|
const pagination = {
|
|
currentPage: page.currentPage,
|
|
totalPages: page.lastPage,
|
|
hasPrevious: page.currentPage > 1,
|
|
hasNext: page.currentPage < page.lastPage,
|
|
previousPage: page.url.prev || null,
|
|
nextPage: page.url.next || null,
|
|
pages: Array.from({ length: page.lastPage }, (_, i) => ({
|
|
number: i + 1,
|
|
href: i === 0 ? `/posts` : `/posts/${i + 1}`,
|
|
})),
|
|
};
|
|
const pageTitle =
|
|
pagination.currentPage === 1
|
|
? "Posts"
|
|
: `Posts / page ${pagination.currentPage}`;
|
|
const description =
|
|
"These are posts I've written. They're all added manually, after having been written and, I suppose, properly considered.";
|
|
---
|
|
|
|
<Layout
|
|
pageTitle={pageTitle}
|
|
description={description}
|
|
currentUrl={Astro.url.pathname}
|
|
>
|
|
{
|
|
paginatedPosts.map((post) => (
|
|
<article>
|
|
<div class="post-meta">
|
|
{post.featured && <div set:html={IconStar({ size: 16 })}/>}
|
|
<time datetime={post.date}>
|
|
{format(parseISO(post.date), "PPPP")}
|
|
</time>
|
|
</div>
|
|
<h3>
|
|
<a href={post.url}>{post.title}</a>
|
|
</h3>
|
|
<p set:html={md(post.description)} />
|
|
</article>
|
|
))
|
|
}
|
|
<Paginator pagination={pagination} />
|
|
</Layout>
|