← 返回
未分类

数据建模架构师

驾驭维度建模、Data Vault 与湖仓一体三把利剑,让数据资产"活"起来。本技能覆盖 Kimball 维度建模(星型模型/SCD六种策略/事实表四类型)、Inmon CIF 企业信息工厂、Data Vault 2.0(Hub/Link/Satellite)、数据分层架构(ODS→DWD→DWS→ADS)、拉链表实战、指标管理体系(原子→派生→复合)、dbt 数据建模工作流与数据血缘分析。配备 PostgreSQL + Metabase + DataHub 实验环境、DDL 生成器、血缘分析引擎与 SCD 处理引擎。
庄子十八代技师
未分类 community v1.0.0 1 版本 100000 Key: 无需
★ 0
Stars
📥 52
下载
💾 0
安装
1
版本
#latest

概述

数据建模架构师

> 驾驭维度建模、Data Vault 与湖仓一体三把利剑——让数据资产"活"起来。

一、数据建模全景图

                            ┌──────────────────────────────┐
                            │      数据建模方法论矩阵        │
                            └──────────────┬───────────────┘
                                           │
         ┌──────────────┬─────────────────┼──────────────┬─────────────┐
         ▼              ▼                  ▼             ▼             ▼
    ┌─────────┐   ┌──────────┐      ┌──────────┐  ┌─────────┐  ┌──────────┐
    │ Kimball │   │  Inmon   │      │  Data    │  │  Anchor │  │  OneData │
    │ 维度建模 │   │ 企业信息 │      │  Vault   │  │  Modeling│  │  阿里    │
    │ 星型模型 │   │ 工厂 CIF │      │  数据金库 │  │  锚建模  │  │ 数据建模 │
    └────┬────┘   └────┬─────┘      └────┬─────┘  └────┬────┘  └────┬─────┘
         │              │                │             │            │
    ┌────┴──────────────┴────────────────┴─────────────┴────────────┘
    │                  数据分层架构(ODS → DWD → DWS → ADS)          │
    └────────────────────────────────────────────────────────────────┘

二、三大方法论速查

2.1 Kimball 维度建模(OLAP 首选)

             ┌─────────────┐
             │  dim_date   │
             │  日期维度    │
             └──────┬──────┘
                    │
    ┌───────────────┼───────────────┐
    │               │               │
┌───┴───────┐ ┌─────┴─────┐ ┌───────┴──────┐
│dim_store  │ │ fact_sales│ │ dim_product  │
│ 门店维度   │─│  销售事实  │─│  商品维度     │
└───────────┘ └─────┬─────┘ └──────────────┘
                    │
            ┌───────┴───────┐
            │               │
      ┌─────┴─────┐ ┌───────┴──────┐
      │dim_user   │ │ dim_channel  │
      │ 用户维度   │ │  渠道维度     │
      └───────────┘ └──────────────┘

核心原则:
  1. 事实表在中心,维度表围绕事实表(星型)
  2. 事实表:业务过程度量值 + 外键(数字、可加)
  3. 维度表:描述性属性(文本、层次)
  4. 维度退化到事实表(如订单号,直接放事实表)

2.2 Inmon CIF 企业信息工厂(数仓顶层设计)

┌─────────────────────────────────────────────────┐
│              Inmon CIF 架构                      │
├─────────────────────────────────────────────────┤
│                                                  │
│  数据源 → ODS → Staging → 3NF EDW → 数据集市      │
│  (各业务  (贴源)  (清洗)   (企业级    (部门级      │
│   系统)                   3范式仓库)  维度建模)    │
│                                                  │
│  关键特征:                                       │
│  · EDW 层严格 3NF,消除冗余                       │
│  · 数据集市层按部门做维度建模(星型)               │
│  · 自上而下设计,先建 EDW 再建 Mart               │
│  · 适合:大型企业,多部门,长期规划                │
└─────────────────────────────────────────────────┘

Kimball vs Inmon:

