You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在VPS上通过Docker+Next.js执行SQLite的Drizzle生产迁移

解决方案

一、处理Drizzle迁移与应用启动的命令执行问题

方法1:Shell命令串联(简单场景)

直接修改Dockerfile的CMD为shell模式,让迁移命令执行完成后再启动应用:

# 替换原有CMD
CMD ["sh", "-c", "pnpm db:migrate:prod && pnpm start"]

注:若迁移命令执行失败,应用不会启动,这是生产环境的合理逻辑,避免应用连接未初始化的数据库。

方法2:Entrypoint脚本(健壮推荐)

通过初始化脚本灵活处理前置操作,还能保证信号正确传递:

  1. 在项目根目录创建entrypoint.sh文件:
#!/bin/sh
set -e

# 执行数据库迁移
pnpm db:migrate:prod

# 以exec方式启动应用,确保容器停止时应用能优雅退出
exec pnpm start
  1. 修改Dockerfile,添加并配置脚本:
# 复制脚本到容器并赋予执行权限
COPY entrypoint.sh /usr/local/bin/
RUN chmod +x /usr/local/bin/entrypoint.sh

# 设置入口脚本
ENTRYPOINT ["entrypoint.sh"]

二、持久化SQLite数据库文件

SQLite依赖本地文件,需将数据库所在目录挂载到宿主机或Docker卷,避免容器销毁后数据丢失:

步骤1:确认数据库路径

确保Drizzle配置中,users.prod.sqlite的存放路径指向项目内固定目录(比如./data),示例配置:

// drizzle.config.js
export default {
  out: "./drizzle",
  schema: "./src/db/schema.ts",
  driver: "better-sqlite",
  dbCredentials: {
    url: "./data/users.prod.sqlite"
  }
};

步骤2:Dockerfile中创建目录(可选但推荐)

在Dockerfile中添加一行,确保容器内的数据库目录存在:

RUN mkdir -p /app/data

步骤3:运行容器时挂载存储

方式A:绑定宿主机目录(需直接访问宿主机文件时使用)

# 宿主机创建存储目录
mkdir -p /var/nextjs-sqlite-data

# 运行容器时挂载目录
docker run -d -p 3000:3000 -v /var/nextjs-sqlite-data:/app/data your-image-name

方式B:使用Docker卷(推荐,Docker统一管理存储)

# 创建Docker卷
docker volume create nextjs-sqlite-data

# 运行容器时挂载卷
docker run -d -p 3000:3000 -v nextjs-sqlite-data:/app/data your-image-name

三、完整Dockerfile示例

结合上述操作,最终Dockerfile示例如下:

FROM node:20-alpine

WORKDIR /app

COPY package.json pnpm-lock.yaml ./
RUN npm install -g pnpm && pnpm install --prod

COPY . .

RUN mkdir -p /app/data

COPY entrypoint.sh /usr/local/bin/
RUN chmod +x /usr/local/bin/entrypoint.sh
ENTRYPOINT ["entrypoint.sh"]

内容的提问来源于stack exchange,提问作者deadcoder0904

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 13:43:22