Beego ORM 初始化必须显式调用 orm.RegisterDriver 和 orm.RegisterDataBase,否则 QueryTable 会 panic;需在 beego.Run() 前注册驱动、数据库和模型,字段需大写并加 orm tag,主键建议标注 orm:"pk;auto",RunSyncdb 生产环境严禁启用 drop 表。

beego ORM 初始化必须显式调用 orm.RegisterDriver 和 orm.RegisterDataBase
不初始化就直接用 orm.QueryTable 会 panic,错误信息通常是 no registered driver 或 database not registered。Beego 的 ORM 是独立模块,不会随框架自动加载数据库驱动和连接配置。
常见错误是只装了 github.com/beego/beego/v2/client/orm 和 MySQL 驱动,但没在 main.go 或 models/init.go 里注册:
-
orm.RegisterDriver("mysql", orm.DRMySQL)—— 注册驱动类型,不能漏掉这句 -
orm.RegisterDataBase("default", "mysql", "root:pass@tcp(127.0.0.1:3306)/test?charset=utf8mb4")—— 连接字符串要带参数,charset=utf8mb4推荐加上,避免 emoji 或四字节 UTF-8 存储失败 - 必须在
beego.Run()之前执行,否则模型注册可能失效
orm.RegisterModel 必须在所有模型定义后、运行前集中调用
哪怕只有一个 models.User 结构体,也得手动注册,ORM 不会自动扫描包内 struct。漏注册会导致 QueryTable("user") 返回空结果或 panic。
推荐做法:在 models/models.go 末尾统一注册,并确保 import 路径正确:
- 结构体字段必须首字母大写(可导出),且加
orm:"column(name);size(50)"等 tag 显式声明映射关系 - 主键建议显式标注
orm:"pk;auto",否则默认找Id字段,且要求是int64类型 - 注册顺序无关,但所有模型必须在
orm.RunSyncdb或首次查询前完成注册
增删改查操作中,Insert/Read/Update 都要求对象已赋值主键或满足条件
比如 o.Read(&u, "Name") 查不到会返回 err != nil(不是 nil),但 o.Read(&u, "Id") 找不到时 err 是 sql.ErrNoRows,不是 panic —— 这点容易误判为失败而中断流程。
-
Insert成功后,int64主键会自动写回结构体字段(前提是 tag 标了auto) -
Update默认只更新非零值字段,想更新零值(如Status: 0)得传字段名列表:o.Update(&u, "Status", "UpdatedAt") -
Delete只接受主键值或完整对象,不支持条件删除(如DELETE FROM user WHERE status = 0),得用o.QueryTable("user").Filter("status", 0).Delete()
自动迁移 RunSyncdb 仅在 dev 模式生效,且会 DROP 表
orm.RunSyncdb("default", false, true) 中第三个参数 true 表示 drop table if exists,生产环境绝对不能设为 true,否则重启服务就丢数据。
它也不会自动加索引或改字段类型,只做“结构对齐”:新增字段会 ADD COLUMN,但已存在字段类型变更(如 string → int)会被忽略,也不会报错。
- 上线前务必用
bee generate docs或手写 SQL 做 schema diff - dev 模式下可以设
true快速验证模型,但 CI/CD 流程中应禁用 - 字段名变更(如从
Name改成Fullname)会导致旧表字段残留,新字段为空,需人工处理
main.go 开头就注册驱动和数据库,而不是等某个 controller 里第一次用 ORM 才去 init —— 那时候 panic 已经发生在 HTTP 请求路径里,日志难追溯,恢复成本高。


















