29 KiB
生产部署计划
更新时间:2026-05-02
当前落地进度
已落地生产基础设施骨架与首批生产 Jenkinsfile:
deploy/systemd/spacetimedb.servicedeploy/systemd/genarrative-api.servicedeploy/nginx/genarrative.confdeploy/nginx/snippets/genarrative-maintenance.confdeploy/env/api-server.env.examplescripts/deploy/maintenance-on.shscripts/deploy/maintenance-off.shscripts/deploy/maintenance-status.shscripts/build-production-release.shscripts/jenkins-checkout-source.shscripts/deploy/production-web-deploy.shscripts/deploy/production-api-deploy.shscripts/deploy/production-stdb-publish.shjenkins/Jenkinsfile.production-web-buildjenkins/Jenkinsfile.production-web-deployjenkins/Jenkinsfile.production-api-buildjenkins/Jenkinsfile.production-api-deployjenkins/Jenkinsfile.production-stdb-module-buildjenkins/Jenkinsfile.production-stdb-module-publishjenkins/Jenkinsfile.production-full-build-and-deployjenkins/Jenkinsfile.production-server-provisionjenkins/Jenkinsfile.production-database-exportjenkins/Jenkinsfile.production-database-importnpm run build:production-release
旧 Jenkins 一体化发布链对应的 Jenkinsfile 已从仓库移除,生产构建和发布入口统一切到 jenkins/Jenkinsfile.production-*。scripts/deploy-rust-remote.sh 等旧发布包脚本暂保留为历史迁移参考,不再作为生产 Jenkins Job 的入口。
目标
将当前部署方式调整为单机生产推荐方案:生产运行路径不使用 Docker,不再使用旧的一体化启动脚本,由 systemd 托管 SpacetimeDB 与 Rust api-server,由 Nginx 托管主站、后台前端与必要反向代理。
本计划用于重新创建 Jenkins 流水线、服务器环境配置、网站发布、api-server 发布、SpacetimeDB 模块发布,以及数据库人工导入导出流程。
生产架构
- Nginx 作为唯一公网入口,负责 HTTPS、静态站点、后台静态页面、维护页与
/admin/api/反向代理。 - SpacetimeDB 作为系统服务运行,监听
127.0.0.1:3000,数据根目录为/stdb。 - Rust
api-server作为系统服务运行,监听127.0.0.1:8082,只被 Nginx 的/admin/api/访问。 - 主站与后台前端构建为静态文件,发布到服务器固定目录,不放入 Jenkins 目录,也不跟随 Docker 镜像。
- 除网站静态发布外,
api-server发布、SpacetimeDB 模块发布、数据库导入、服务器配置变更都必须先进入维护模式。
服务器目录
/opt/genarrative/releases/<version>/:每次发布的完整版本目录。/opt/genarrative/current:指向当前生效版本的软链接。/srv/genarrative/web:指向/opt/genarrative/current/web,供 Nginx 托管静态站点。/etc/genarrative/api-server.env:api-server生产环境变量文件。/var/lib/genarrative/maintenance/enabled:维护模式开关文件。/stdb:SpacetimeDB 程序、配置与数据根目录。
生产密钥
/etc/genarrative/api-server.env 中的生产密钥指所有只能存在于生产服务器、不能进入 Git、不能进入构建产物的敏感配置。典型内容包括:
- LLM 或第三方服务 API Key。
- 短信服务 Access Key 与 Secret。
- 后台登录、会话、签名、加密相关密钥。
- 生产 SpacetimeDB 地址与数据库名。
- 只允许生产使用的回调地址、白名单或内部令牌。
该文件由服务器配置流水线或人工初始化创建,权限建议为 root:genarrative、0640。Jenkins 构建任务不能读取该文件;只有生产发布或服务启动需要读取。
systemd 服务
SpacetimeDB
- 服务名:
spacetimedb.service - 运行用户:
spacetimedb - 工作目录:
/stdb - 启动命令:
/stdb/spacetime --root-dir=/stdb start --listen-addr=127.0.0.1:3000 - 对外暴露:默认不直接暴露公网端口。
该方案与 SpacetimeDB 官方自托管文档一致:使用 Ubuntu、专用用户、/stdb 根目录、systemd 服务和 Nginx。
api-server
- 服务名:
genarrative-api.service - 运行用户:
genarrative - 工作目录:
/opt/genarrative/current - 可执行文件:
/opt/genarrative/current/api-server - 环境文件:
/etc/genarrative/api-server.env - 监听地址:
127.0.0.1:8082
api-server 不放入 Docker,也不直接暴露公网端口。发布时替换版本目录并重启 genarrative-api.service。
Nginx 规则
只保留必要入口:
/:主站静态页面。/admin/:后台前端静态页面,后台构建时使用/admin/作为 base path。/admin/api/:反向代理到http://127.0.0.1:8082/admin/api/。- HTTP 到 HTTPS:只保留 301 重定向。
/maintenance.html:维护中页面。
移除这些公网反向代理:
/api/*/generated-*- 公网
/healthz - 其他旧的一体化 web server 代理入口。
SpacetimeDB 公网路由默认保持收敛,只按实际前端 SDK 需要暴露最小集合。禁止开放可远程发布数据库或管理实例的通用入口。
维护模式
维护模式由 /var/lib/genarrative/maintenance/enabled 控制:
- 文件存在:进入维护模式。
- 文件不存在:退出维护模式。
行为:
- 网站静态资源发布不进入维护模式。
api-server发布、SpacetimeDB 模块发布、数据库导入、服务器配置变更必须进入维护模式。- 普通页面在维护模式下展示
/maintenance.html。 /admin/api/*在维护模式下返回 503。- 静态资源仍允许访问,避免维护页样式和资源加载失败。
- 发布成功后自动解除维护模式。
- 发布失败时保持维护模式,并通过邮件通知人工处理。
构建产物
生产发布包构建入口:
npm run build:production-release -- --name <version>
每次构建产物按版本号归档:
build/<version>/
├─ web/
│ ├─ index.html
│ ├─ assets/
│ ├─ maintenance.html
│ └─ admin/
├─ web.tar.gz
├─ web.tar.gz.sha256
├─ api-server
├─ api-server.sha256
├─ spacetime_module.wasm
├─ spacetime_module.wasm.sha256
├─ release-manifest.json
├─ scripts/
│ ├─ database-export.mjs
│ ├─ database-import.mjs
│ ├─ spacetime-migration-common.mjs
│ ├─ maintenance-on.sh
│ ├─ maintenance-off.sh
│ └─ maintenance-status.sh
├─ deploy/
│ ├─ systemd/
│ │ ├─ spacetimedb.service
│ │ └─ genarrative-api.service
│ ├─ nginx/
│ │ ├─ genarrative.conf
│ │ └─ snippets/genarrative-maintenance.conf
│ └─ env/api-server.env.example
└─ README.md
web/ 可以保留在构建目录中供本地 smoke test 与人工排查使用,但 Jenkins Web Build 归档和 Web Deploy 传输必须以 web.tar.gz 为主,避免把大量静态碎文件逐个传回 Jenkins controller。api-server 和 spacetime_module.wasm 是单文件产物,默认直接归档单文件与对应 .sha256,不强制压缩。
不再生成旧产物:
web-server.mjs- 旧的一体化
start.sh - 旧的一体化
stop.sh
Jenkins 节点
Jenkins 可运行在 Windows 或其他机器上,本机 Windows 只作为人工触发入口;构建与发布动作只允许由 Jenkins 调度到 Linux agent 执行。当前已接入的 Linux agent 是开发/构建机,同时也是 development 环境部署机。
开发/构建/开发部署实例
- Jenkins Job 参数不暴露真实节点名、IP 或带 IP 的标签。
- 构建 Job 固定使用 label expression:
linux && genarrative-build。 - 当前开发/构建/开发部署 agent 必须同时配置
linux与genarrative-build两个标签;非 Linux 节点不能承担构建或部署。 - 用途:拉代码、安装依赖、构建主站、构建后台、构建
api-server、构建 SpacetimeDB wasm、归档产物,并执行DEPLOY_TARGET=development的开发环境部署。
生产/发布实例
- Jenkins Job 参数不暴露真实节点名、IP 或带 IP 的标签。
- 生产机已作为独立 Linux Jenkins agent 接入,节点名使用脱敏名称
genarrative-release-deploy-01,调度标签只使用linux与genarrative-release-deploy。 - 生产机真实连接地址只允许保存在 Jenkins 节点 SSH launcher 的
host字段中,不能写入节点名、调度标签、Job 参数默认值或文档推荐命令。 - 发布 Job 通过
DEPLOY_TARGET选择逻辑部署目标,再在 Jenkinsfile 内部映射到 Linux-only 脱敏调度表达式:development -> linux && genarrative-build,release -> linux && genarrative-release-deploy。 - 用途:服务器配置、发布静态网站、发布
api-server、发布 SpacetimeDB 模块、数据库导入导出、维护模式切换。
Git 仓库访问
Jenkins controller 与 Linux agent 看到的 Git 服务地址不同,必须拆成两层配置:
- Jenkins Job 的
Pipeline script from SCM由 controller 执行,SCM URL 使用 controller 可访问的公网地址:http://82.157.175.59:3000/GenarrativeAI/Genarrative.git。 - Jenkinsfile 内部的源码、脚本 checkout 在 Linux agent 上执行,
GIT_REMOTE_URL使用 agent 本机可访问地址:http://127.0.0.1:3000/GenarrativeAI/Genarrative.git。
因此生产 Jenkinsfile 不使用 checkout scm 作为构建源码入口,而是显式 checkout([$class: 'GitSCM', userRemoteConfigs: [[url: "${GIT_REMOTE_URL}"]], ...])。后续 scripts/jenkins-checkout-source.sh 会继续把 origin 设置为 GIT_REMOTE_URL,并按 SOURCE_BRANCH / COMMIT_HASH 拉取和校验目标提交。
127.0.0.1 只代表当前执行该阶段的 Linux agent 自身;如果 release agent 与 Git 服务不在同一台机器,必须把对应 Jenkinsfile 的 GIT_REMOTE_URL 改成 release agent 可访问的内网地址,不能让 release 发布阶段回退到 controller 公网拉取。
SSH PEM 凭证
在 Jenkins 中使用 SSH Username with private key 类型添加 PEM 私钥:
genarrative-dev-ssh-key:开发/构建实例 SSH 凭证。genarrative-prod-root-ssh:当前开发/构建实例已使用的 SSH 凭证;生产/发布实例复用同一个凭证。
推荐使用非 root 用户,例如 jenkins。该用户只通过 sudoers 获得必要命令权限,例如 systemctl restart genarrative-api、nginx -t、维护脚本、发布目录切换等。
Jenkins 流水线
生产 Jenkins 目标流水线:
Genarrative-Server-ProvisionGenarrative-Web-BuildGenarrative-Web-DeployGenarrative-Api-BuildGenarrative-Api-DeployGenarrative-Stdb-Module-BuildGenarrative-Stdb-Module-PublishGenarrative-Database-ExportGenarrative-Database-ImportGenarrative-Full-Build-And-Deploy
已落地的生产流水线脚本文件:
jenkins/Jenkinsfile.production-web-buildjenkins/Jenkinsfile.production-web-deployjenkins/Jenkinsfile.production-api-buildjenkins/Jenkinsfile.production-api-deployjenkins/Jenkinsfile.production-stdb-module-buildjenkins/Jenkinsfile.production-stdb-module-publishjenkins/Jenkinsfile.production-full-build-and-deployjenkins/Jenkinsfile.production-server-provisionjenkins/Jenkinsfile.production-database-exportjenkins/Jenkinsfile.production-database-import
Genarrative-Database-Export、Genarrative-Database-Import 的生产版 Jenkinsfile 已落地;旧的数据库导入导出 Jenkinsfile 已删除,避免继续沿用旧部署目录和旧一体化发布链假设。
构建流水线运行在当前 Linux agent 的脱敏 label expression linux && genarrative-build。发布、导入导出和服务器配置流水线通过 DEPLOY_TARGET 映射到 Linux-only 脱敏部署表达式;其中 development 映射到当前 Linux 开发/构建/开发部署 agent 的 linux && genarrative-build,release 映射到独立 Linux 生产部署 agent 的 linux && genarrative-release-deploy,不能复用当前开发/构建/开发部署 agent。真实机器名、IP 和带 IP 的 Jenkins label 只允许留在 Jenkins 节点连接配置中,不能暴露为 Job 参数默认值、调度标签或文档推荐值。
发布流水线通过 Jenkins copyArtifacts(...) 从对应构建 Job 获取归档产物,因此 Jenkins 需要安装并启用 Copy Artifact 插件。数据库导入流水线的手动上传模式使用 stashedFile 文件参数,因此 Jenkins 还需要安装并启用 File Parameter 插件。生产发布不能退回到读取构建 workspace 本地目录的旧模式。
所有发布流水线必须提供 DEPLOY_TARGET 参数,用于选择逻辑部署目标:
- 默认值:
development,用于当前 Linux 开发/构建/开发部署 agent 上的开发环境部署,对应脱敏调度表达式linux && genarrative-build。 - 备选值:
release,对应生产发布目标,由独立 Linux 生产部署 agent 执行。
发布流水线的 agent 必须使用 DEPLOY_TARGET 在 Jenkinsfile 内部映射到脱敏 label expression,并且表达式必须包含 linux,避免在参数页面暴露真实节点名、IP 或带 IP 的 Jenkins label,也避免非 Linux 节点执行构建或部署。release 目标还必须要求 CONFIRM_RELEASE_DEPLOY_AGENT=true。Genarrative-Full-Build-And-Deploy 也必须透传同一个 DEPLOY_TARGET,确保 Stdb publish、API deploy、Web deploy 三个部署动作落到同一类目标部署环境。
Rust 构建缓存与磁盘控制
Jenkins 在 agent 上执行构建时会为不同 Job 或不同构建创建独立 workspace;Rust 默认把编译产物写入仓库内 server-rs/target/,会导致每个 workspace 都保留一份完整 target 目录,占用大量磁盘。生产构建流水线必须把 Rust 缓存固定到 workspace 外的稳定目录。
如果构建 agent 使用 root 账户执行,缓存目录不应写死为 /var/lib/jenkins。推荐优先使用单独数据盘,例如 /data/jenkins-cache/genarrative/;如果没有数据盘,可使用 /var/cache/genarrative-build/:
mkdir -p /var/cache/genarrative-build/{cargo-home,cargo-target,sccache}
chmod 700 /var/cache/genarrative-build
Rust 构建流水线建议统一设置:
environment {
CARGO_HOME = '/var/cache/genarrative-build/cargo-home'
CARGO_TARGET_DIR = '/var/cache/genarrative-build/cargo-target/prod-release'
CARGO_INCREMENTAL = '0'
RUSTC_WRAPPER = 'sccache'
SCCACHE_DIR = '/var/cache/genarrative-build/sccache'
SCCACHE_CACHE_SIZE = '30G'
}
如使用数据盘,则把上述路径替换为:
environment {
CARGO_HOME = '/data/jenkins-cache/genarrative/cargo-home'
CARGO_TARGET_DIR = '/data/jenkins-cache/genarrative/cargo-target/prod-release'
CARGO_INCREMENTAL = '0'
RUSTC_WRAPPER = 'sccache'
SCCACHE_DIR = '/data/jenkins-cache/genarrative/sccache'
SCCACHE_CACHE_SIZE = '30G'
}
scripts/build-production-release.sh 必须尊重 CARGO_TARGET_DIR,不能硬编码从 server-rs/target/ 拷贝 Rust 产物。脚本中的产物路径应按以下口径计算:
CARGO_TARGET_DIR="${CARGO_TARGET_DIR:-${SERVER_RS_DIR}/target}"
API_BINARY_SOURCE="${CARGO_TARGET_DIR}/x86_64-unknown-linux-gnu/release/api-server"
WASM_SOURCE="${CARGO_TARGET_DIR}/wasm32-unknown-unknown/release/spacetime_module.wasm"
并发与清理规则:
- Rust 构建 Job 建议使用
disableConcurrentBuilds(),或对共享CARGO_TARGET_DIR加 Jenkinslock,避免多个同包 release 构建同时写入同一最终产物路径。 - 生产发布流水线只能消费
build/<version>/或 Jenkins 归档产物,不允许从共享cargo-target目录直接发布。 SCCACHE_CACHE_SIZE必须设置上限,避免编译缓存无限增长。- 对
/var/cache/genarrative-build/cargo-target或数据盘对应目录配置定期清理,建议保留最近 14 到 30 天。 - Jenkins Job 必须配置构建记录和归档产物保留策略,避免历史 release 包长期堆积。
统一源码版本参数
所有构建流水线、发布流水线和 Genarrative-Full-Build-And-Deploy 都必须支持以下参数:
SOURCE_BRANCH:源码分支,默认master,代表origin/master最新提交。COMMIT_HASH:可选 Git commit hash,留空时使用origin/<SOURCE_BRANCH>最新 commit;填写时必须是 7 到 40 位十六进制 hash,并且该 commit 必须属于origin/<SOURCE_BRANCH>。DEPLOY_TARGET:逻辑部署目标选择参数。发布流水线和Genarrative-Full-Build-And-Deploy必填;构建流水线仅在PUBLISH_AFTER_BUILD=true时用于触发下游发布。
执行规则:
- 流水线先按 Jenkins SCM 配置 checkout 仓库,再执行
git fetch --tags --prune origin "+refs/heads/<SOURCE_BRANCH>:refs/remotes/origin/<SOURCE_BRANCH>"。 - 如果工作区是浅克隆,流水线必须尝试
git fetch --unshallow --tags,确保能验证目标 commit 与分支关系。 COMMIT_HASH为空时,detached checkout 到refs/remotes/origin/<SOURCE_BRANCH>当前最新 commit。COMMIT_HASH非空时,先解析到完整 commit,再用git merge-base --is-ancestor <commit> refs/remotes/origin/<SOURCE_BRANCH>校验该提交属于指定分支,校验通过后 detached checkout。- 流水线日志必须输出最终
SOURCE_BRANCH与实际SOURCE_COMMIT。 - 构建产物必须写入
release-manifest.json,至少包含version、source_branch、source_commit、built_at和组件类型,供发布、回滚和审计使用。
构建流水线使用上述参数决定实际构建源码。发布流水线也暴露同名参数,但只用于选择本次发布使用的部署脚本、配置模板和 smoke test 逻辑;被发布的应用文件仍必须来自 Jenkins 归档产物或指定 release 包,不允许在发布流水线中重新构建。
当构建流水线以 PUBLISH_AFTER_BUILD=true 触发下游发布流水线时,必须把 SOURCE_BRANCH 和实际解析出的 SOURCE_COMMIT 作为下游 COMMIT_HASH 传递,确保部署逻辑和刚生成的产物可追溯到同一源码版本。
构建流水线支持参数 PUBLISH_AFTER_BUILD:
false:只构建并归档产物。true:构建成功后触发对应发布流水线。
发布流水线必须从归档产物获取文件,不依赖构建 workspace 的本地状态。
流水线职责
Genarrative-Server-Provision
用于生产服务器一次性或低频配置:
- 创建
spacetimedb、genarrative等系统用户。 - 创建
/stdb、/opt/genarrative、/srv/genarrative、/etc/genarrative、/var/lib/genarrative/maintenance。 - 安装或更新 SpacetimeDB。
- 安装 systemd unit。
- 安装 Nginx 配置和维护模式 snippet。
- 执行
nginx -t。 - 启用并启动
spacetimedb.service与genarrative-api.service。
该流水线属于高风险操作,默认要求人工确认后执行。
已落地的 Jenkinsfile 为 jenkins/Jenkinsfile.production-server-provision。该流水线默认 DRY_RUN=true,只打印将执行的初始化动作;真正写入系统用户、目录、systemd、Nginx 配置并启动服务时,必须设置 DRY_RUN=false 且勾选 CONFIRM_PROVISION。当 DEPLOY_TARGET=release 时,还必须勾选 CONFIRM_RELEASE_DEPLOY_AGENT,并通过 linux && genarrative-release-deploy 调度到独立 release 部署 agent。
Web Build / Deploy
构建:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 目标源码,默认构建origin/master最新 commit。 - 构建主站静态文件。
- 构建后台前端,base path 为
/admin/。 - 生成或复制
maintenance.html。 - 将
web/打包为web.tar.gz,生成web.tar.gz.sha256。 - 归档
web.tar.gz、web.tar.gz.sha256和release-manifest.json;web/展开目录不作为 Jenkins 主归档对象。
发布:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 部署脚本源码,默认使用origin/master最新 commit;上游构建触发时使用上游传入的实际构建 commit。 - 获取
web.tar.gz与web.tar.gz.sha256,先校验 checksum,再解压到/opt/genarrative/releases/<version>/web。 - 更新
/opt/genarrative/current与/srv/genarrative/web指向。 - 执行 Nginx 配置测试和静态页面 smoke test。
- 不进入维护模式。
Api Build / Deploy
构建:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 目标源码,默认构建origin/master最新 commit。 - 编译 Rust
api-server。 - 归档单一可执行文件、必要运行说明和
release-manifest.json。
发布:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 部署脚本源码,默认使用origin/master最新 commit;上游构建触发时使用上游传入的实际构建 commit。 - 进入维护模式。
- 解包到
/opt/genarrative/releases/<version>/api-server。 - 更新
/opt/genarrative/current。 - 重启
genarrative-api.service。 - 检查本机
/healthz。 - 导出产物归档成功后解除维护模式。
- 失败时保留维护模式并发邮件。
Stdb Module Build / Publish
构建:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 目标源码,默认构建origin/master最新 commit。 - 使用
spacetime build构建spacetime_module.wasm。 - 归档 wasm、发布脚本和
release-manifest.json。
发布:
- 先按
SOURCE_BRANCH/COMMIT_HASH解析并 checkout 发布脚本源码,默认使用origin/master最新 commit;上游构建触发时使用上游传入的实际构建 commit。 - 进入维护模式。
- 将 wasm 上传到生产实例。
- 在生产实例本机执行
spacetime publish -s local --bin-path spacetime_module.wasm <database-name>。 - 成功后执行必要 smoke test。
- 成功后解除维护模式。
- 失败时保留维护模式并发邮件。
Full Build-And-Deploy
- 先解析一次最终
SOURCE_COMMIT,所有下游构建和发布都使用同一个分支与 commit。 - 并行执行 Web / API / Stdb 三条构建流水线。
- 构建全部成功后,按顺序执行 Stdb publish、API deploy、Web deploy,并把同一个
DEPLOY_TARGET透传给三条发布流水线。 - 每条下游构建都只消费自己的归档产物,不直接复用别的 workspace。
- 生产 Web 发布只处理
web.tar.gz与 checksum,API 发布只处理api-server与 checksum,Stdb 发布只处理spacetime_module.wasm与 checksum。
数据库导出与导入
导出
Genarrative-Database-Export 用于人工导出生产数据:
- 已落地 Jenkinsfile:
jenkins/Jenkinsfile.production-database-export。 - 通过
DEPLOY_TARGET选择逻辑导出目标;development映射到linux && genarrative-build,release映射到linux && genarrative-release-deploy。 release导出必须勾选CONFIRM_RELEASE_DEPLOY_AGENT,避免当前开发/构建/开发部署 agent 冒充 release 部署机。- 进入维护模式,避免导出期间继续写入。
- 从目标机器本机 SpacetimeDB 导出指定数据库数据,默认连接
SPACETIME_SERVER=local,自托管root-dir默认/stdb。 - 产物归档到 Jenkins,并可额外保存到
SERVER_BACKUP_DIRECTORY。 - 敏感 token 与 bootstrap secret 只通过 Jenkins Secret Text 凭据 ID 注入,不作为明文 Job 参数。
- 成功后解除维护模式。
- 失败时保留维护模式并邮件通知。
导入
Genarrative-Database-Import 用于人工导入或恢复数据:
- 已落地 Jenkinsfile:
jenkins/Jenkinsfile.production-database-import。 - 通过
DEPLOY_TARGET选择逻辑导入目标;development映射到linux && genarrative-build,release映射到linux && genarrative-release-deploy。 release导入必须勾选CONFIRM_RELEASE_DEPLOY_AGENT,避免当前开发/构建/开发部署 agent 冒充 release 部署机。- 通过
INPUT_SOURCE选择数据源,pipeline_archive从Genarrative-Database-Export归档复制INPUT_FILE,manual_upload使用本次构建上传的MANUAL_INPUT_FILE;两种方式互斥,Prepare阶段会直接拦截混填。 DRY_RUN默认开启;真正写入数据时必须勾选CONFIRM_IMPORT,并让CONFIRM_DATABASE与CONFIRM_INPUT_FILE分别完全匹配DATABASE与实际输入文件。REPLACE_EXISTING=true且DRY_RUN=false时必须额外勾选CONFIRM_REPLACE_EXISTING。- 进入维护模式。
- 导入前先生成一次安全备份。
- 执行导入。
- 执行数据校验和服务 smoke test。
- 成功后解除维护模式。
- 失败时保留维护模式并邮件通知。
pipeline_archive模式默认使用导出流水线Genarrative-Database-Export;只需要填写EXPORT_BUILD_NUMBER_TO_IMPORT时,归档输入路径自动解析为database-exports/spacetime-migration-<导出构建号>.json。如果导出时覆盖过WORKSPACE_EXPORT_DIRECTORY或EXPORT_NAME,再显式填写归档内相对路径INPUT_FILE。manual_upload模式需要上传MANUAL_INPUT_FILE,并在CONFIRM_INPUT_FILE中填写原始文件名;此模式不再填写EXPORT_BUILD_NUMBER_TO_IMPORT或INPUT_FILE,EXPORT_JOB_NAME的默认值会被忽略。- 敏感 token 与 bootstrap secret 只通过 Jenkins Secret Text 凭据 ID 注入,不作为明文 Job 参数。
数据库表结构变更必须同步检查并更新 migration.rs,不能只发布 wasm。
全量构建并发布
Genarrative-Full-Build-And-Deploy 编排:
- 按
SOURCE_BRANCH/COMMIT_HASH解析一次最终SOURCE_COMMIT,默认origin/master最新 commit。 - 并行触发
Genarrative-Web-Build、Genarrative-Api-Build、Genarrative-Stdb-Module-Build,三条构建都必须使用同一个SOURCE_BRANCH和SOURCE_COMMIT。 - 三条构建全部成功后,按顺序触发
Genarrative-Stdb-Module-Publish、Genarrative-Api-Deploy、Genarrative-Web-Deploy,同样继续透传同一个SOURCE_BRANCH、SOURCE_COMMIT和DEPLOY_TARGET。 - 最后执行生产 smoke test。
网站最后发布,避免后台或主站提前指向尚未完成发布的后端能力。
这种编排能够在不牺牲版本一致性的前提下缩短总耗时,同时避免 Web / API / Stdb 彼此等待构建资源。并行构建时仍要保证每条构建流水线独立归档自己的产物,发布阶段只能消费归档结果,不能回到构建 workspace 重新取文件。
Genarrative-Full-Build-And-Deploy 额外作为定时任务运行,Jenkins 在每天凌晨 4 点自动触发一次,默认按 SOURCE_BRANCH=master 解析最新提交,并以 DEPLOY_TARGET=development 把全量构建结果部署到开发机。该定时任务不改写手动触发参数语义,只是给主线全量发布补一个固定的夜间全量刷新入口。
回滚
- 网站回滚:将
/srv/genarrative/web或/opt/genarrative/current切回上一版本并 reload Nginx。 api-server回滚:将/opt/genarrative/current切回上一版本并重启genarrative-api.service。- SpacetimeDB 模块回滚:发布上一版本
spacetime_module.wasm。 - 数据回滚:使用导入流水线恢复指定备份,必须进入维护模式。
待落地文件
后续工程落地时需要新增或改造:
deploy/systemd/spacetimedb.servicedeploy/systemd/genarrative-api.servicedeploy/nginx/genarrative.confdeploy/nginx/snippets/genarrative-maintenance.confdeploy/env/api-server.env.examplescripts/deploy/maintenance-on.shscripts/deploy/maintenance-off.shscripts/deploy/maintenance-status.shscripts/build-production-release.shscripts/jenkins-checkout-source.shscripts/deploy/production-web-deploy.shscripts/deploy/production-api-deploy.shscripts/deploy/production-stdb-publish.shjenkins/Jenkinsfile.production-web-buildjenkins/Jenkinsfile.production-web-deployjenkins/Jenkinsfile.production-api-buildjenkins/Jenkinsfile.production-api-deployjenkins/Jenkinsfile.production-stdb-module-buildjenkins/Jenkinsfile.production-stdb-module-publishjenkins/Jenkinsfile.production-full-build-and-deployjenkins/Jenkinsfile.production-server-provision- 删除旧 Jenkinsfile:
Jenkinsfile.build-and-deploy、Jenkinsfile.deploy、Jenkinsfile.database-export、Jenkinsfile.database-import - 更新旧部署文档,标记旧一体化脚本为废弃或迁移对象。
jenkins/Jenkinsfile.production-database-exportjenkins/Jenkinsfile.production-database-import
参考
- SpacetimeDB 官方自托管文档:https://spacetimedb.com/docs/how-to/deploy/self-hosting/
- 该文档建议 Ubuntu 24.04、
spacetimedb专用用户、/stdbroot-dir、systemd 托管,以及 Nginx/HTTPS。 - 默认公网路由只开放 TypeScript SDK 必需的
/v1/identity与/v1/database/<database>/subscribe,其他发布、SQL、管理类入口保持本机可用。
- 该文档建议 Ubuntu 24.04、