chore: add local development and build foundation
This commit is contained in:
parent
aaca47d825
commit
093f0ca14a
22
.gitea/workflows/build.yml
Normal file
22
.gitea/workflows/build.yml
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
name: build
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
branches: [main, develop, 'feature/**']
|
||||||
|
tags: ['v*']
|
||||||
|
pull_request:
|
||||||
|
branches: [main, develop]
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- uses: actions/checkout@v4
|
||||||
|
- uses: actions/setup-node@v4
|
||||||
|
with:
|
||||||
|
node-version: '22.22.0'
|
||||||
|
- run: node --version
|
||||||
|
- run: node scripts/check-migrations.mjs
|
||||||
|
- uses: actions/upload-artifact@v3
|
||||||
|
with:
|
||||||
|
name: migrations-${{ github.sha }}
|
||||||
|
path: "*.up.sql"
|
||||||
|
if-no-files-found: error
|
||||||
7
README.md
Normal file
7
README.md
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
# 数据库迁移
|
||||||
|
|
||||||
|
这些文件是历史增量,不是完整数据库。运行全部迁移前,必须导入经授权的脱敏基础结构,至少存在 `users.teacher`;其他业务表依赖私有 dbtable 模块,也需核对。不要用虚构的 users 表冒充完整初始化。
|
||||||
|
|
||||||
|
在上级工作区运行 `./scripts/workspace.ps1 migrate`,使用隔离的本地 MySQL 和 golang-migrate 记录版本。已有数据库须先核对 schema_migrations 与实际结构;禁止盲目 force。已执行的 SQL 不修改,新变更新增时间戳文件。
|
||||||
|
|
||||||
|
`node scripts/check-migrations.mjs` 仅检查命名、版本唯一性和非空。SQL 是否可执行须在脱敏基线数据库验证。现有迁移无 down 脚本,生产回退依赖经验证的备份恢复或补偿迁移,不自动回滚。
|
||||||
13
scripts/check-migrations.mjs
Normal file
13
scripts/check-migrations.mjs
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
import { readdirSync, readFileSync } from 'node:fs';
|
||||||
|
import assert from 'node:assert/strict';
|
||||||
|
const files = readdirSync('.').filter(f => f.endsWith('.sql')).sort();
|
||||||
|
assert(files.length > 0, 'No migrations');
|
||||||
|
const versions = new Set();
|
||||||
|
for (const file of files) {
|
||||||
|
const match = /^(\d+)_[a-z0-9_]+\.up\.sql$/.exec(file);
|
||||||
|
assert(match, `Invalid migration filename: ${file}`);
|
||||||
|
assert(!versions.has(match[1]), `Duplicate version: ${file}`);
|
||||||
|
versions.add(match[1]);
|
||||||
|
assert(readFileSync(file, 'utf8').trim(), `Empty migration: ${file}`);
|
||||||
|
}
|
||||||
|
console.log(`${files.length} migration files checked (structure only; MySQL execution still required).`);
|
||||||
Loading…
Reference in New Issue
Block a user