| 维度 | Kimball | Inmon |
|:---|:---|:---|
| **设计** | 自下而上(业务过程驱动) | 自上而下(企业全局驱动) |
| **中心** | 数据集市(星型模型) | 企业数据仓库(3NF) |
| **范式** | 维度建模(反范式) | 第三范式(规范化) |
| **速度** | 快速交付(周/月) | 长周期(月/年) |
| **耦合** | 业务过程紧耦合 | 数据松耦合 |
| **适合** | 快速迭代、敏捷团队 | 大型企业、合规要求高 |

2.3 Data Vault 2.0(敏捷数仓)

┌─────────────────────────────────────────────────┐
│          Data Vault 2.0 三件套                   │
├─────────────────────────────────────────────────┤
│                                                  │
│  Hub(业务实体核心键):                           │
│    ┌─────────────────┐                           │
│    │ Hub_Customer     │                           │
│    │ ─────────────── │                           │
│    │ customer_hash_key│  ← 业务主键的哈希         │
│    │ customer_id      │  ← 业务主键               │
│    │ load_date        │  ← 加载时间               │
│    │ record_source    │  ← 数据来源               │
│    └────────┬────────┘                           │
│             │                                    │
│    ┌────────┴────────┐                           │
│    │ Link_Cust_Order  │  ← 实体间关系             │
│    │ ─────────────── │                           │
│    │ link_hash_key    │                           │
│    │ customer_hash_key│                           │
│    │ order_hash_key   │                           │
│    │ load_date        │                           │
│    └────────┬────────┘                           │
│             │                                    │
│    ┌────────┴────────┐                           │
│    │ Sat_Customer     │  ← 描述性属性+时间线      │
│    │ ─────────────── │                           │
│    │ customer_hash_key│                           │
│    │ load_date        │                           │
│    │ customer_name    │                           │
│    │ email            │                           │
│    │ city             │                           │
│    └─────────────────┘                           │
│                                                  │
│  优势:                                           │
│  · 并行加载:Hub/Link/Sat 可独立写入              │
│  · 可审计:每条记录带 load_date + record_source   │
│  · 弹性扩展:新增数据源不破坏现有结构              │
│  · 历史追溯:Sat 自动保留全部历史版本              │
└─────────────────────────────────────────────────┘

三、数据分层架构设计

3.1 经典四层架构

┌─────────────────────────────────────────────────────────┐
│  ADS (Application Data Service)  应用数据服务层          │
│  · 报表/大屏/KPI 指标                                   │
│  · 高度汇总,面向具体应用                                │
│  · 例:每日GMV大屏、用户留存报表                          │
├─────────────────────────────────────────────────────────┤
│  DWS (Data Warehouse Service)   数据仓库服务层           │
│  · 轻度汇总(主题宽表)                                  │
│  · 面向主题域:用户主题/商品主题/交易主题                 │
│  · 例:用户日活宽表、商品SKU日汇总表                      │
├─────────────────────────────────────────────────────────┤
│  DWD (Data Warehouse Detail)    数据仓库明细层          │
│  · 清洗后的明细数据                                      │
│  · 维度退化、统一编码、去重去噪                           │
│  · 例:订单事实表、用户行为日志明细                       │
├─────────────────────────────────────────────────────────┤
│  ODS (Operational Data Store)   操作数据存储层          │
│  · 贴源层,原始数据不做处理                              │
│  · 增量/全量同步,保留原始结构                           │
│  · 例:MySQL binlog 同步、API 日志原始入湖               │
└─────────────────────────────────────────────────────────┘

3.2 分层落地 SQL

-- =====================================================
-- DWD 层:订单明细事实表(维度建模)
-- 来源:ODS 层业务库多表 JOIN 清洗
-- =====================================================

