283 lines
12 KiB
Markdown
283 lines
12 KiB
Markdown
# V3.1 Schema 迁移清单
|
||
|
||
> 生成自 `init_v3.sql` → `schema.v31.prisma`(已通过 `prisma validate`)
|
||
> 旧版备份:`schema.legacy-v21.prisma`(当前运行中的 `schema.prisma`)
|
||
|
||
## 激活步骤(P0)
|
||
|
||
```bash
|
||
cd server/dukang-api
|
||
# 1. 备份并切换 schema
|
||
cp prisma/schema.prisma prisma/schema.legacy-v21.prisma # 若尚未备份
|
||
cp prisma/schema.v31.prisma prisma/schema.prisma
|
||
|
||
# 2. 开发库建议删库重建
|
||
mysql -u root -p -e "DROP DATABASE IF EXISTS dukang_haoke; CREATE DATABASE dukang_haoke ..."
|
||
# 或:mysql < prisma/init_v3.sql
|
||
|
||
# 3. 生成 Client
|
||
pnpm db:generate
|
||
npx prisma db push # 或 prisma migrate dev --name v31_init
|
||
|
||
# 4. 新 seed(待编写 seed-v31.ts)
|
||
pnpm prisma:seed
|
||
```
|
||
|
||
---
|
||
|
||
## 表对照(27 张 v3.1)
|
||
|
||
| v3.1 物理表 | Prisma Model | 旧表/Model | 变化 |
|
||
|-------------|--------------|------------|------|
|
||
| `common_wx_app_config` | `CommonWxAppConfig` | `wx_app_configs` / `WxAppConfig` | 重命名 |
|
||
| `common_resource` | `CommonResource` | — | **新增**(替代 `store_media`、裸 URL) |
|
||
| `common_event` | `CommonEvent` | `benefit_ledgers`, `order_status_logs`, `store_audits`, `event_logs`, `operation_logs` | **合并** |
|
||
| `common_ticket` | `CommonTicket` | `after_sale_tickets`, `refunds`, `delivery_intercepts`, `alerts` | **合并** |
|
||
| `common_product_item` | `CommonProductItem` | `products` / `Product` | 重命名 + `cover_resource_id` |
|
||
| `common_store_category` | `CommonStoreCategory` | `store_categories` / `StoreCategory` | 重命名 |
|
||
| `common_promo_code` | `CommonPromoCode` | `promo_codes` / `PromoCode` | 重命名 + `qrcode_resource_id` |
|
||
| `common_city` | `CommonCity` | `cities` / `City` | 重命名 |
|
||
| `common_city_commission_rule` | `CommonCityCommissionRule` | `city_commission_rules` | 重命名 |
|
||
| `partner_partner` | `Partner` | `partners` | 重命名 + 合同字段内联 |
|
||
| `partner_account` | `PartnerAccount` | `partner_accounts` | 重命名 |
|
||
| `partner_bill` | `PartnerBill` | `partner_bills` | 状态枚举精简 |
|
||
| `hq_account` | `HqAccount` | `hq_accounts` | 重命名 |
|
||
| `user_user` | `User` | `users` | 重命名;`phone` 可空;含 `deviceKey`/合并字段 |
|
||
| `user_address` | `UserAddress` | `user_addresses` | 重命名 |
|
||
| `user_city_preference` | `UserCityPreference` | `user_city_preferences` | 重命名 |
|
||
| `user_promo_attribution` | `UserPromoAttribution` | `user_promo_attributions` | 重命名 |
|
||
| `store_store` | `Store` | `stores` | `cover_url` → `cover_resource_id` |
|
||
| `store_account` | `StoreAccount` | `store_accounts` | 重命名 |
|
||
| `user_order` | `Order` | `orders` | **无 order_items**;商品快照内嵌 |
|
||
| `user_order_delivery` | `OrderDelivery` | `order_deliveries` | 重命名 + `sign_photo_resource_id` |
|
||
| `user_benefit_coupon` | `BenefitCoupon` | `benefit_coupons` | 重命名 |
|
||
| `user_redeem_record` | `RedeemRecord` | `redeem_records` | 重命名 |
|
||
| `user_store_rating` | `StoreRating` | `store_ratings` | 重命名 |
|
||
| `store_payout` | `StorePayout` | `store_payouts` | 重命名 |
|
||
| `log_third_party` | `LogThirdParty` | `payments`, `sms_logs` | **合并** |
|
||
| `log_user_analytics` | `LogUserAnalytics` | `event_logs`(埋点部分) | **拆分** |
|
||
|
||
### 删除的表(v3.1 不再存在)
|
||
|
||
| 旧表 | 替代方案 |
|
||
|------|----------|
|
||
| `store_media` | `common_resource`(`owner_type=STORE`) |
|
||
| `partner_contracts` | `partner_partner.contract_*` + `common_resource` CONTRACT |
|
||
| `order_items` | `user_order` 内嵌快照字段 |
|
||
| `order_status_logs` | `common_event(ORDER_STATUS)` |
|
||
| `payments` | `log_third_party` + `user_order.pay_*` |
|
||
| `refunds` | `common_ticket(REFUND)` |
|
||
| `delivery_intercepts` | `common_ticket(ALERT)` 或 RESHIPMENT |
|
||
| `benefit_ledgers` | `common_event(BENEFIT_LEDGER)` |
|
||
| `redeem_tokens` | **仅 Redis** |
|
||
| `order_commissions` | `partner_bill` 汇总(无明细表) |
|
||
| `partner_withdrawals` | 手册 v3.1 未包含(后续按需) |
|
||
| `store_audits` | `common_event(STORE_AUDIT)` |
|
||
| `after_sale_tickets` | `common_ticket` |
|
||
| `alerts` | `common_ticket(ALERT)` |
|
||
| `operation_logs` | `common_event(HQ_OPERATION)` |
|
||
| `event_logs` | `common_event` + `log_user_analytics` |
|
||
|
||
### preV1 扩展字段(已并入 v3.1)
|
||
|
||
| 字段 | 表 | 说明 |
|
||
|------|-----|------|
|
||
| `device_key` / `phone_verified_at` / `merged_into_user_id` | `user_user` | 访客 JWT + 验机 + 账号合并 |
|
||
| `client_ip` / `ip_*` / `gps_*` | `user_order` | 下单位置快照 |
|
||
|
||
~~以下字段在切换后丢失~~ → **已保留**
|
||
|
||
---
|
||
|
||
## Prisma Client 调用变更速查
|
||
|
||
| 旧调用 | v3.1 调用 |
|
||
|--------|-----------|
|
||
| `prisma.product` | `prisma.commonProductItem` |
|
||
| `prisma.city` | `prisma.commonCity` |
|
||
| `prisma.cityCommissionRule` | `prisma.commonCityCommissionRule` |
|
||
| `prisma.storeCategory` | `prisma.commonStoreCategory` |
|
||
| `prisma.promoCode` | `prisma.commonPromoCode` |
|
||
| `prisma.orderDelivery` | `prisma.orderDelivery`(表名变 `user_order_delivery`) |
|
||
| `prisma.benefitCoupon` | `prisma.benefitCoupon`(表 `user_benefit_coupon`) |
|
||
| `prisma.benefitLedger` | `prisma.commonEvent`(`eventType=BENEFIT_LEDGER`) |
|
||
| `prisma.redeemToken` | **删除**,改 Redis |
|
||
| `prisma.storeMedia` | `prisma.commonResource` |
|
||
| `prisma.storeAudit` | `prisma.commonEvent`(`eventType=STORE_AUDIT`) |
|
||
| `prisma.payment` | `prisma.logThirdParty` |
|
||
| `prisma.orderStatusLog` | `prisma.commonEvent`(`eventType=ORDER_STATUS`) |
|
||
| `prisma.orderItem` | **删除**,读写 `order` 快照字段 |
|
||
|
||
> `Partner`、`Store`、`User`、`Order` 等 Model 名保留,仅 `@@map` 物理表名变化。
|
||
|
||
---
|
||
|
||
## 后端模块影响面
|
||
|
||
### P0 — 基础设施
|
||
|
||
| 路径 | 影响 | 工作量 |
|
||
|------|------|--------|
|
||
| `prisma/schema.prisma` | 已切换为 v3.1 | ✅ |
|
||
| `prisma/schema.v31.prisma` | 与 `schema.prisma` 同步源 | ✅ |
|
||
| `prisma/seed-prev1.ts` | 保留为 `seed-legacy`;主 seed 为 `seed-v31.ts` | ✅ |
|
||
| `prisma/sync-benefit-to-price.ts` | `product` → `commonProductItem` | 低 |
|
||
| `packages/shared-types` | `ClientApp` 去掉 `USER_H5` 等;新增 Resource/Event 枚举 | 中 |
|
||
|
||
### P1 — common 模块(新建)
|
||
|
||
| 路径 | 说明 |
|
||
|------|------|
|
||
| `src/modules/common/common.module.ts` | **新建** |
|
||
| `src/modules/common/resource.service.ts` | OSS 凭证、登记、CRUD |
|
||
| `src/modules/common/resource.controller.ts` | `/common/resources/*` |
|
||
| `src/modules/common/event.service.ts` | 事件写入/查询/时间线 |
|
||
| `src/modules/common/ticket.service.ts` | 工单 CRUD |
|
||
|
||
### P2 — IAM
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/iam/auth.service.ts` | 去掉访客 `deviceKey` 流程;`user.phone` 必填;`prisma.user` 字段变更 |
|
||
| `modules/iam/user-address.service.ts` | 表名映射,逻辑基本不变 |
|
||
| `common/guards/phone-verified.guard.ts` | 适配新 User 模型 |
|
||
| `common/guards/super-admin.guard.ts` | 无大变 |
|
||
|
||
### P3 — catalog
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/catalog/catalog.service.ts` | `city`→`commonCity`,`product`→`commonProductItem`;返回 `coverResource.url` |
|
||
|
||
### P4 — trade(改动最大)
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/trade/trade.service.ts` | 下单写 `user_order` 快照(无 `orderItem`);支付写 `log_third_party`;状态变更写 `common_event`;去掉 IP/GPS 字段或扩展 |
|
||
| `integrations/pay/*` | 回调改查 `log_third_party` |
|
||
| `jobs/*`(配送 Mock) | `orderDelivery` 字段对齐 |
|
||
|
||
### P5 — benefit
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/benefit/benefit.service.ts` | 发券逻辑保留;流水从 `benefitLedger.create` → `commonEvent.create(BENEFIT_LEDGER)`;读明细改查 `commonEvent` |
|
||
|
||
### P6 — redeem
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/redeem/redeem.service.ts` | **删除** `redeemToken` DB 写入,仅 Redis;`cityCommissionRule`→`commonCityCommissionRule` |
|
||
|
||
### P7 — store
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/store/store.service.ts` | `storeAudit`→`commonEvent`;封面改 `coverResourceId`;`city`→`commonCity` |
|
||
|
||
### P8 — settlement
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/settlement/settlement.service.ts` | `partnerBill` 状态枚举变更;去掉 `orderCommission` 明细 |
|
||
|
||
### P9 — analytics
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/analytics/analytics.service.ts` | `eventLog`→`logUserAnalytics` |
|
||
|
||
### P10 — ops(HQ 后台)
|
||
|
||
| 路径 | 关键改动 |
|
||
|------|----------|
|
||
| `modules/ops/admin-stores.service.ts` | `storeMedia`→`commonResource`;`coverUrl`→`coverResourceId`;`city`→`commonCity` |
|
||
| `modules/ops/admin-benefit.service.ts` | 流水列表改查 `commonEvent` |
|
||
| `modules/ops/admin-orders.service.ts` | 订单含内嵌商品快照;无 `items` include |
|
||
| `modules/ops/admin-dashboard.service.ts` | 统计字段:去掉 guest/merged 用户计数 |
|
||
| `modules/ops/admin-cities.service.ts` | `city`→`commonCity` |
|
||
| `modules/ops/admin-partners.service.ts` | 订单关联 `city.partnerId` 不变 |
|
||
| `modules/ops/admin-redeem.service.ts` | 表名映射 |
|
||
| `modules/ops/admin-users.service.ts` | 去掉 merged/guest 相关 |
|
||
| `admin-stores.controller.ts` | `/admin/store-media` → `/admin/resources` 或复用 common API |
|
||
|
||
---
|
||
|
||
## 前端影响面
|
||
|
||
| 应用 | 影响 |
|
||
|------|------|
|
||
| `apps/h5-user` | 登录流(phone 必填);商品图 URL 来源;订单详情无 items 数组 |
|
||
| `apps/h5-shop` | 门店详情封面 URL |
|
||
| `apps/h5-partner` | 录店上传走 `/common/resources` |
|
||
| `apps/admin-web` | 门店资源页改 `common_resource`;权益流水改 event;订单详情结构调整 |
|
||
| `packages/shared-types` | 枚举与 DTO 同步 |
|
||
|
||
---
|
||
|
||
## P1 进度(common 模块)
|
||
|
||
| 项 | 状态 |
|
||
|----|------|
|
||
| `modules/common/` Resource/Event/Ticket/ThirdPartyLog | ✅ |
|
||
| `common/event/event.helpers.ts` 权益/订单事件 | ✅ |
|
||
| 业务层改用 `commonEvent` / `commonResource` / `logThirdParty` | ✅ |
|
||
| `pnpm run build` | ✅ |
|
||
|
||
## P2–P6 进度(业务层 + 兼容层 + 后台)
|
||
|
||
| 项 | 状态 |
|
||
|----|------|
|
||
| P2 IAM + catalog 适配 v3.1 | ✅ |
|
||
| P3 trade + benefit(下单/发券/支付日志/事件) | ✅ |
|
||
| P4 redeem + store(Redis token + 封面资源) | ✅ |
|
||
| P5 ops 后台(订单/门店/权益/城市/合伙人) | ✅ |
|
||
| P6 兼容层 `v31-compat.ts`(订单 items、门店 coverUrl、流水/状态日志) | ✅ |
|
||
| `admin/products` CRUD + HQ 商品页 | ✅ |
|
||
| `sync-benefit-to-price.ts` → `commonProductItem` | ✅ |
|
||
| `schema.prisma` ↔ `schema.v31.prisma` 同步 | ✅ |
|
||
| smoke 脚本 `scripts/smoke-prev1.mjs` | ✅ |
|
||
|
||
### 新增 HQ API
|
||
|
||
| 路径 | 说明 |
|
||
|------|------|
|
||
| `GET/POST /admin/products` | 商品列表/新建 |
|
||
| `GET/PUT /admin/products/:id` | 商品详情/更新 |
|
||
|
||
### 新增 API(`/api/v1/common/*`)
|
||
|
||
| 路径 | 说明 |
|
||
|------|------|
|
||
| `POST /common/resources/upload-token` | Mock OSS 直传凭证 |
|
||
| `POST/GET/PUT/DELETE /common/resources` | 资源 CRUD |
|
||
| `POST/GET /common/events` | 事件写入/查询 |
|
||
| `GET /common/events/timeline` | 时间线 |
|
||
| `POST/GET/PUT /common/tickets` | 工单 |
|
||
| `GET /common/third-party-logs` | HQ 只读支付/第三方日志 |
|
||
|
||
## 建议实施顺序
|
||
|
||
```
|
||
P0 schema 切换 + seed-v31
|
||
→ P1 common 模块(resource + event)
|
||
→ P2 IAM + catalog(可登录、可看商品)
|
||
→ P3 trade + benefit(可下单发券)
|
||
→ P4 redeem + store(可核销)
|
||
→ P5 ops 后台 + settlement
|
||
→ P6 前端对齐 + smoke
|
||
```
|
||
|
||
**冻结规则**:P0~P1 期间不新增业务功能,只修迁移阻塞项。
|
||
|
||
---
|
||
|
||
## 文件索引
|
||
|
||
| 文件 | 说明 |
|
||
|------|------|
|
||
| `prisma/init_v3.sql` | DDL 源 |
|
||
| `prisma/schema.v31.prisma` | **新生成**,待激活 |
|
||
| `prisma/schema.legacy-v21.prisma` | 旧版备份 |
|
||
| `prisma/schema.prisma` | 当前运行版(**v3.1 已激活**) |
|