# BD_Manual：dim_groupbuy_package_ex 新增团购详情字段

> 日期：2026-03-05
> 涉及库：`etl_feiqiu` / `test_etl_feiqiu`
> 迁移脚本：`db/etl_feiqiu/migrations/2026-03-05__add_detail_fields_to_dim_groupbuy_package_ex.sql`
> 直接原因：整合团购详情接口（QueryPackageCouponInfo），需在 DWD 扩展表中存储可用台区、助教服务、关联门店等维度信息
> Prompt 摘要：etl-coupon-detail spec — 需求 4 验收标准 1

---

## 1. 变更说明

### 变更内容

在 `dwd.dim_groupbuy_package_ex` 表新增 4 个 JSONB 列，用于存储从团购详情接口提取的维度数据。

| Schema | 表 | 新增列 | 类型 | 说明 |
|--------|-----|--------|------|------|
| dwd | dim_groupbuy_package_ex | table_area_ids | JSONB | 可用台区 ID 列表（来自详情接口 tableAreaId） |
| dwd | dim_groupbuy_package_ex | table_area_names | JSONB | 可用台区名称列表（来自详情接口 tableAreaNameList） |
| dwd | dim_groupbuy_package_ex | assistant_services | JSONB | 助教服务关联（来自详情接口 packageCouponAssistants） |
| dwd | dim_groupbuy_package_ex | groupon_site_infos | JSONB | 关联门店信息（来自详情接口 grouponSiteInfos） |

所有列均为 NULLABLE，使用 `ADD COLUMN IF NOT EXISTS` 确保幂等性。

### 数据来源

ODS 层 `ods.group_buy_package_details` 表（由 `ODS_GROUP_PACKAGE` 任务的详情拉取子流程写入），通过 `coupon_id = groupbuy_package_id` 关联后在 DWD 加载时合并。

---

## 2. 兼容性影响

| 组件 | 影响 | 说明 |
|------|------|------|
| ETL DWD 加载 | 需配合修改 | `dwd_load_task.py` 需新增 LEFT JOIN 逻辑从 ODS 详情表读取并映射到这 4 个字段（Task 4.2/4.3） |
| ETL SCD2 | 自动兼容 | 新增 JSONB 字段自动纳入 `_is_row_changed` 变更检测 |
| 后端 API | 无影响 | 当前无接口直接查询 dim_groupbuy_package_ex 的详情字段 |
| 小程序 | 无影响 | 不直接使用 DWD 层表 |
| RLS 视图 | 无影响 | dim_groupbuy_package_ex 无 RLS 视图 |

---

## 3. 回滚策略

```sql
ALTER TABLE dwd.dim_groupbuy_package_ex
    DROP COLUMN IF EXISTS table_area_ids,
    DROP COLUMN IF EXISTS table_area_names,
    DROP COLUMN IF EXISTS assistant_services,
    DROP COLUMN IF EXISTS groupon_site_infos;
```

回滚后需同步撤销 `dwd_load_task.py` 中对应的 LEFT JOIN 和字段映射逻辑。

---

## 4. 验证 SQL

```sql
-- 1. 确认 4 个新列存在且类型正确
SELECT column_name, data_type, is_nullable
  FROM information_schema.columns
 WHERE table_schema = 'dwd'
   AND table_name = 'dim_groupbuy_package_ex'
   AND column_name IN ('table_area_ids', 'table_area_names', 'assistant_services', 'groupon_site_infos')
 ORDER BY ordinal_position;
-- 预期：4 行，data_type 均为 'jsonb'，is_nullable 均为 'YES'

-- 2. 确认列 COMMENT 已写入
SELECT a.attname AS column_name, d.description AS comment
  FROM pg_catalog.pg_attribute a
  JOIN pg_catalog.pg_class c ON a.attrelid = c.oid
  JOIN pg_catalog.pg_namespace n ON c.relnamespace = n.oid
  LEFT JOIN pg_catalog.pg_description d ON d.objoid = c.oid AND d.objsubid = a.attnum
 WHERE n.nspname = 'dwd'
   AND c.relname = 'dim_groupbuy_package_ex'
   AND a.attname IN ('table_area_ids', 'table_area_names', 'assistant_services', 'groupon_site_infos')
 ORDER BY a.attnum;
-- 预期：4 行，每行 comment 非 NULL

-- 3. 确认表主键和索引未受影响
SELECT indexname, indexdef
  FROM pg_indexes
 WHERE schemaname = 'dwd'
   AND tablename = 'dim_groupbuy_package_ex';
-- 预期：原有 4 个索引不变（pkey + 3 个辅助索引）
```
