67 lines
2.0 KiB
Plaintext
67 lines
2.0 KiB
Plaintext
---
|
|
import { type CollectionEntry, getCollection } from "astro:content";
|
|
import PageLayout from "@layouts/PageLayout.astro";
|
|
import Container from "@components/Container.astro";
|
|
import FormattedDate from "@components/FormattedDate.astro";
|
|
import { readingTime } from "@lib/utils";
|
|
import BackToPrev from "@components/BackToPrev.astro";
|
|
import Link from "@components/Link.astro";
|
|
|
|
export async function getStaticPaths() {
|
|
const projects = (await getCollection("projects"))
|
|
.filter(post => !post.data.draft)
|
|
.sort((a, b) => b.data.date.valueOf() - a.data.date.valueOf());
|
|
return projects.map((project) => ({
|
|
params: { slug: project.slug },
|
|
props: project,
|
|
}));
|
|
}
|
|
type Props = CollectionEntry<"projects">;
|
|
|
|
const project = Astro.props;
|
|
const { Content } = await project.render();
|
|
---
|
|
|
|
<PageLayout title={project.data.title} description={project.data.description}>
|
|
<Container>
|
|
<div class="animate">
|
|
<BackToPrev href="/projects">
|
|
Back to projects
|
|
</BackToPrev>
|
|
</div>
|
|
<div class="space-y-1 my-10">
|
|
<div class="animate flex items-center gap-1.5">
|
|
<div class="font-base text-sm">
|
|
<FormattedDate date={project.data.date} />
|
|
</div>
|
|
•
|
|
<div class="font-base text-sm">
|
|
{readingTime(project.body)}
|
|
</div>
|
|
</div>
|
|
<div class="animate text-2xl font-semibold text-black dark:text-white">
|
|
{project.data.title}
|
|
</div>
|
|
{(project.data.demoURL || project.data.repoURL) && (
|
|
<nav class="animate flex gap-1">
|
|
{project.data.demoURL && (
|
|
<Link href={project.data.demoURL} external>
|
|
live site
|
|
</Link>
|
|
)}
|
|
{project.data.demoURL && project.data.repoURL && (
|
|
<span>/</span>
|
|
)}
|
|
{project.data.repoURL && (
|
|
<Link href={project.data.repoURL} external>
|
|
repo
|
|
</Link>
|
|
)}
|
|
</nav>
|
|
)}
|
|
</div>
|
|
<article class="animate">
|
|
<Content />
|
|
</article>
|
|
</Container>
|
|
</PageLayout> |