import React from "react"; // Database connection is now handled by the centralized db module import { renderToString } from "react-dom/server"; import { AppShell } from "./src/frontend/AppShell"; import { Home } from "./src/frontend/pages/home"; import { NotFound } from "./src/frontend/pages/not-found"; import demo from "./temp/appshell.html"; import { Post } from "./src/frontend/pages/post"; import { getPostWithTags } from "./src/db/index"; async function blogPosts(hmr: boolean) { const glob = new Bun.Glob("**/*.md"); const blogPosts: Record = {}; for await (const file of glob.scan("./content")) { const post = await import(`./content/${file}`, { with: { type: "html" } }); const route = `/${file.replace(/\.md$/, "")}`; if (hmr) { // Use Bun Importer plugin for hot reloading in the browser blogPosts[`/hmr${route}`] = post.default; } else { // Use the Database for sending just the HTML or the HTML and AppShell blogPosts[route] = (req: Request) => { const path = new URL(req.url).pathname; const post = getPostWithTags(path); if (!post) return new Response(renderToString(), { status: 404, headers: { "Content-Type": "text/html" }, }); const data = { title: post.title, summary: post.summary, date: new Date(post.date), readingTime: post.reading_time, tags: post.tags || [], }; // AppShell is already loaded, just send the
content if (req.headers.get("shell-loaded") === "true") { return new Response( renderToString(), { headers: { "Content-Type": "text/html", }, }, ); } // AppShell is not loaded, send the with the
content inside return new Response( renderToString( , ), { headers: { "Content-Type": "text/html", }, }, ); }; } } Object.keys(blogPosts).map((route) => { console.info(route); }); return blogPosts; } Bun.serve({ development: { hmr: true, console: true, }, routes: { // standard mounting of blog posts ...(await blogPosts(false)), // hot module replacement in development mode ...(process.env.NODE_ENV === "development" ? (await blogPosts(true)) : []), // Home page "/": (req: Request) => { // Extract URL parameters from the request to pass to the component const url = new URL(req.url); const searchParams = Object.fromEntries(url.searchParams.entries()); if (req.headers.get("shell-loaded") === "true") { return new Response(renderToString(), { headers: { "Content-Type": "text/html", }, }); } return new Response( renderToString( , ), { headers: { "Content-Type": "text/html", }, }, ); }, "/target": demo, "/profile-picture.webp": () => { return new Response(Bun.file("./src/public/profile-picture.webp"), { headers: { "Content-Type": "image/webp", }, }); }, "/*": (req) => { if(req.headers.get("shell-loaded") === "true") { return new Response(renderToString(), { status: 404, headers: { "Content-Type": "text/html" }, }); } return new Response(renderToString(), { status: 404, headers: { "Content-Type": "text/html" }, }); } }, });