Strapi+Heroku Postgres修改Schema后数据丢失,该如何解决?
问题分析与解决方案
这不是正常现象,是配置错误导致的
你的数据丢失问题绝非Strapi搭配Heroku Postgres的正常行为,核心原因是生产环境的配置或部署流程触发了数据库重置操作,而非Schema变更本身导致的数据丢失。常见诱因包括:
NODE_ENV环境变量被错误设为development:Strapi在开发模式下会自动同步Schema,若配置不当可能重置数据库(本地SQLite因存储特性未触发,但PostgreSQL环境会出现数据丢失)。- 数据库配置中
settings.force被设为true:该参数会强制Strapi每次启动时重建数据库表,直接清空所有数据。 - 部署脚本包含
strapi db:drop/strapi db:create等危险命令:这类操作会直接删除并重建数据库,导致数据丢失。
修复配置并启用可靠的Schema迁移方案
1. 先修正核心配置
- 在Heroku控制台确认
NODE_ENV环境变量值为production。 - 修改生产环境数据库配置文件(
config/env/production/database.js),确保关键参数正确:module.exports = ({ env }) => ({ connection: { client: 'postgres', connection: { connectionString: env('DATABASE_URL'), ssl: { rejectUnauthorized: false }, }, pool: { min: 2, max: 10 }, settings: { force: false, // 禁止强制重建数据库 autoMigration: false, // 生产环境关闭自动同步,改用手动迁移 }, }, });
2. 启用Strapi官方迁移工具
Strapi自带增量迁移系统,能在不丢失数据的前提下更新Schema:
- 本地开发时,每次修改Schema后,运行命令生成迁移文件:
迁移文件会生成在strapi migration:generate --name=modify-post-required-field./database/migrations目录下。 - 编辑迁移文件,编写
up(应用变更)和down(回滚变更)逻辑,比如修改字段的required属性:module.exports = { async up(queryRunner) { await queryRunner.query(`ALTER TABLE "posts" ALTER COLUMN "title" DROP NOT NULL;`); }, async down(queryRunner) { await queryRunner.query(`ALTER TABLE "posts" ALTER COLUMN "title" SET NOT NULL;`); }, }; - 将迁移文件提交到Git仓库,部署到Heroku。
- 修改
package.json的启动脚本,确保每次部署自动执行迁移:"scripts": { "start": "strapi db:migrate && strapi start", "build": "strapi build" }
备选CMS推荐(若需更换)
如果觉得Strapi的迁移流程不符合需求,可考虑这些对Schema迁移更友好的CMS:
- Directus:自带可视化迁移工具,支持增量更新,PostgreSQL适配完善,部署到Heroku流程简单,无需手动编写SQL迁移脚本。
- Payload CMS:基于MongoDB/PostgreSQL,内置迁移系统,Schema变更可通过代码定义,自动生成迁移逻辑,数据保护能力强。
- KeystoneJS:依托Prisma ORM的成熟迁移系统,支持可视化Schema编辑,增量迁移稳定,适合需要复杂数据模型的项目。
内容的提问来源于stack exchange,提问作者Strawberryplants
相关产品推荐
相关产品推荐

