|
|
2 months ago | |
|---|---|---|
| .. | ||
| 2026-07-31-factory-to-brand-batch.sql | 2 months ago | |
| 2026-07-31-product-serialcursor.sql | 2 months ago | |
| 2026-07-31-solution-provider-vendor.sql | 2 months ago | |
| 2026-08-08-channel-dimension.sql | 2 months ago | |
| 2026-08-11-region-cn-hw.sql | 2 months ago | |
| 2026-08-18-product-provider.sql | 2 months ago | |
| README.md | 2 months ago | |
README.md
数据迁移脚本
老结构(厂家/出货单/授权码)→ 新结构(品牌商/生产批次/带 batchno 的授权码)的一次性迁移。
只对应用主库(starpivot)执行,按文件名日期顺序跑。两个脚本都用事务包裹、幂等可重复执行。
执行顺序
# 0) 先备份(必做)
docker exec postgres pg_dump -U starpivot -d starpivot --no-owner --no-privileges -f /tmp/pre.sql
docker cp postgres:/tmp/pre.sql ./starpivot-premigrate-$(date +%Y%m%d-%H%M).sql
# 1) 主迁移
docker cp 2026-07-31-factory-to-brand-batch.sql postgres:/tmp/m1.sql
docker exec postgres psql -U starpivot -d starpivot -v ON_ERROR_STOP=1 -f /tmp/m1.sql
# 2) 补 product.serialcursor(新代码 allocSerialRange 依赖,缺了生产授权码直接报错)
docker cp 2026-07-31-product-serialcursor.sql postgres:/tmp/m2.sql
docker exec postgres psql -U starpivot -d starpivot -v ON_ERROR_STOP=1 -f /tmp/m2.sql
# 3) 方案商改手工 ID + 厂商分组,并按 factoryflag 回填品牌商归属
docker cp 2026-07-31-solution-provider-vendor.sql postgres:/tmp/m3.sql
docker exec postgres psql -U starpivot -d starpivot -v ON_ERROR_STOP=1 -f /tmp/m3.sql
# 4) 渠道商维度(2026-08-08):授权码/批次/用户设备加 channelid,
# stats_global_day 把 channel_id 并进复合主键
# ⚠️ 执行前先停 console(stats_global_day 的唯一写库方),执行后再起。
# 脚本 [A] 段跑 console 主库,[B] 段(默认注释)跑各应用业务库。
docker cp 2026-08-08-channel-dimension.sql postgres:/tmp/m4.sql
docker exec postgres psql -U starpivot -d starpivot -v ON_ERROR_STOP=1 -f /tmp/m4.sql
# 5) 区域二值化(2026-08-11):app_registry.region 与 console_account.regions 统一成 cn/hw,
# 对应后台「应用切换按应用去重、区域只留 国内/海外」的改动。只跑 console 主库。
docker cp 2026-08-11-region-cn-hw.sql postgres:/tmp/m5.sql
docker exec postgres psql -U starpivot -d starpivot -v ON_ERROR_STOP=1 -f /tmp/m5.sql
想先看结果不落库:把脚本末尾的
COMMIT;改成ROLLBACK;跑一遍即可。
映射关系
| 老 | 新 | 说明 |
|---|---|---|
factory |
brand |
id 沿用,所以各表 factoryid 的值无需转换 |
factory.factoryflag |
brand.providerid |
它就是方案商 ID(十六进制:ABEF/ABF0~ABF4/AB21),解析成整数即可 |
factory.probatch |
— | 老批次计数器,新结构无对应字段,丢弃 |
factory_deliverynote |
production_batch |
并上授权码里实际存在的批次(见下) |
license_b*.factoryid |
.brandid |
新增列回填,老列保留作对照 |
license_b*.probatch |
.batchno |
6 位短码,字符集同 comm.GeneratePublicCode |
product.factoryid |
.brandid |
改列名 |
factory_public_code.factoryid |
.brandid |
改列名 |
| — | solution_provider |
按 factoryflag 的实际取值建 7 条,带 vendor 厂商分组(1=杰里 2=蓝汛 3=恒玄) |
老主表 license |
— | 不动。新代码只读分表 license_<pid十六进制> |
批次来源取并集:以各 license_b* 分表按 (productid, probatch) 聚合为主(保证每个授权码都挂得上批次),
出货单里有、授权码里没有的补进来;MAC 区间和生产时间用出货单回填。
production_batch.remark 里写了 probatch=<老批次号>,既是对账依据,也是脚本重跑时的幂等锚点。
已知的语义差异
老数据的 number 是批次内序号(每批都从 1 重新计数),而新代码的 number 是产品级全局序号,
由 product.serialcursor 累加分配。因此:
- 迁移后同一产品的多个批次,
serialstart/serialend会重叠(如都是 1~2),这是老数据本身的性质,无法反推出全局序号; - 脚本 2 把
serialcursor初始化为该产品现有max(number),新生产的批次序号会接在老数据之后,不会与历史重叠; - 授权码
code由license.GenerateV2生成,内部带随机种子,不依赖serial唯一,所以老数据number重复不会造成主键冲突。
方案商 ID 规则(重要)
solution_provider.id 是手工指定的有含义编码,不自增(列上的序列默认值已 DROP):十六进制看,
0xC101 = 杰里 01 方案、0xC102 = 杰里 02 方案。历史 ID(ABEF/ABF0~ABF4/AB21)
已烧录进设备、不可变更,只能保留;新增方案商一律用 C 开头段。
一个厂商可有多个方案,所以 vendor 分组(enum SolutionVendor)才是「三个方案商」那一层:
ABEF→杰里,ABF0~ABF3→蓝汛,ABF4→恒玄,AB21→未指定(慕然科技,待确认)。
因为 id 不自增,api_addsolutionprovider 会强制校验 id 非 0 且不重复——否则不传 id 会插成 0,第二条直接主键冲突。
2026-07-31 广州测试环境的执行结果
品牌商 25、方案商 7、生产批次 64(63 个来自授权码 + 1 个仅出货单登记)、
授权码 37,253 条全部回填 batchno(未填 0、孤儿 0、brandid 与 factoryid 不一致 0)。
25 个品牌商按 factoryflag 全部归属到方案商,未归属 0 个。