记录 Music Tag Web V2 的数据库迁移过程
⚠️ 注意:数据库迁移操作有风险,请务必提前做好备份!
背景
Music Tag Web 是我日常高频使用的一个项目。最近偶然发现该项目已经支持 MySQL 部署,于是决定把手头的 SQLite 数据库迁移到 MySQL,并记录下整个过程,方便以后查阅,也希望能帮到有同样需求的朋友。
准备工作
- Navicat Premium — 数据库管理 & 迁移的主力工具
- Office / Excel — 处理表数据的辅助工具
- SQLite 本地数据库文件 — 待迁移的源数据
第一步:导出并查看 SQLite 数据库
首先导出 SQLite 的本地数据库文件,用 Navicat 打开,确认数据完整无误。

第二步:初始化 MySQL 数据库
创建一个专用的 MySQL 账号给项目使用,然后启动 Docker 容器,让项目自动完成数据库表结构的初始化。

确认表结构生成无误后,停止容器,然后清空数据库内的所有记录。
⚠️ 清空前再次确认选中的是目标数据库,不要清错表!

第三步:使用 Navicat Data Transfer 迁移数据
打开 Navicat 的 Data Transfer 功能,配置好源库和目标库:
- 左边是源库(SQLite)
- 右边是目标库(MySQL)


关键设置
在 Options 中,取消勾选"新建表(Create tables)"和"删除表(Drop tables)",因为我们已经提前初始化好了表结构。

执行
点击开始执行迁移。如果中途失败:
- 清除目标库所有记录,解决问题后重新执行;
- 也可以在 Options 中勾选 "Continue on error",执行完成后查看日志,单独处理失败的表。
第四步:处理常见迁移问题
下面是我在迁移过程中踩到的几个坑:
1. music_artist 表 — 唯一键冲突
full_text 字段被设为不区分大小写的唯一值(utf8mb4_unicode_ci),导致 Reol 和 REOL 被判为冲突。

解决办法: 将该字段的排序规则从 utf8mb4_unicode_ci 改为 utf8mb4_bin 后保存。

2. task_task 表 — 非空字段缺少数据
表中部分非空字段没有数据,导致导入失败。
解决办法: 从原表导出 Excel,缺失的数值字段填 0,处理好后重新导入(注意日期格式)。

3. sqlite_sequence 表
这个表是 SQLite 特有的,MySQL 表结构中不存在,直接忽略即可,无需处理。
4. music_folder 表
导入时遇到 NOT NULL 约束报错。解决办法: 先取消该字段的 NOT NULL 约束再导入。

第五步:修复启动报错
所有表迁移完成后,启动 Docker 容器,结果发现启动失败 🫠

进入容器内部,依次执行以下命令:
python manage.py migrate task 0027 --fake
python manage.py migrate

这两条命令的作用是标记已完成的 migration 记录,让 Django 的 migration 状态和实际数据库状态保持一致。
完成!
重启容器后即可正常登录,数据库迁移大功告成 🎉


总结
整个迁移过程的核心思路:
- 结构先走 — 用项目初始化生成表结构
- 数据后搬 — 用 Navicat Data Transfer 搬数据
- 逐个排错 — 字段编码、非空约束、唯一键冲突,见招拆招
- fake migrate — 用
--fake同步 Django migration 状态
整个过程比预想的顺利,半天就能搞定。希望这篇记录能帮到你!
