
最近一段时间身边好几个朋友都在问建站的事有人想搭个人博客有人想给工作室做个官网还有人纠结于Shopify、WordPress、自建站到底有什么区别。我给他们的答案基本一致如果不想被平台抽成绑架、又想保留完整的自主权那就用开源CMS自己搭一个站。而在众多方案里我比较推荐的是Halo。Halo是一个基于Java开发的现代化开源CMS系统可以直接部署在自己的服务器上后台操作体验非常顺畅主题和插件生态也做得越来越成熟。这篇文章不打算跟你讲太多纸上谈兵的概念而是用一次真实的Halo建站全过程把环境准备、部署配置、主题美化、域名绑定到后续的SEO优化和常见坑位全部过一遍。无论你是刚接触源码建站的新手还是从WordPress迁移过来的老站长按着这条路线走基本能少走一大半弯路。1. 为什么选择Halo自建站先想清楚你要的是哪种站1.1 Shopify、WordPress和自建站到底差在哪很多人在选型的时候容易被建站这个词搞糊涂其实市面上主流方案就三个维度SaaS平台、传统开源CMS、纯手写或静态生成。Shopify这类SaaS平台本质上是租房子。你在人家的平台上开店服务器、安全补丁、支付通道都有人管但每个月要交订阅费交易还要抽成更重要的是你的数据和流量入口不完全在自己手里。适合不想碰技术、只想尽快卖货的商家。WordPress是开源CMS里占有率最高的方案PHP生态插件极其丰富虚拟主机几乎通吃。但也正因为它生态太庞大插件和主题的兼容性问题、安全补丁频率、后台的臃肿感都比较明显。WordPress本身不差只是对于追求轻量、快速、现代体验的人而言它的学习成本和时间成本其实是被低估的。自建站听起来最自由但如果是纯手写HTML或套用静态生成器内容发布和管理都得自己折腾。真要追求源码建站的掌控感又想要一个能后台写文章、管理评论、换主题的像样系统Halo这种现代开源CMS正好卡在中间。它具备独立服务器的完全自主权数据在自己的机器上功能靠插件按需扩展后台界面又很接近现在主流SaaS后台的交互水平。1.2 Halo解决的核心痛点我选Halo有几个很直接的考量。一是部署清爽。Halo不像WordPress需要搭配PHP、MySQL、Apache那一整套LAMP环境它本质上就是一个Java应用跑起来只要一个JDK或者一个Docker容器。这对服务器配置有限的个人站长来说非常友好很多1核1G的小机器也能稳定跑。二是内容管理的体验。Halo 2.x版本的后台是前后端分离的架构管理界面响应快发文章、传图片、配分类标签的流程非常顺手甚至可以直接对接Markdown编辑器。写技术博客的人应该都懂一个好用的写作体验直接决定了你愿不愿意持续更新。三是外观定制成本低。Halo主题市场里有很多高质量的免费主题安装是点一下的事改个站点标题、配色、导航菜单都不需要碰代码。就算你是个完全不懂前端的人也能在半小时内让站点看起来像回事。这对第一次接触建站的人来说正向反馈来得很快不容易劝退。四是插件生态覆盖了常见需求。评论系统、站点搜索、统计脚本、文章加密、图床管理、甚至对接微信公众号自动同步都能通过插件解决。它不是那种装一个插件就能变出全宇宙的大杂烩但该有的东西基本都有而且都是官方或社区认证过的安全风险比乱七八糟的来源低很多。2. 建站前的准备工作域名、服务器与部署思路2.1 先定域名再定服务器这是顺序问题经常有人一上来就买服务器折腾完才发现域名没有备案、访问不了或者域名解析了但不知道指向哪里。正常路径应该是反过来的先想清楚站点的定位和名字把域名定下来再按域名的合规要求去准备服务器。域名注册没什么好纠结的阿里云、腾讯云、Cloudflare哪里顺手在哪买。个人博客用 .com、.cn 或者 .me 都行如果主要面向国内用户记得提前确认是否需要ICP备案。这一点一定要在买服务器之前就查清楚否则建好的站放在国内机房但域名未备案HTTP访问会被拦截到时候再迁移服务器就非常折腾。2.2 服务器配置怎么选如果你是纯个人博客日访问量几百到几千这个级别Halo跑起来资源占用并没有想象中那么大。我自己的实践是1核2G的云服务器跑Halo加MySQL、Nginx日常内存占用稳定在60%左右完全够用。如果还想在上面跑一些脚本、监控工具建议直接上2核4G反正差价不大省得以后频繁迁移。操作系统方面Debian和Ubuntu都是稳妥的选择CentOS虽然也常见但官方维护周期已经过了不建议新项目再用。这篇文章里的命令我统一用Ubuntu 22.04演示Debian系基本通用。2.3 Docker和裸JAR部署怎么选Halo官方提供了两种主流部署方式Docker容器化部署和直接用JAR包启动。如果你是新手我的建议是无脑选Docker。原因很简单环境隔离依赖不会污染宿主机升级方便拉新镜像替换容器即可回滚容易出问题还能切回旧镜像。唯一需要注意的是Docker部署时要把数据目录挂载出来否则容器一删数据全没了。裸JAR方式适合已经有Java运维经验、不想在服务器上多装一层Docker的进阶用户。本质上就是下载一个jar包然后用java -jar halo.jar跑起来。这种方式对内存的占用更可控排查问题也直观一些但升级时要手动处理配置兼容操作门槛确实高一点。3. 从零到一完整搭建一个Halo站点3.1 服务器基础环境初始化拿到一台全新的Ubuntu服务器之后别急着装东西先把系统源和基础工具搞定。下面这几条命令我每次开新机器都会先跑一遍。sudo apt update sudo apt upgrade -y sudo apt install -y curl wget git vim ufw然后配置防火墙把SSH端口和后面要用的8090端口放出来。注意如果你后面准备用Nginx反向代理8090端口其实只需要对本机开放公网只保留80和443即可。sudo ufw allow OpenSSH sudo ufw allow 80/tcp sudo ufw allow 443/tcp sudo ufw enable这里有个非常容易踩的坑很多人装完Docker之后发现访问不了端口第一反应是防火墙没放行其实还要检查云服务商的安全组。阿里云、腾讯云的安全组默认不开放自定义端口光在系统里开放没用得去控制台把入方向规则加上。我早期排查过不少这类灵异事件最后都是安全组的锅。3.2 安装Docker与Docker Compose如果你走Docker路线先确认系统里有没有装过旧版Docker免得命令冲突。官方安装脚本是最省事的curl -fsSL https://get.docker.com | bash sudo systemctl enable --now docker装完验证一下sudo docker version如果输出了Client和Server两段信息说明Docker服务已经正常跑起来了。顺便装上Compose插件后面编排Halo加数据库的堆栈会用到sudo apt install -y docker-compose-plugin sudo docker compose version3.3 用Docker Compose编排Halo与MySQLHalo默认支持H2内嵌数据库零配置就能启动适合先跑起来看一眼效果。但你要是准备长期运营我不建议用H2数据文件虽然也在本地但备份恢复、故障排查都比MySQL麻烦。直接一步到位用MySQL 8。先在服务器上建一个工作目录比如/opt/halo把编排文件放在这里路径清晰方便维护sudo mkdir -p /opt/halo sudo vim /opt/halo/docker-compose.yml写入下面这个编排文件version: 3.8 services: mysql: image: mysql:8.0 container_name: halo-mysql restart: always environment: MYSQL_DATABASE: halodb MYSQL_USER: halo MYSQL_PASSWORD: your_password_here MYSQL_ROOT_PASSWORD: your_root_password_here volumes: - ./mysql-data:/var/lib/mysql networks: - halo-network halo: image: halohub/halo:2.20 container_name: halo restart: always depends_on: - mysql ports: - 127.0.0.1:8090:8090 environment: SPRING_CONFIG_ADDITIONAL_LOCATION: optional:file:/root/.halo2/ volumes: - ./halo-data:/root/.halo2 networks: - halo-network networks: halo-network: driver: bridge提示这里的your_password_here和your_root_password_here务必换成强密码别用root、123456这种一猜就中的值。尤其你的MySQL端口如果暴露到公网弱密码就是给扫描器送人头。我特意把Halo端口绑定到了127.0.0.1:8090也就是只允许本机访问。配合后面的Nginx反向代理公网进来的流量只走80/443端口不需要直接暴露应用端口能少很多无意义的扫描攻击。这个习惯我强烈建议保留。在启动之前还需要给Halo准备一份配置文件让它知道该连哪个数据库。创建/opt/halo/halo-data/application.yamlserver: port: 8090 spring: datasource: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://mysql:3306/halodb?useUnicodetruecharacterEncodingutf-8useSSLfalseallowPublicKeyRetrievaltrue username: halo password: your_password_here halo: work-dir: /root/.halo2 external-url: http://your-domain.com security: initializer: super-admin-username: admin super-admin-password: your_admin_password_here注意这里的url里主机名写的是mysql因为Docker Compose内部网络中容器之间通过服务名互相访问不是localhost。external-url先填你的域名或IP后面绑定域名时这个值要改成最终域名否则后台生成的文章链接地址会不对。然后启动cd /opt/halo sudo docker compose up -d看启动日志确认没有报错sudo docker compose logs -f halo看到类似Started HaloApplication in ... seconds的日志说明应用正常启动了。3.4 Nginx反向代理与HTTPS很多教程会把这一步放在最后但我觉得应该在初始化后台之前就把反向代理配好。因为Halo的站点URL设置和HTTPS强制跳转都依赖最终的公网入口先配好Nginx后面就不用返工。安装Nginxsudo apt install -y nginx sudo systemctl enable --now nginx在/etc/nginx/conf.d/下新建一个站点配置文件名字最好跟域名对应比如halo.confserver { listen 80; server_name your-domain.com; client_max_body_size 1024m; location / { proxy_pass http://127.0.0.1:8090; proxy_set_header Host $host; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection upgrade; } }这里有两个细节值得多说一下。client_max_body_size 1024m是给后台上传图片和附件用的Halo默认的附件上传如果超过Nginx默认的1m限制会直接报413错误。不少人在后台传图失败排查半天插件问题其实就是这一行没配。proxy_set_header Upgrade和Connection upgrade是给WebSocket用的Halo后台有些实时功能依赖WebSocket不配这几个请求头后台某些操作会出现诡异的行为。配置检查没问题后重载Nginxsudo nginx -t sudo systemctl reload nginxHTTPS直接用certbot一把梭sudo apt install -y certbot python3-certbot-nginx sudo certbot --nginx -d your-domain.comcertbot会自动修改Nginx配置加上证书和跳转规则整个过程约一分钟。证书快到期时它会自动续期前提是系统里装了certbot的定时任务一般装完默认就有了可以检查一下/etc/cron.d下面有没有certbot相关的条目。4. 后台初始化与站点美化4.1 首次登录与基础参数配置浏览器打开https://your-domain.com/console用我们之前在application.yaml里配置的管理员账号密码登录。首次登录成功后系统会引导你初始化站点信息包括站点名称、站点描述、Logo这些基础内容。这里我建议花点时间认真想想站点名称和副标题。它们不仅显示在页面上还会被主题自动抓取到浏览器的标题栏、页脚和SEO的title标签里。起一个准确的站点名远比之后在代码层面去改各种元信息要省事得多。后台还有几个参数我每次部署都会检查一遍文章默认路径规则建议改成/archives/{slug}这种带自定义别名的格式比默认带一长串数字ID的URL好看对SEO也友好。时区和日期格式改成Asia/Shanghai避免文章发布时间跟本地时间对不上。邮箱配置如果你要开启评论通知、订阅功能提前把SMTP邮箱配置好不然后面用户留了评论你都不知道。4.2 主题安装与个性化调整Halo的主题市场是这个系统做得最出色的部分之一。在后台左侧找到主题点击安装新主题就能在主题市场里浏览所有可用主题。每个主题都有预览图、评分和功能特性说明选一个看着顺眼的装上去就行。第一次用的人容易犯一个错误装完主题之后发现首页布局跟预览图不一样就开始怀疑是不是自己配置错了。其实主题装好之后需要到外观页面点击启用并且很多主题在启用后还要去主题设置里选首页展示模式才能完全生效。Halo后台的主题设置项非常丰富比如首页是走列表式还是卡片式、导航栏穿什么风格、页脚展示哪些模块、文章页是否显示TOC目录这些都可以可视化配置。如果主题设置满足不了需求再考虑动代码。主题文件里最基本要改的就是settings.yaml里定义的配置项和主题目录下的templates模板文件。不过我的建议是先花时间在后台设置里把配好的选项全部试一遍实在不够再提PR或找主题作者反馈别一上来就改代码否则以后主题一升级你的改动全被覆盖。4.3 插件体系评论、搜索与统计Halo的插件管理在后台左侧菜单里同样可以直接在插件市场在线安装。我每次新站点必装的是下面几类评论系统我推荐用Halo官方自带的评论插件数据存在自己的数据库里可定制性强还有反垃圾评论的基础策略。有些第三方评论服务虽然接入方便但数据在人家手里服务不稳定就会直接波及你站点的评论区自建站讲的就是数据可控这点别妥协。站点搜索可以装官方或者社区的搜索插件默认是基于数据库的模糊检索内容量不大的时候速度完全够用。如果你站点文章很多搜索体验要求高再考虑对接外部搜索引擎。统计分析我建议直接在主题或页脚里插入站点统计脚本的代码或者用插件加载。不过统计这类东西会拖累页面加载速度一个站点装一个统计就够了不要为了看数据装上两三个那是自己折腾自己。5. 内容创作实操与SEO基础5.1 把写作体验调到顺手的状态Halo后台的编辑器和市面上的Markdown编辑器使用体验非常接近。左侧是编辑区右侧是即时预览图片可以直接拖拽上传。我这里说三个能明显提升写作效率的小设置。第一在文章设置里把自动保存草稿打开。Halo支持自动保存编辑过程中就算浏览器崩了草稿也还在不用重新写。第二给文章启用自定义别名(slug)。写文章时手动设置一个简短、贴合主题的别名比如文章标题是手把手带你上手Halo建站别名就设成halo-guide生成的地址就是/archives/halo-guide。这个习惯对SEO的友好程度是很多新手忽略的。第三利用好分类和标签。Halo支持多级分类和标签体系。我建议分类控制在两到三层以内标签也别每次写出十几个标签的意义是聚合相关话题太碎了等于没分。这个跟你做资料归档的逻辑是一样的先规划好结构后面内容多了才好找。5.2 上线前必做的SEO基础配置在建站内容还没多起来的时候先把SEO的底子打好后面会省很多事。站点地图Halo有专门的SEO插件或内置的sitemap.xml接口在网站根路径直接访问就能拿到自动生成的站点地图。到百度站长平台和Google Search Console分别提交你的sitemap地址搜索引擎收录的速度会快很多。robots.txt确认站点根目录的robots.txt没有误屏蔽任何路径。有些主题或插件会默认配置过于激进的屏蔽规则导致搜索引擎不能正常抓取内容这是很隐蔽的问题经常被忽略。上线后可以去各大搜索引擎的抓取测试工具里跑一遍抓取请求看看返回是否正常。页面标题和描述Halo主题一般会自动把文章标题、摘要和分类信息组合到HTML的title和meta description里。如果主题没做这层处理就需要在主题设置里确认相应的SEO配置项。多花十分钟做这一步比以后通过站长工具一条条提交URL省事得多。5.3 自建站内容安全的三个底线既然是自己管服务器内容安全和数据安全就得自己负责。我总结了几条必须刻进DNA的底线。备份是第一优先级。Halo本身的数据备份功能可以把数据库和附件打成一个压缩包在后台直接下载。但我强烈建议在此基础上再做一层数据库定时备份写一个简单的cron脚本每天把MySQL数据目录或mysqldump导出的SQL文件同步到对象存储或者另一台机器上。服务器挂了可以再买但写了两年的文章没备份那才是真的损失。更新要选时机。Halo版本发布后不要第一时间升级先看GitHub的release页面有没有人反馈严重问题等个三到五天再动手。升级前一定要备份数据库和配置文件然后按官方升级文档操作。我见过不少升级完后台白屏的案例九成都是没备份就冲了。最后是私密内容。Halo插件市场里有文章加密插件可以对指定文章设置访问密码。如果你的站点涉及私密分享或者付费内容建议加上这层不要在公网裸奔。自建站最忌讳的就是以为没人知道这个地址搜索引擎的爬虫比你想象的勤快得多。6. 常见问题与排查技巧实录6.1 部署阶段最容易踩的坑部署阶段的问题基本都是环境或配置问题集中在下面几个方面。Docker拉取镜像慢如果是国内服务器从Docker Hub拉镜像经常超时。解决方法是配置镜像加速器国内主流云厂商都有提供。改完/etc/docker/daemon.json记得执行systemctl restart docker然后重新拉镜像。数据库连接失败最常见的两类原因一类是application.yaml里的数据库账号密码跟MySQL容器初始化时设置的不一致另一类是url里的主机名写错了。注意容器内访问MySQL用的是服务名mysql不是localhost也不是服务器公网IP。端口被占用8090端口如果已经被其他进程占用Docker启动日志里会直接报端口冲突。用ss -lntp | grep 8090看看是什么进程占用了端口把进程停掉或者改Halo的端口都可以。整理成速查表更直观现象可能原因排查命令/方法公网无法访问站点云安全组未放行80/443端口登录云控制台检查入方向规则后台图片上传报413Nginx没配置client_max_body_size检查Nginx配置文件并重载数据库连接失败账号密码或主机名配置错误核对application.yaml与compose环境变量升级后后台白屏未按版本升级或缓存异常查看日志必要时清理浏览器缓存Docker拉镜像超时网络问题未配置加速器配置registry-mirrors后重启Docker时间显示不对时区未设置在后台把时区改为Asia/Shanghai6.2 升级Halo版本的规范操作Halo的版本升级有一个大原则跨版本升级前先看官方升级说明。项目从2.x到后续版本变化很大数据库结构也在不断演进直接替换新版镜像不一定能读旧数据。标准操作流程是# 1. 备份 cd /opt/halo sudo docker compose exec mysql mysqldump -u halo -p halodb halo-backup.sql # 2. 拉取新镜像 sudo docker pull halohub/halo:2.21 # 3. 修改docker-compose.yml里的镜像版本号 # 4. 重新创建容器 sudo docker compose up -d启动后马上看日志和后台功能如果有异常把docker-compose.yml里的版本号改回旧版本再执行一次docker compose up -d就能快速回滚到升级前的状态。这就是用Docker部署的最大好处升级和回滚都是分钟级操作。6.3 针对小内存服务器的优化建议如果你的服务器只有1G内存Halo加MySQL可能会比较吃紧。有几个实测有效的优化手段。首先是给Docker设置内存限制防止某个容器跑崩拖垮整台机器。在docker-compose.yml的halo服务里加入mem_limit: 768mMySQL服务加mem_limit: 512m这样两个容器总占用被限制在1.3G以内系统还有富余内存跑Nginx和SSH。其次是MySQL的参数调优。在compose里给MySQL容器加启动参数比如--innodb-buffer-pool-size64M和--performance-schemaoff能显著降低内存占用。个人博客的数据量通常不大这些参数调低之后几乎没有任何性能感知差异但内存占用能降下来一大截。最后是建议定期清理Halo上传目录里的临时文件和回收站。后台删除图片默认进入回收站如果站点运行时间久了回收站可能堆积了大量废弃图片不仅占磁盘空间也会让备份包变大。每隔一段时间清理一次保持数据目录干净整洁。6.4 上线后的日常维护清单站点跑起来之后维护工作其实很轻但我建议把下面几件事固定成习惯。每天或每周看一下docker compose logs里有没有异常报错尤其是数据库连接断开和内存溢出的错误。这两种问题通常不会立刻让站点挂掉但会表现为偶尔出现500页面或后台响应缓慢。定期检查HTTPS证书的有效期。certbot虽然会自动续期但如果服务器时间不同步或者定时任务被禁用了证书过期是悄无声息的。文件名和目录名里面的过期时间不会提醒你只有用户的浏览器会显示大红警告页。可以在cron里加一条每天检查证书剩余天数的脚本快到期时发邮件通知自己。最后就是保持内容更新。搜索引擎对新站的抓取频率和权重积累很大程度上取决于内容的更新频率和稳定性。建站初期不用追求数量能稳定产出优质内容比一次性灌入几十篇文章再停更三个月要有效得多。写在最后做自建站这些年我发现很多人的问题不是技术门槛而是被选型焦虑耗掉了太多精力。Halo这套方案的优势在于它把复杂的东西藏在了成熟的设计后面同时又把该留给你的自由都留给了你。你不需要成为一个Java专家也不需要懂前端框架只需要理解域名、服务器、反向代理这几个基础概念就能拥有一个完全属于自己的站点。我个人在实际操作中的体会是部署最顺利那次反而是我第一次用Docker Compose的版本因为前面的坑都踩完了。如果你正准备把第一个Halo站点跑起来记住两件事一是配置环境变量和数据库密码时多用点心二是备份永远在升级之前。做到这两点你的建站之路基本已经成功了一大半。最后再分享一个小技巧把docker-compose.yml和application.yaml这两个文件存一份到你的Git仓库或者网盘里。以后无论是换服务器还是灾难恢复只要把这两个文件拿回来加上一份数据库备份你的整个站点就能在新机器上原样复活。这比任何花哨的功能都实在。