Logo文档

博客系统

学习如何在 NEXTDEVKIT 中使用 Fumadocs MDX 创建和管理博客内容

对于博客功能,我们使用 Fumadocs MDX 库。

Fumadocs MDX 是一个允许您用 Markdown 创建博客文章并使用 MDX 组件为博客文章添加丰富内容的库。

🏗️ 博客系统架构

NEXTDEVKIT 的博客系统构建结构如下:

src/
├── content/
│   └── blog/
│       ├── writing-a-new-blog-post-here.md
│       ├── writing-a-new-blog-post-here.zh.md
│       ├── md-test.md
│       └── md-test.zh.md
├── app/
│   └── [locale]/
│       └── (marketing)/
│           └── blog/
│               ├── page.tsx          # 博客列表页面
│               ├── layout.tsx        # 博客布局
│               └── [...slug]/
│                   └── page.tsx      # 单独的博客文章
├── components/
│   └── blog/
│       ├── mdx-components.tsx        # 自定义 MDX 组件
│       ├── toc.tsx                   # 目录
│       └── go-to-top.tsx             # 返回顶部按钮
├── config/
│   └── marketing/
│       └── blog.ts                   # 博客配置
└── source.config.ts                 # 博客集合架构

📝 编写博客文章

要创建新的博客文章,您需要在 src/content/blog/ 目录中创建一个新的 Markdown 文件。

文件名应该是博客文章的 slug。

如果您希望 URL 为 https://your-app.com/blog/my-first-post,那么文件名应该是 my-first-post.mdx

文件应该包含以下前置内容:

---
title: "我的第一篇博客文章"
description: "这是我第一篇博客文章的描述"
createdAt: 2024-01-15T10:00:00Z
updatedAt: 2024-01-15T10:00:00Z
author: "John Doe"
image: "/blog/my-first-post.jpg"
tags: ["教程", "入门指南"]
keywords: "nextdevkit, saas, 教程, 入门指南"

博客文章架构

每篇博客文章必须包含这些前置内容字段:

字段类型必需描述
titlestring博客文章标题
descriptionstringSEO 简要描述
keywordsstringSEO 关键词(逗号分隔)
createdAtdate发布日期
updatedAtdate最后更新日期
tagsstring[]分类标签
authorstring作者姓名
imagestring封面图片 URL

titledescriptionkeywords 也用于 SEO。

在前置内容块之后,您可以用 MDX 编写博客文章的内容。

⚙️ 博客配置

源配置

博客系统在 source.config.ts 中配置:

src/source.config.ts
import { defineCollections } from "fumadocs-mdx/config";
import { z } from "zod";

export const blogs = defineCollections({
  type: "doc",
  dir: "src/content/blog",
  schema: (ctx) => {
    return z.object({
      title: z.string(),
      description: z.string(),
      // ... 其他字段
    });
  },
});

博客配置

博客设置在 src/config/marketing/blog.ts 中定义:

src/config/marketing/blog.ts
export interface BlogConfig {
  title: string;
  description: string;
  placeholderImage: string;
}

export async function getBlogConfig(): Promise<BlogConfig> {
  const t = await getTranslations("blog");

  return {
    title: t("title"),
    description: t("description"),
    placeholderImage: "/marketing/feature-techstacks.png",
  };
}

🌐 多语言支持

NEXTDEVKIT 博客系统使用文件命名约定支持多种语言:

文件命名约定

  • 默认语言(英语)filename.md
  • 其他语言filename.{locale}.md

示例:多语言博客文章

英文版本getting-started.md

---
title: "Getting Started with NEXTDEVKIT"
description: "Learn how to build modern SaaS applications"
createdAt: 2024-01-15T10:00:00Z
updatedAt: 2024-01-15T10:00:00Z
tags: ["tutorial", "getting-started"]
author: "NEXTDEVKIT Team"
---

# Getting Started with NEXTDEVKIT

