1. 课程导论:什么是 Mock 测试、为什么需要 Mock、Mock 在 PostgreSQL 集成测试中的价值

1.1 什么是 Mock 测试

Mock 测试是一种软件测试技术,通过创建模拟对象(Mock Object)来替代真实依赖组件,从而在隔离环境中验证被测单元的行为。在数据库领域,Mock 测试的核心思想是:用轻量级的模拟层替代真实的数据库实例、外部服务或中间件,使测试只关注当前逻辑的正确性,而不受底层基础设施状态的影响。

核心定义:Mock 对象是“替身”,它预先定义了期望的输入输出行为,测试过程中验证被测代码是否按预期与 Mock 交互。

Mock 测试与 Stub(桩)、Fake(伪实现)的区别如下表所示:

概念 行为特征 状态验证 典型用途
Mock 预设期望,验证交互行为(是否被调用、调用次数、参数) 验证行为 外部服务、消息队列、数据库连接
Stub 返回固定数据,不验证交互 不验证 接口返回值占位
Fake 有轻量级真实逻辑实现(如内存数据库) 可验证状态 本地替代真实数据库
提示:本课程聚焦于 PostgreSQL 集成测试场景,我们主要使用 Mock 技术来隔离外部依赖(如 Redis、第三方 API、其他数据库),同时结合 Fake 技术(如嵌入式 PG 或 pgmock)来模拟 PostgreSQL 自身行为。
Mock 测试核心概念示意图 Mock 测试核心概念 被测系统 (SUT) 真实数据库 外部 API 消息队列 Mock 数据库 Mock API Mock 队列 Mock 替代真实依赖

1.2 为什么需要 Mock

在 PostgreSQL 集成测试中,直接依赖真实数据库会带来一系列痛点,Mock 技术正是为解决这些问题而生:

  • 环境不稳定:真实数据库需要安装、配置、启动,CI/CD 环境中可能因资源不足或版本冲突导致测试失败。
  • 测试速度慢:每次测试都要建立 TCP 连接、执行 DDL/DML、清理数据,单条测试可能耗时数百毫秒,大规模测试集不可接受。
  • 数据污染:并行测试时,不同用例可能相互干扰,需要复杂的隔离策略(如 schema 级隔离、事务回滚)。
  • 外部依赖不可控:如果被测代码还依赖 Redis、Kafka 或第三方 HTTP 服务,这些组件的可用性直接影响测试结果。
  • 难以模拟异常:真实数据库很难模拟网络超时、连接断开、死锁等边界场景,而这些正是健壮性测试的关键。
常见误区:Mock 测试不是要完全替代集成测试。它的目标是在单元测试和轻量级集成测试中消除外部不确定性,让开发者快速获得反馈。完整的端到端测试仍然需要真实数据库。

以下表格对比了使用 Mock 与不使用 Mock 的测试差异:

维度 不使用 Mock(真实数据库) 使用 Mock(模拟层)
执行速度 慢(50-500ms/用例) 快(1-10ms/用例)
环境依赖 需要安装 PG、配置用户、创建数据库 无外部依赖,纯内存运行
并行能力 需 schema 或数据库级隔离 天然隔离,无状态冲突
异常模拟 困难(需注入故障) 容易(直接返回错误)
CI/CD 稳定性 受宿主机 PG 版本、资源影响 稳定可重复

1.3 Mock 在 PostgreSQL 集成测试中的价值

在 PostgreSQL 生态中,Mock 技术的价值体现在三个层面:

  1. 加速开发反馈循环:开发者可以在不启动数据库的情况下,秒级验证 SQL 构建逻辑、ORM 映射、事务处理代码的正确性。
  2. 提升测试覆盖率:轻松模拟数据库连接失败、查询超时、唯一约束冲突、死锁等异常场景,覆盖真实环境中难以触发的边界条件。
  3. 降低基础设施成本:CI/CD 流水线无需为每个分支启动独立 PostgreSQL 实例,减少资源消耗和排队等待时间。
典型场景举例:假设你有一个用户注册服务,它先查询 PostgreSQL 判断用户名是否已存在,再写入新记录。使用 Mock 后,你可以分别测试“用户名已存在时返回错误”和“写入成功时返回用户 ID”两条路径,无需真实数据库中有任何数据。
Mock 在 PostgreSQL 集成测试中的价值分层 Mock 在 PG 集成测试中的价值分层 加速开发反馈循环 秒级验证 SQL 构建、ORM 映射、事务逻辑,无需启动真实数据库 提升测试覆盖率 模拟连接失败、超时、死锁、约束冲突等真实环境难以触发的异常 降低基础设施成本 CI/CD 无需为每个分支启动独立 PG 实例,减少资源消耗与排队等待 价值从下到上递进

1.4 本课程覆盖的 Mock 技术栈

本课程将围绕 PostgreSQL 集成测试场景,系统讲解以下 Mock 技术:

  • pgmock 库:纯 Python 实现的 PostgreSQL 协议模拟器,支持 SQL 解析、预置结果集、错误注入。
  • 嵌入式 PostgreSQL(pg_tmp / pgxn):在测试进程中启动临时 PG 实例,实现 Fake 级别的隔离。
  • unittest.mock / pytest-mock:对数据库连接池、游标对象进行方法级别的 Mock。
  • docker-compose + Testcontainers:容器化真实 PG 实例,配合网络隔离实现轻量级集成测试。
  • 自定义 Mock 中间件:基于 asyncio 或 threading 构建的数据库代理层,支持流量录制与回放。
学习路径建议:如果你刚开始接触 Mock 测试,建议从 unittest.mock 和 pgmock 入手;如果你需要更真实的 SQL 兼容性,可以学习嵌入式 PG 方案;对于微服务架构,Testcontainers 是最佳实践。

通过本课程的学习,你将掌握一套完整的 PostgreSQL Mock 依赖隔离方法论,能够根据项目阶段和测试目标灵活选择最合适的 Mock 策略,构建出快速、稳定、可重复的集成测试环境。