CREATE TABLE dwd.fact_order_detail (
    -- 退化维度(直接放事实表)
    order_id            BIGINT        COMMENT '订单ID(退化维度)',
    order_no            VARCHAR(32)   COMMENT '订单编号',

    -- 维度外键
    user_key            BIGINT        COMMENT '用户维度键(代理键)',
    product_key         BIGINT        COMMENT '商品维度键',
    store_key           BIGINT        COMMENT '门店维度键',
    date_key            INT           COMMENT '日期维度键 YYYYMMDD',
    channel_key         INT           COMMENT '渠道维度键',

    -- 度量值(事实)
    order_amount        DECIMAL(18,2) COMMENT '订单金额',
    discount_amount     DECIMAL(18,2) COMMENT '优惠金额',
    actual_amount       DECIMAL(18,2) COMMENT '实付金额',
    product_quantity    INT           COMMENT '商品数量',
    product_count       INT           COMMENT 'SKU数',

    -- 可加事实(可跨维度聚合)
    is_first_order      TINYINT       COMMENT '是否首单 1-是 0-否',
    is_coupon_used      TINYINT       COMMENT '是否用券',

    -- 审计字段
    etl_time            TIMESTAMP     COMMENT 'ETL处理时间',
    source_table        VARCHAR(64)   COMMENT '来源表'
)
PARTITION BY (date_key)
COMMENT '订单明细事实表(DWD层)';


-- DWS 层:用户主题日汇总宽表
CREATE TABLE dws.dws_user_daily (
    user_key            BIGINT,
    date_key            INT,

    -- 用户维度属性(退化到宽表)
    user_level          VARCHAR(16)   COMMENT '用户等级',
    city                VARCHAR(32),
    register_date       DATE,

    -- 交易指标
    order_count         INT           COMMENT '订单数',
    order_amount        DECIMAL(18,2) COMMENT '订单金额',
    actual_amount       DECIMAL(18,2) COMMENT '实付金额',
    avg_order_amount    DECIMAL(18,2) COMMENT '客单价',
    first_order_count   INT           COMMENT '首单数',

    -- 行为指标
    login_count         INT           COMMENT '登录次数',
    browse_duration     INT           COMMENT '浏览时长(秒)',
    add_cart_count      INT           COMMENT '加购次数',

    -- 衍生指标
    pay_conversion_rate DECIMAL(5,4)  COMMENT '支付转化率',
    retention_day1      DECIMAL(5,4)  COMMENT '次日留存率',

    etl_time            TIMESTAMP
)
PARTITION BY (date_key)
COMMENT '用户主题日汇总宽表(DWS层)';


-- ADS 层:流量转化漏斗
CREATE TABLE ads.ads_conversion_funnel_daily (
    date_key            INT,
    step_name           VARCHAR(32)   COMMENT '漏斗步骤: 曝光/点击/加购/下单/支付',
    user_count          BIGINT        COMMENT '用户数',
    step_rate           DECIMAL(5,4)  COMMENT '步骤转化率',
    overall_rate        DECIMAL(5,4)  COMMENT '整体转化率'
)
COMMENT '流量转化漏斗(ADS层)';

四、缓慢变化维(SCD)

4.1 六种策略

┌────────────────────────────────────────────────────────┐
│                缓慢变化维(SCD)策略                     │
├────────┬─────────────┬─────────────────────────────────┤
│ Type   │ 策略        │ 示例                            │
├────────┼─────────────┼─────────────────────────────────┤
│ Type 0 │ 保留原始值   │ 出生日期(永不变化)             │
│ Type 1 │ 直接覆盖     │ 用户昵称(旧值不重要)           │
│ Type 2 │ 新增行      │ 用户等级升级(需要历史)          │
│ Type 3 │ 新增列      │ 部门更名(只保留前一个值)        │
│ Type 4 │ 历史表分离   │ 用户地址(主表+历史表)          │
│ Type 6 │ 混合(1+2+3) │ 自选属性(部分覆盖+部分新增行)   │
└────────┴─────────────┴─────────────────────────────────┘

4.2 Type 2 拉链表实现

-- =====================================================
-- SCD Type 2:用户维度表(拉链表)
-- 每次属性变更 → 插入新行,旧行标记过期
-- =====================================================

-- 维度表结构
CREATE TABLE dim.dim_user (
    user_key            BIGINT        COMMENT '代理键(自增,唯一)',
    user_id             VARCHAR(32)   COMMENT '业务主键',
    user_name           VARCHAR(64),
    user_level          VARCHAR(16)   COMMENT '普通/白银/黄金/钻石',
    city                VARCHAR(32),
    phone               VARCHAR(20),

    -- SCD Type 2 核心字段
    effective_date      DATE          COMMENT '生效日期',
    expire_date         DATE          COMMENT '失效日期(9999-12-31=当前有效)',
    is_current          TINYINT       COMMENT '是否当前版本 1-是 0-否',

    etl_time            TIMESTAMP
);

-- 处理逻辑(每日 ETL)
-- 1. 新用户 → 直接插入
INSERT INTO dim.dim_user (user_id, user_name, user_level, city, phone,
                          effective_date, expire_date, is_current)
SELECT
    user_id, user_name, user_level, city, phone,
    CURRENT_DATE, '9999-12-31', 1
FROM ods.user
WHERE user_id NOT IN (SELECT user_id FROM dim.dim_user WHERE is_current = 1);

-- 2. 属性变更 → 关闭旧版本 + 插入新版本
-- Step 2a: 关闭过期版本
UPDATE dim.dim_user
SET expire_date = CURRENT_DATE - 1,
    is_current = 0
WHERE user_id IN (
    SELECT user_id FROM ods.user
    WHERE CONCAT(user_name, user_level, city, phone)
       != (SELECT CONCAT(user_name, user_level, city, phone)
           FROM dim.dim_user d
           WHERE d.user_id = ods.user.user_id AND d.is_current = 1)
)
AND is_current = 1;

-- Step 2b: 插入新版本
INSERT INTO dim.dim_user (user_id, user_name, user_level, city, phone,
                          effective_date, expire_date, is_current)
SELECT
    u.user_id, u.user_name, u.user_level, u.city, u.phone,
    CURRENT_DATE, '9999-12-31', 1
FROM ods.user u
JOIN dim.dim_user d ON u.user_id = d.user_id AND d.is_current = 1
WHERE CONCAT(u.user_name, u.user_level, u.city, u.phone)
   != CONCAT(d.user_name, d.user_level, d.city, d.phone);

-- 查询技巧:
-- 查当前用户 → is_current = 1
-- 查历史快照 → 事实表 date_key BETWEEN effective_date AND expire_date
SELECT f.*, d.user_level
FROM dwd.fact_order_detail f
JOIN dim.dim_user d
  ON f.user_key = d.user_key
 AND f.date_key BETWEEN d.effective_date AND d.expire_date;

五、维度建模核心模式

5.1 事实表类型

┌──────────────────┬─────────────────────┬──────────────────┐
│ 事实表类型       │ 粒度                │ 示例             │
├──────────────────┼─────────────────────┼──────────────────┤
│ 事务事实表       │ 一行=一次事务        │ 订单表、支付流水 │
│ Transaction      │ 最细粒度            │                  │
├──────────────────┼─────────────────────┼──────────────────┤
│ 周期快照事实表   │ 一行=一个周期状态    │ 库存日快照       │
│ Periodic Snapshot│ 定期采样            │ 账户余额日表     │
├──────────────────┼─────────────────────┼──────────────────┤
│ 累积快照事实表   │ 一行=实体全生命周期  │ 订单生命周期表   │
│ Accumulating     │ 多状态日期列        │ 保险理赔全程表   │
├──────────────────┼─────────────────────┼──────────────────┤
│ 无事实事实表     │ 多对多关系          │ 学生选课事实表   │
│ Factless         │ 只有外键无度量      │ 参会记录表       │
└──────────────────┴─────────────────────┴──────────────────┘

5.2 累积快照事实表(订单生命周期)

-- 一行记录跟踪订单的完整生命周期
CREATE TABLE dwd.fact_order_lifecycle (
    order_id            BIGINT,
    user_key            BIGINT,
    product_key         BIGINT,
    date_key            INT,

    -- 多状态日期列
    order_create_time   TIMESTAMP     COMMENT '下单时间',
    order_pay_time      TIMESTAMP     COMMENT '支付时间',
    order_ship_time     TIMESTAMP     COMMENT '发货时间',
    order_deliver_time  TIMESTAMP     COMMENT '签收时间',
    order_cancel_time   TIMESTAMP     COMMENT '取消时间',

    -- 时效度量
    pay_duration        INT           COMMENT '支付耗时(分钟)',
    ship_duration       INT           COMMENT '发货耗时(小时)',
    delivery_duration   INT           COMMENT '配送耗时(小时)',
    is_cancelled        TINYINT       COMMENT '是否取消',

    -- 金额
    order_amount        DECIMAL(18,2),
    actual_amount       DECIMAL(18,2),

    etl_time            TIMESTAMP,
    update_time         TIMESTAMP     COMMENT '最后更新时间'
);
-- ETL: 每天用最新状态 UPDATE 对应列,而非 INSERT 新行

