Go简易博客系统应基于net/http和database/sql手写实现:用结构体封装路由便于测试与扩展中间件;原生SQL控制slug生成、时间字段等细节;开发期用FileServer和ParseFiles提升效率;必须处理所有错误并注意Rows.Close()等易漏细节。

Go 本身不内置 Web 框架或 ORM,所谓“简易博客系统”必须自己选型组合,否则连数据库存文章都得手写 SQL 字符串拼接。
用 net/http 而不是第三方框架起步
新手容易一上来就装 gin 或 echo,但博客核心逻辑简单(列表、详情、新增),net/http 完全够用,且能看清请求生命周期。路由别写死在 http.HandleFunc 里,封装成结构体方法更易测试:
type BlogHandler struct {
db *sql.DB
}
func (h *BlogHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
switch r.URL.Path {
case "/":
h.listPosts(w, r)
case "/post":
if r.Method == "GET" {
h.showPost(w, r)
} else if r.Method == "POST" {
h.createPost(w, r)
}
}
}这样后续加中间件(如登录校验)也只改 ServeHTTP 即可,不用动每个 handler 函数。
用 database/sql + 原生 SQL 管理文章数据
别碰 gorm 这类全自动 ORM——它会让字段映射、时间类型、NULL 处理变成黑盒,而博客的 created_at、updated_at、slug 生成等细节恰恰需要显式控制。示例插入逻辑:
立即学习“go语言免费学习笔记(深入)”;
_, err := db.Exec(
"INSERT INTO posts(title, slug, content, created_at) VALUES(?, ?, ?, ?)",
title, slug, content, time.Now().UTC(),
)注意点:
dmSOBC SHOP网店系统由北京时代胜腾信息技术有限公司(http://www.webzhan.com)历时6个月开发完成,本着简单实用的理念,商城在功能上摒弃了外在装饰的一些辅助功能,尽可能的精简各项模块开发,做到有用的才开发,网店V1.0.0版本开发完成后得到了很多用户的使用并获得了好评,公司立即对网店进行升级,其中包括修正客户提出的一些意见和建议,现对广大用户提供免费试用版本,如您在使用
-
slug必须手动生成(用strings.ReplaceAll+ 小写处理),不能依赖数据库自增 ID -
created_at和updated_at别设默认值,Go 层统一用time.Now().UTC() - 查询列表时用
SELECT * FROM posts ORDER BY created_at DESC LIMIT 10,别省略ORDER BY,SQLite/MySQL 默认顺序不可靠
静态资源和模板别放 go:embed 里过早
开发阶段直接用 http.FileServer 挂载 ./static 目录,模板用 html/template 加载文件路径:
t := template.Must(template.ParseFiles("templates/layout.html", "templates/index.html"))理由很实际:
-
go:embed会让每次改 CSS 或 HTML 都要重新编译,打断开发流 - 模板错误(比如
{{.Title}}写成{{.title}})在ParseFiles阶段就 panic,比运行时渲染失败更容易定位 - 上线前再用
go:embed打包,不影响开发效率
别跳过错误处理,尤其在数据库和模板环节
Go 的错误返回不是装饰,是契约。常见漏点:
-
db.QueryRow(...).Scan(&v)后没检查err,导致v是零值还继续用 -
template.Execute返回非nil错误时直接忽略,浏览器看到空白页却无日志 -
http.Redirect后没return,后续代码仍执行(比如又写了一次响应头)
最简单的兜底:所有 HTTP handler 函数末尾加 if err != nil { http.Error(w, err.Error(), http.StatusInternalServerError) },先保功能通,再细化错误类型。
真正卡住人的从来不是语法,而是 database/sql 的 Rows.Close() 忘调导致连接泄漏,或是模板里 {{range .Posts}} 遇到空切片时不渲染也不报错——这些细节不跑一遍真实请求根本发现不了。









