从零开始搭建个人博客

2026 年 6 月 9 日

3046 字

15 分钟

未分类

一直想抽空搭一个完全属于自己的个人博客。
前阵子在逛 Astro 官网的主题市场时,一眼就相中了 Momo 这款主题。
它最吸引我的地方就是那股纯白、利落的极简风
没有任何花里胡哨的组件,能让人把心思完全放在文字本身。
此外,Astro 标志性的“孤岛架构”让生成的静态页面几乎没有冗余代码,加载速度快得惊人。

我把这次建站的完整流程记录下来,既作为日后重新配置的参考,也希望能帮到想搭建同款博客的朋友。

第一步:环境准备

安装 Node.js

Node.js® 是一个免费、开源、跨平台的 JavaScript 运行时环境。
Astro 基于 Node.js 开发,因此你需要先安装 Node.js 运行环境。

如果你尚未安装 Node.js:

请访问 https://nodejs.org/ 下载并安装 Node.js 运行环境。
网上有许多详细的 Node.js 安装教程,你可以搜索“Node.js 安装教程”找到适合的指南。

验证安装

安装完成后,打开你的终端,输入以下命令验证安装是否正确:

第一个命令:

node -v

第二个命令:

npm -v

如果看到类似这样的版本号输出,说明安装成功:

v25.6.0  # Node.js 版本
11.9.0     # npm 版本

如果这些命令提示“未找到命令”或显示错误信息,
请重新检查 Node.js 的安装步骤,确保已将 Node.js 添加到系统环境变量中。

关于包管理器(推荐pnpm)

相比npm,为何推荐使用pnpm?它在以下两个方面优势显著:

  1. 极致的安装速度 pnpm采用独特的硬链接机制管理依赖,避免了npm复制文件的操作,
    通常能将依赖安装时间缩短数倍。

  2. 高效的磁盘利用 在pnpm的全局存储模式下,同一个版本的依赖包在磁盘上只会保存一次。
    你创建的所有项目都可以共享这些依赖,从而节省大量磁盘空间。

安装 pnpm 非常简单,只需在终端中执行以下命令即可:

npm install -g pnpm@latest-10

安装完毕后,可通过以下命令来验证是否安装成功:

pnpm -v

如果终端显示出 pnpm 的版本号(例如 10.29.3),就说明 pnpm 已准备就绪。

安装 Git

获取 Momo 主题最推荐的方式是通过 Git,这样方便后续直接拉取源码并同步主题的日常更新。
当然,你也可以直接在 GitHub 仓库页面点击 “Download ZIP” 下载压缩包。

如果选择使用 Git,前往 Git 官网下载安装完成后,可在终端执行以下命令进行验证:

git --version

如果终端正确输出了类似 git version 2.xx.x 的字样,说明 Git 已成功安装。

安装 VS Code

推荐使用 Visual Studio Code 作为编辑器,用来修改配置和撰写文章会更加顺手。

安装完成后,进入博客项目文件夹,右键 →「通过 Code 打开」 即可开始编辑。

第二步:初始化博客

Momo 是一个「开箱即用」的 Astro 博客主题,
不需要复杂的配置和主题合并,克隆下来就能跑。

1. 获取源码

你可以创建一个 Blog 的项目文件夹然后执行:

git clone https://github.com/Motues/Momo.git

2. 安装依赖

克隆完成后双击进入 Momo 文件夹执行:

pnpm install

这一步会自动安装 Astro、Tailwind、Pagefind 等所有依赖。

3. 本地启动

在终端中执行以下命令,启动 Astro 的本地开发服务器:

pnpm dev

启动成功后,终端会输出一个本地访问地址。
打开浏览器访问:

http://localhost:4321/

如果一切顺利,这时候一个博客在本地就算是初始化完成了。

WARNING

重要的事情说三遍!!!
后续所有步骤均需在 Blog\Momo 项目根目录下执行。
重要的事情说三遍!!!
后续所有步骤均需在 Blog\Momo 项目根目录下执行。
重要的事情说三遍!!!
后续所有步骤均需在 Blog\Momo 项目根目录下执行。

第三步:个性化修改