六、指标管理体系

6.1 原子指标 → 派生指标 → 复合指标

原子指标(不可拆分):
  支付金额、订单数、用户数、GMV

派生指标(原子指标 + 维度 + 时间):
  最近7天 各品类 支付金额
  本月 新用户 订单数

复合指标(派生指标运算):
  客单价 = 支付金额 / 订单数
  转化率 = 支付用户数 / 访问用户数
  同比增长 = (本期 - 同期) / 同期

6.2 指标定义规范(OneData)

-- dbt 模型:指标标准化定义
-- models/metrics/user_metrics.yml

metrics:
  - name: dau
    label: 日活跃用户数
    description: 当日至少打开一次APP的去重用户数
    type: simple
    type_params:
      measure: count_distinct_user
    filter: |
      {{ dimension('event_type') }} = 'app_launch'
    time_grains: [day, week, month]

  - name: gmv
    label: 总交易额
    description: 所有支付成功的订单金额总和
    type: simple
    type_params:
      measure: sum_order_amount
    filter: |
      {{ dimension('order_status') }} = 'paid'

  - name: conversion_rate
    label: 下单转化率
    description: 访问用户中完成下单的用户占比
    type: ratio
    type_params:
      numerator: count_distinct_order_users
      denominator: count_distinct_visit_users

七、dbt 数据建模工作流

# models/
# ├── staging/      # 基础层:ODS → Staging(重命名+类型转换)
# ├── intermediate/ # 中间层:Staging → 业务实体
# └── marts/        # 集市层:中间层 → 维度表/事实表

# staging/stg_orders.sql
SELECT
    id                       AS order_id,
    user_id,
    CAST(amount AS DECIMAL(18,2)) AS amount,
    status,
    created_at               AS order_create_time,
    _ingested_at             AS etl_time
FROM {{ source('raw', 'orders') }}

# marts/dim_user.sql
WITH user_versions AS (
    SELECT *,
        ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY updated_at DESC) AS rn
    FROM {{ ref('stg_users') }}
)
SELECT
    {{ dbt_utils.generate_surrogate_key(['user_id']) }} AS user_key,
    user_id,
    user_name,
    user_level,
    city,
    CURRENT_DATE AS effective_date,
    '9999-12-31' AS expire_date,
    TRUE AS is_current
FROM user_versions
WHERE rn = 1

# marts/fact_sales_daily.sql
{{
    config(
        materialized='incremental',
        partition_by={'field': 'date_key', 'data_type': 'int'},
        unique_key=['date_key', 'user_key', 'product_key']
    )
}}
SELECT
    DATE_FORMAT(order_create_time, '%Y%m%d') AS date_key,
    {{ dbt_utils.generate_surrogate_key(['user_id']) }} AS user_key,
    {{ dbt_utils.generate_surrogate_key(['product_id']) }} AS product_key,
    COUNT(DISTINCT order_id) AS order_count,
    SUM(amount)              AS total_amount,
    COUNT(DISTINCT user_id)  AS user_count
FROM {{ ref('stg_orders') }}
WHERE status = 'paid'
{% if is_incremental() %}
  AND order_create_time >= (SELECT MAX(etl_time) FROM {{ this }})
{% endif %}
GROUP BY date_key, user_key, product_key

八、数据建模反模式

