import fs from 'fs'; import path from 'path'; import { bundleMDX } from 'mdx-bundler'; import remarkGfm from 'remark-gfm'; import rehypeSlug from 'rehype-slug'; export interface Frontmatter { title: string; date: string; excerpt?: string; teaser?: string; tags?: string[]; icon?: string; image?: string; video?: string; } export interface Post { slug: string; frontmatter: Frontmatter; code: string; } const contentDirectory = path.join(process.cwd(), 'content'); const datePrefixRegex = /^\d{4}-\d{2}-\d{2}-/; export function getPostSlugs(type: 'projects' | 'research' | 'teaching' | 'experience') { const typeDirectory = path.join(contentDirectory, type); if (!fs.existsSync(typeDirectory)) return []; return fs.readdirSync(typeDirectory).map(file => file.replace(datePrefixRegex, '').replace(/\.mdx$/, '') ); } export async function getPostBySlug(type: 'projects' | 'research' | 'teaching' | 'experience', slug: string): Promise { const typeDirectory = path.join(contentDirectory, type); const allFiles = fs.readdirSync(typeDirectory); const fileName = allFiles.find(file => file.replace(datePrefixRegex, '').replace(/\.mdx$/, '') === slug ); if (!fileName) { console.error(`[MDX] Could not find a file for slug: ${slug} in ${typeDirectory}`); return null; } const fullPath = path.join(typeDirectory, fileName); const fileContents = fs.readFileSync(fullPath, 'utf8'); const dateMatch = fileName.match(/^\d{4}-\d{2}-\d{2}/); const dateFromFilename = dateMatch ? dateMatch[0] : new Date().toISOString(); const { code, frontmatter } = await bundleMDX({ source: fileContents, mdxOptions(options) { options.remarkPlugins = [...(options.remarkPlugins ?? []), remarkGfm]; options.rehypePlugins = [...(options.rehypePlugins ?? []), rehypeSlug]; return options; }, }); return { slug, frontmatter: { ...frontmatter, date: dateFromFilename } as Frontmatter, code, }; }