在这个主题原版的基础上,我做了一些个性化修改。
如果你也喜欢同样的风格,可以跟着下面的步骤一起调整,将博客打造得和我完全一致。

1. 安装插件

为了让博客具备完善的 SEO(搜索引擎优化)和极致的加载速度,需要先补充两个底层插件:

  • @astrojs/sitemap:自动生成网站地图,方便搜索引擎抓取你博客的全部文章。
  • @zokki/astro-minify:自动压缩 HTML、CSS 和 JS 代码,进一步压榨页面体积,让加载速度更快。

在终端里先执行 Ctrl + C 停掉刚才的本地服务,然后运行以下命令安装它们:

pnpm add @astrojs/sitemap
pnpm add @zokki/astro-minify

2. 修改配置文件:astro.config.mjs

找到并打开 astro.config.mjs 文件。

为了让刚安装的两个插件生效,需要把它们配置到文件里。

在开头添加 import 导入插件

import sitemap from "@astrojs/sitemap";
import { minify } from '@zokki/astro-minify';

修改 site 为你的域名,
并在 integrations 里找到 svelte() 在后面添加 sitemap(), minify() 调用函数

export default defineConfig({
  site: 'https://example.com', // Root URL of site
  i18n: {
    locales: ['zh-cn', 'en'],
    defaultLocale: 'zh-cn',
    routing: {
      prefixDefaultLocale: false,
      redirectToDefaultLocale: false
    }
  },
  integrations: [icon({
    include: {
      "fa6-brands": ["*"],
      "fa6-solid": ["*"],
      "simple-icons": ["*"],
      "vscode-icons": ["*"],
      "material-symbols": ["*"],
      "flue": ["*"],
    }
  }), svelte(),sitemap(), minify()],

3. 修改配置文件:src/config.ts

修改 title 然后把 comments 的 enable 改为 false

export const siteConfig: SiteConfig = {
    title: "example",
    subTitle: "Blog",

    favicon: "/favicon/favicon.ico", // Path of the favicon, relative to the /public directory

    pageSize: 6, // Number of posts per page
    toc: {
        enable: true,
        depth: 3 // Max depth of the table of contents, between 1 and 4
    },
    blogNavi: {
        enable: true // Whether to enable blog navigation in the blog footer
    },
    comments: {
        enable: false, // Whether to enable comments
        platform: "default", // Comment platform, set "default" to use Momo-backend, also supports "twikoo"
        backendUrl: "https://api.example.com" // Backend URL for comments
    },
    theme: {
        AOS: true, // Whether to enable AOS (Animate On Scroll) for animations
        LQIP: true, // Whether to enable LQIP (Low-Quality Image Placeholder) for image placeholders
        PhotoSwipe: true // Whether to enable PhotoSwipe for image viewer
    }
}

这里只改 indexPage 和 startYear 就行

export const profileConfig: ProfileConfig = {
    avatar: "assets/avatar.png", // Relative to the /src directory. Relative to the /public directory if it starts with '/'
    name: "example",
    description: "example",
    indexPage: "https://github.com/example",
    startYear: 2025,
}

4. 修改配置文件:src\components\Footer.astro

所有 target 修改为 _blank 防止从某些页面返回时加载动画无限循环

<!-- footer -->
<footer class="flex flex-col md:flex-row md:justify-between items-start md:items-center py-10 text-[var(--text-color-70)] max-w-[var(--header-width)] mx-auto w-full">
    <div class="mb-1 md:mb-0">
        © {profileConfig.startYear} - {new Date().getFullYear()} <a class="link-line" target="_blank" href={introPage}>{profileConfig.name}</a>. 
    </div>
    <div class="right">
        <p>Powered by 
        <a target="_blank" href="https://astro.build" title="Astro" class="tooltip-wrapper"><Icon name="simple-icons:astro" class="inline-block" /></a> 
        <a target="_blank" href="https://svelte.dev/" title="Svelte" class="tooltip-wrapper"><Icon name="simple-icons:svelte" class="inline-block"/></a> 
        <a target="_blank" href="https://tailwindcss.com/" title="tailwindcss" class="tooltip-wrapper"><Icon name="simple-icons:tailwindcss" class="inline-block"/></a> 
        <a target="_blank" href="https://github.com/Motues/Momo" title="Momo" class="tooltip-wrapper"><Icon name="simple-icons:github" class="inline-block"/></a> 
         | 
        <a href="/rss.xml" target="_blank" title="RSS" class="tooltip-wrapper"><Icon name="simple-icons:rss" class="inline-block" /></a>
        </p>
    </div>
</footer>

5. 修改配置文件:src\components\Header.astro

隐藏 Dark Mode

        <!-- Dark Mode 
        <ThemeIcon class="flex items-center justify-center w-10 h-10 hover:bg-[var(--button-hover-color)] rounded-lg hover:text-current active:scale-90 border border-[var(--button-border-color)] transition-all duration-300"/>
        -->

if 开头添加 window.innerWidth < 776 && 隐藏顶部导航栏跟随

  let isFixed = false;
  window.addEventListener('scroll', () => {
    if (window.innerWidth < 776 && window.scrollY > 0 && !isFixed && navBar && navBarList) {
      navBar.classList.add('fixed');
      navBar.classList.remove('border-[var(--bg-color)]');
      navBarList.classList.add(
        'border-[var(--button-border-color)]',
        'shadow-[0_4px_12px_var(--shadow-color)]'
      );
      isFixed = true;
    } else if (window.scrollY === 0 && isFixed && navBar && navBarList) {
      navBar.classList.remove('fixed');
      navBar.classList.add('border-[var(--bg-color)]');
      navBarList.classList.remove(
        'border-[var(--button-border-color)]',
        'shadow-[0_4px_12px_var(--shadow-color)]'
      );
      isFixed = false;
    }
  });
}

6. 修改配置文件:src\i18n\language\en.ts

找到 cover 修改 title subTitle

cover: {
        title: {
            home: "Welcome to My Blog!",
            archive: "Archive",
            about: "About",
            friends: "Friends",
        },
        subTitle: {
            home: "example",
            archive: "Total of {count} articles",
            about: "",
            friends: "",
        }
    },

找到 page404 修改 title subTitle errorCode

    page404: {
        title: "404",
        subTitle: "page not found or removed",
        backToHome: "Home",
        backToPreview: "Previous Page",
        errorCode: "404",
        notice: "Perhaps you can try:"
    },

7. 修改配置文件:src\i18n\language\zh-cn.ts

找到 cover 修改 title subTitle

    cover: {
        title: {
            home: "欢迎来到我的博客!",
            archive: "文章归档",
            about: "关于",
            friends: "友链",
        },
        subTitle: {
            home: "example",
            archive: "共 {count} 篇文章",
            about: "",
            friends: "",
        }
    },

找到 page404 修改 title subTitle errorCode

page404: {
        title: "404",
        subTitle: "页面不存在或已被移除",
        backToHome: "返回首页",
        backToPreview: "返回上一页",
        errorCode: "404",
        notice: "或许你可以尝试:"
    },

8. 修改配置文件:src\pages\404.astro

MainPageLayout 替换下面这一段代码

<MainPageLayout title={pageTitle} lang="zh-CN">
    <div class="mx-auto w-full max-w-[var(--page-width)] px-4 text-center">
        <div class="my-8">
            <h1 class="text-7xl md:text-8xl font-bold text-black dark:text-white mb-2">{t("page404.title")}</h1>
            <p class="text-xl md:text-2xl text-[var(--text-color-80)]">{t("page404.subTitle")}</p>
        </div>

        <div class="mt-8 flex flex-col items-center">
            <p class="text-[var(--text-color-70)]">{t("page404.notice")}</p>
            <div class="mt-4 flex gap-4">
                <a href={indexPage}
                class="px-6 py-2 border border-[var(--button-border-color)] rounded-lg text-[var(--text-color)] hover:bg-[var(--button-hover-color)] transition-all">
                    {t("page404.backToHome")}
                </a>
                <a href="javascript:history.back()"
                class="px-6 py-2 border border-[var(--button-border-color)] rounded-lg text-[var(--text-color)] hover:bg-[var(--button-hover-color)] transition-all">
                    {t("page404.backToPreview")}
                </a>
            </div>
        </div>
    </div>
</MainPageLayout>

在完成上述的所有个性化修改后,你就搭建好了属于你自己的博客。
接下来,就是学会如何预览最终打包效果,以及如何开始撰写你的第一篇文章。

第四步:写文章、构建与预览

1. 撰写新文章

Momo 主题内置了快捷命令,可以快速创建新文章。

创建命令:

pnpm newpost <文章路径> [语言]
  • <文章路径>:文章的文件夹名,同时也是 slugId
  • [语言]:可选,默认为 zh-cn,也可以指定 en

使用示例:

# 创建中文文章
pnpm newpost hello-world

# 创建英文文章
pnpm newpost hello-world en

执行后会自动生成对应的 Markdown 文件:

src/content/blog/hello-world/
└── zh-cn.md   # 或 en.md

生成的模板内容如下:

---
title: new post
pubDate: 2026-06-09
description: Some description here
category: ""
image: ""
draft: false
slugId: hello-world
---

## Title

Content goes here...

根据实际需求修改 titledescriptioncategory 等字段,然后在 ## Title 下方撰写正文即可。

2. 本地打包

文章写完后,在项目根目录下执行:

pnpm build

执行后,Astro 会在根目录生成 dist 文件夹,里面全是优化压缩后的纯静态文件。

3. 生产环境预览

pnpm preview

该命令会启动一个本地静态服务器,完美模拟线上真实环境。
打开浏览器访问:

http://localhost:4321/

在这里可以确认新文章是否正常显示,以及整体效果。
确认无误后,就可以进入下一步
发布到互联网。

第五步:线上部署与域名绑定

这里推荐使用 Cloudflare Pages,完全免费且自带全球 CDN 加速。
为了省去配置 Git 的麻烦,我们直接选择上传文件夹功能。

1. 部署步骤

  1. 准备文件:确保本地已执行 pnpm build,此时根目录下会生成一个 dist 文件夹。
  2. 创建项目:登录 Cloudflare 控制台,点击 「Workers 和 Pages」 -> 「创建」 -> 「Pages」
  3. 直接上传:点击 「直接上传」(Upload assets)标签页,输入项目名称。
  4. 选择文件夹:点击上传区域的 「文件夹」(folder)按钮,
    在弹出窗口中选中本地的 dist 文件夹,点击上传。
  5. 部署站点:等待网页加载完毕后,点击底部的 「部署站点」

等待上传完成,Cloudflare 就会生成一个免费的 *.pages.dev 网址,博客正式上线!

注意:以后每次写了新文章或修改了配置,都需要在本地重新执行 pnpm build
并将新生成的 dist 文件夹再次选择上传覆盖。

2. 绑定自定义域名

如果你有自己的域名,可以让博客看起来更专业:

  1. 进入刚刚创建的 Pages 项目后台,切换到 「自定义域」(Custom domains)标签页。
  2. 点击 「设置自定义域」,输入你的个人域名(如 blog.example.com)。
  3. 如果你的域名解析也托管在 Cloudflare,直接点击确认,系统会自动帮你添加 DNS 解析记录;
    如果是其他服务商,按照页面提示去修改 CNAME 记录即可。

绑定成功后,稍等几分钟,你就可以用自己的专属域名访问博客了。

总结

回看整个搭建过程,
从最初的环境配置到最终的线上部署,
核心其实只有三步:配好基础环境、按需微调配置、打包上传托管。

借助 Astro 的极致性能与 Momo 主题的极简设计,我们不仅在本地搭建起了一个纯粹的文字空间,
更通过 Cloudflare Pages 让它获得了免费、稳定且全球加速的线上家园。
这种“无数据库、无繁琐后台”的静态方案,完美契合了独立博客的初衷

让技术退居幕后,让文字重回焦点。

至此,博客搭建已正式完工。
在接下来的日子里,剩下的事情就是安安静静地把心思放在内容上。
不妨现在就静下心来,敲下键盘,去记录、去表达、去留住属于你的每一个瞬间。

祝你写作愉快!

从零开始搭建个人博客
https://05740682.de5.net/blog/setup-blog/
作者
05740682
发布时间
2026 年 6 月 9 日
许可协议
CC BY-NC-SA 4.0

输入关键词开始搜索