Welcome to NEXTDEVKIT! This guide will help you build modern SaaS applications.

## What is NEXTDEVKIT?

NEXTDEVKIT is a complete toolkit for building SaaS applications...

中文版本getting-started.zh.md

---
title: "NEXTDEVKIT 快速入门"
description: "学习如何使用 NEXTDEVKIT 构建现代 SaaS 应用"
createdAt: 2024-01-15T10:00:00Z
updatedAt: 2024-01-15T10:00:00Z
tags: ["教程", "快速入门"]
author: "NEXTDEVKIT 团队"
---

# NEXTDEVKIT 快速入门

欢迎使用 NEXTDEVKIT!本指南将帮助您构建现代 SaaS 应用程序。

## 什么是 NEXTDEVKIT?

NEXTDEVKIT 是一个完整的 SaaS 应用程序构建工具包...

🎨 丰富内容组件

自定义 MDX 组件

NEXTDEVKIT 在 src/components/blog/mdx-components.tsx 中提供自定义 MDX 组件:

const components = {
  // 具有自定义样式的增强标题
  h1: ({ className, ...props }) => (
    <h1 className={cn("font-heading my-8 text-2xl md:text-[1.8rem]", className)} {...props} />
  ),
  // ... 其他组件
};

📑 目录

自动生成目录

NEXTDEVKIT 自动从您的博客文章标题生成目录:

src/components/blog/toc.tsx
export function DashboardTableOfContents({ items }: TocProps) {
  const itemIds = React.useMemo(
    () => items
      .map((item) => item.url)
      .filter(Boolean)
      .map((id) => id?.split("#")[1]),
    [items]
  );
  
  const activeHeading = useActiveItem(itemIds);
  
  return (
    <div className="space-y-2">
      <Tree items={items} activeItem={activeHeading} />
    </div>
  );
}

目录功能

  • 自动生成 从标题结构
  • 活跃标题 高亮显示
  • 平滑滚动 到章节
  • 响应式设计 适用于移动端/桌面端
  • 交集观察器 用于活跃状态

🔧 自定义

添加自定义组件

创建自定义 MDX 组件:

src/components/blog/custom-components.tsx
export function VideoEmbed({ url, title }) {
  return (
    <div className="my-8">
      <iframe
        src={url}
        title={title}
        className="w-full aspect-video rounded-lg"
        allowFullScreen
      />
    </div>
  );
}

export function Newsletter() {
  return (
    <div className="my-8 p-6 bg-blue-50 rounded-lg">
      <h3 className="text-lg font-semibold mb-2">订阅我们的时事通讯</h3>
      <p className="text-gray-600 mb-4">获取最新的 NEXTDEVKIT 更新和技巧。</p>
      <div className="flex gap-2">
        <input
          type="email"
          placeholder="输入您的邮箱"
          className="flex-1 px-3 py-2 border rounded-md"
        />
        <button className="px-4 py-2 bg-blue-600 text-white rounded-md hover:bg-blue-700">
          订阅
        </button>
      </div>
    </div>
  );
}

添加到 MDX 组件:

src/components/blog/mdx-components.tsx
import { VideoEmbed, Newsletter } from './custom-components';

const components = {
  ...defaultMdxComponents,
  VideoEmbed,
  Newsletter,
  // ... 其他组件
};

🔧 故障排除

常见问题

文章未显示

  • 检查前置内容语法
  • 验证文件扩展名(.md.mdx
  • 确保正确的日期格式
  • 检查语言配置

MDX 组件错误

  • 验证组件导入
  • 检查 markdown 中的 JSX 语法
  • 确保组件正确导出

样式问题

  • 检查 CSS 类名
  • 验证 Tailwind 配置
  • 查看 MDX 组件样式

构建错误

  • 验证前置内容架构
  • 检查缺失的必需字段
  • 验证图片路径存在

🔗 相关资源


🎯 下一步

现在您了解了博客系统,请探索这些相关功能: