2. 数据完整性概念:数据完整性的四个维度
在数据库迁移场景中,数据完整性是指数据库中数据的准确性、一致性和可靠性的程度。它是衡量迁移后数据是否“可用”的核心标尺。业界通常将数据完整性划分为四个相互独立又彼此关联的维度:实体完整性、域完整性、参照完整性和用户定义完整性。
冒烟验证核心原则: 迁移后的数据完整性验证,必须覆盖这四个维度。任何一个维度的缺失,都可能导致业务逻辑错误或数据不可用。
2.1 四个维度总览
下表从定义、约束对象、典型数据库对象和迁移验证要点四个角度,对四个维度进行横向对比:
| 维度 | 定义 | 约束对象 | 典型数据库对象 | 迁移验证要点 |
|---|---|---|---|---|
| 实体完整性 | 保证每行数据在表中是唯一可识别的 | 行(记录) | 主键(PRIMARY KEY)、唯一索引(UNIQUE) | 主键值非空、不重复;唯一索引无重复值 |
| 域完整性 | 保证列中的数据符合定义的格式、类型和范围 | 列(字段) | 数据类型(INT/VARCHAR)、非空(NOT NULL)、默认值(DEFAULT)、CHECK 约束 | 字段类型、长度、精度一致;CHECK 约束生效 |
| 参照完整性 | 保证表与表之间的关联关系正确,外键值必须匹配主键值或为 NULL | 表间关系 | 外键(FOREIGN KEY) | 外键引用有效;无孤立子记录;级联操作正确 |
| 用户定义完整性 | 业务自定义的规则,不属于前三类的特殊约束 | 业务规则 | 触发器(TRIGGER)、存储过程、自定义函数、业务逻辑约束 | 触发器逻辑正确;业务规则计算结果一致 |
2.2 实体完整性(Entity Integrity)
实体完整性是数据完整性的第一道防线。它要求:
- 每个表必须有一个主键(PRIMARY KEY)。
- 主键列的值必须唯一且非空(NOT NULL)。
- 唯一索引(UNIQUE)也属于实体完整性的范畴,它确保非主键列的组合值不重复。
迁移冒烟验证技巧: 在源库和目标库分别执行
SELECT COUNT(DISTINCT pk_col) FROM table 和 SELECT COUNT(*) FROM table,若两个值相等,则主键唯一性通过。再检查 SELECT COUNT(*) FROM table WHERE pk_col IS NULL 是否为 0。
2.3 域完整性(Domain Integrity)
域完整性关注的是列级的数据有效性。它确保:
- 字段的数据类型(如 INT、VARCHAR、DATE)与源库一致。
- 字段长度、精度(如 DECIMAL(10,2))未发生截断或溢出。
- 非空约束(NOT NULL)被正确迁移。
- 默认值(DEFAULT)在插入时生效。
- CHECK 约束(如
age >= 0 AND age <= 150)在目标库中仍然有效。
-- 域完整性验证示例:检查字段类型和长度是否一致
SELECT
COLUMN_NAME,
DATA_TYPE,
CHARACTER_MAXIMUM_LENGTH,
IS_NULLABLE,
COLUMN_DEFAULT
FROM INFORMATION_SCHEMA.COLUMNS
WHERE TABLE_NAME = 'orders'
ORDER BY ORDINAL_POSITION;
2.4 参照完整性(Referential Integrity)
参照完整性维护表之间的父子关系。它要求:
- 外键(FOREIGN KEY)列的值必须存在于被引用表的主键列中,或者为 NULL。
- 当父表记录被更新或删除时,子表的行为(级联、置空、限制)必须符合业务预期。
- 迁移后不能出现孤立子记录(orphan records)。
常见迁移陷阱: 某些数据库迁移工具在批量导入时,为了提升速度会临时禁用外键约束。如果迁移完成后忘记重新启用,参照完整性将完全失效。冒烟验证时必须检查外键约束状态。
-- 检查外键约束是否启用(以 MySQL 为例)
SELECT
TABLE_NAME,
CONSTRAINT_NAME,
CONSTRAINT_TYPE,
ENFORCED
FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS
WHERE CONSTRAINT_TYPE = 'FOREIGN KEY' AND TABLE_SCHEMA = 'target_db';
2.5 用户定义完整性(User-Defined Integrity)
用户定义完整性是业务逻辑的最后一道关卡。它涵盖:
- 触发器(TRIGGER):在 INSERT、UPDATE、DELETE 时自动执行的业务逻辑。
- 存储过程与函数:封装了复杂业务规则的代码对象。
- 自定义约束:如业务状态机转换规则(订单状态只能从“待支付”变为“已支付”)。
- 复合业务规则:例如“折扣金额不能超过订单总额的 30%”。
这类完整性在迁移中最容易被忽略,因为工具通常只迁移表结构和数据,而不验证业务逻辑的正确性。
2.6 四个维度的关系与冒烟验证策略
下面的 SVG 图展示了四个维度在数据库中的层级关系,以及冒烟验证的推荐顺序:
2.7 冒烟验证中的维度优先级
在数据库迁移的冒烟验证阶段,建议按照自底向上的顺序进行验证:
- 先验证实体完整性:主键和唯一索引是数据可识别的基础。
- 再验证域完整性:确保每一列的数据格式和范围正确。
- 然后验证参照完整性:检查表间关系是否断裂。
- 最后验证用户定义完整性:确认业务逻辑在目标库中正确执行。
经验法则: 如果实体完整性或域完整性在冒烟阶段失败,则参照完整性和用户定义完整性的验证结果将不可信。因为底层数据已经存在质量问题,上层约束的验证会失去意义。