反模式问题正确做法
:---:---:---
大宽表几百列更新锁、存储膨胀、维护难DWS 层做主题拆分
用业务ID做关联字符串 JOIN 极慢统一用代理键(数字)
维度属性塞事实表事实表膨胀、更新困难事实表只放外键+度量
拉链表不用代理键无法区分历史版本user_id + user_key 分离
ODS 直接出报表数据脏、计算重复必经 DWD→DWS→ADS
多层 CROSS JOIN笛卡尔积爆炸先聚合再 JOIN
分区键不用在 WHERE全表扫描WHERE 必须含分区键

九、技术选型决策树

数据量 < 100GB + 团队 < 5人
  → Kimball 维度建模 + dbt + 单机 MySQL/PostgreSQL

数据量 100GB~10TB + 多业务线
  → Kimball + Inmon 混合(DWD星型 + EDW 3NF)+ dbt + ClickHouse/Doris

数据源频繁变化 + 需要完整审计
  → Data Vault 2.0 + dbt + Snowflake/BigQuery

超大规模 + 实时 + 半结构化
  → 湖仓一体(Iceberg/Hudi) + dbt + Trino/Spark

超大企业 + 严格合规
  → Inmon CIF + Data Vault(ODS 层)+ Teradata/Snowflake

十、建模产出物清单

□ 业务过程矩阵(业务过程 × 维度)
□ 总线矩阵(共享维度一致性)
□ 概念数据模型(CDM)
□ 逻辑数据模型(LDM):实体关系图
□ 物理数据模型(PDM):DDL + 分区/索引策略
□ ETL 映射文档(源表 → 目标表字段映射)
□ 数据字典(表/字段/枚举值说明)
□ 数据血缘图(dbt docs + lineage)
□ 指标口径文档(原子指标→派生指标→复合指标)
□ SCD 策略清单(每个维度的变更策略)
*(内容由AI生成,仅供参考)*

版本历史

共 1 个版本

  • v1.0.0 SKILL.md(25.7KB):数据建模全景图、Kimball vs Inmon vs Data Vault 三大方法论对比、星型模型与总线矩阵、SCD 六种策略含 Type 2 拉链表 SQL 实现、事实表四种类型(事务/周期快照/累积快照/无事实)、数据分层架构四层 DDL、指标管理体系与 OneData 规范、dbt 模型增量物化工作流、反模式清单、技术选型决策树、十大建模产出物清单 scripts/(6个脚本):docker-compose.yml(PostgreSQL + Metabase + DataHub + Neo4j + ES 8服务环境)、init_schema.sql(ODS→DWD→DWS→ADS 全分层建表+示例数据+日期维度填充)、model_generator.py(维度表/事实表DDL生成器+总线矩阵+dbt模型生成)、lineage_analyzer.py(dbt SQL解析+依赖图构建+Mermaid/DOT导出+上溯下溯影响分析)、scd_handler.py(SCD Type 0/1/2/3/4/6 六种策略完整处理引擎)、setup_env.sh + validate_env.py(一键部署+环境验证+性能压测) 无 references:本技能为核心方法论与实战代码深度整合,所有知识点已直接内嵌到 SKILL.md 和脚本注释中 当前
    2026-06-01 22:08 安全 安全

安全检测

腾讯云安全 (Keen)

安全,无风险
查看报告

腾讯云安全 (Sanbu)

安全,无风险
查看报告

🔗 相关推荐

向量数据库大师

user_69009747
向量数据库选型与性能调优完全指南。Milvus 全索引类型深度拆解(IVF_FLAT/SQ8/PQ/HNSW/DISKANN,含召回率/内存/QPS 量化对比),四层性能优化金字塔(资源配置→分区分片→索引选择→查询参数),含 benchm
★ 0 📥 67

RAG 知识库搭建

user_69009747
企业级 RAG 知识库从零搭建全流程。文档分块策略(固定/语义/结构化三大方案 + 小2大高级优化)、2026 主流嵌入模型选型(中文 BGE / 多语言 BGE-M3 / 英文 OpenAI,含 MTEB 榜单)、完整 Pipeline(
★ 0 📥 71

Flink 实时数仓

user_69009747
Flink+Paimon+StarRocks 实时数仓全链路:CDC 入湖、物化表开发、分钟级大屏输出,一套 SQL 流批一体。
★ 0 📥 66