一文带你了解Mock 技术体系

简介: **Mock和测试替身简介** 学习Mock提升测试深度、效率和降低成本。示例:测试股票软件时模拟市场涨跌。Test Double包括Dummy(占位)、Fake(简化的实现)、Stub(预设回答)、Spy(记录行为)和Mock(预编程期望)。Fake如内存数据库,适用于测试。Stub用于预设响应,如Swagger接口。Mock确保收到预期调用。常用Mock工具有WireMock、Mitmproxy等。WireMock用于构建模拟API,支持stub和proxy模式。掌握Mock技术能更好地隔离和测试系统组件。

简介

为什么要学习 Mock

  • 提高测试深度
  • 提高测试效率
  • 降低成本
  1. 测试股票软件,模拟当天股票全部上涨
  2. 测试股票软件,模拟当天股票全部下跌
  3. 测试股票软件,模拟部分股票涨幅10%

Test Double 测试替身

  • Dummy 占位对象 对象被传递但从未实际使用过。通常它们仅用于填充参数列表。
  • Fake 假对象 对象实际上有工作实现,但通常采取一些捷径,这使得它们不适合生产(内存数据库就是一个很好的例子)。
  • Stubs 桩对象 为测试期间调用提供预设答案,通常根本不响应任何超出测试程序的内容。
  • Spies 间谍对象 它们还根据调用方式记录一些信息。其中一种形式可能是电子邮件服务,它记录发送了多少消息。
  • Mocks 模拟对象 是我们在这里谈论的:预先编程的对象,这些期望形成了它们期望接收的调用的规范。

测试替身关键概念的区别

image.png

一个真实的技术架构例子

  • dummy 只要端口开着就行
  • fake 内存数据库
  • spy UI 界面后端请求记录
  • stub 假的登录后端服务
  • hook 新用户判断方法修改
  • proxy 代理转发机制
  • mock 模拟对象

image.png

Fake 假对象 定义

Fake objects actually have working implementations, but usually take some shortcut which makes them not suitable for production (an InMemoryTestDatabase is a good example).

假对象实际上有工作实现,但通常采取一些捷径,这使得它们不适合生产(纯内存数据库就是一个很好的例子)。

image.png

Fake 应⽤场景

image.png

Stub 桩定义

Stubs provide canned answers to calls made during the test, usually not responding at all to anything outside what's programmed in for the test.

为测试期间调用提供预设答案,通常根本不响应任何超出测试程序的内容。

image.png

Stub 应⽤场景 Swagger

image.png

Setup Stub Server

java -jar moco-runner-1.2.0-standalone.jar http -p 12345 -c foo.json

{
   
   
  "request" :
    {
   
   
      "uri" : "/foo",
      "queries" :
        {
   
   
          "param" : "blah"
        }
    },
  "response" :
    {
   
   
      "text" : "bar"
    }
}

image.png

Mock 模拟对象定义

Mocks are pre-programmed with expectations which form a specification of the calls they are expected to receive. They can throw an exception if they receive a call they don't expect and are checked during verification to ensure they got all the calls they were expecting.

模拟预编程了期望,这些期望形成了他们期望接收的调用的规范。如果他们收到了他们不期望的调用,他们可以抛出异常,并在验证过程中进行检查以确保他们得到了他们期望的所有调用。

image.png

Mock 两种应用场景

  • mock on stub:按需返回期望数据
  • mock on proxy:按需返回真实数据的修改副本

#

常⽤的 Mock 工具

  • Charles 测试工程师常用
  • BurpSuite 黑客常用
  • Fiddler 只能 Windows 上使用
  • Nginx 服务器反向代理与修改
  • Mitmproxy 代理工具 可编程
  • Wiremock 代理工具 可编程

#

mitmproxy

mitmproxy is a set of tools that provide an interactive, SSL/TLS-capable intercepting proxy for HTTP/1, HTTP/2, and WebSockets.

image.png

mitmproxy mock on proxy

python3 -m http.server
mitmdump -p 8001  -m reverse:127.0.0.1:8000 --flow-detail 4 -B '/~bs .*Directory.*/Directory/ceshiren.com mock'

#

mitmproxy 强大的插件机制 Addons

  • dns
  • tcp
  • cert
  • http/https
  • websocket

image.png

#

adb mock 案例



import sys

from mitmproxy import ctx
from mitmproxy import tcp
from mitmproxy.utils import strutils
from mitmproxy.tools.main import mitmdump


def tcp_message(flow: tcp.TCPFlow):
    message = flow.messages[-1]
    old_content = message.content
    message.content = old_content.replace(
        b":0;localabstract:webview_devtools_remote_",
        b":   0;localabstract:xweb_devtools_remote_"
    )

    ctx.log.info(
        "[tcp_message{}] from {} to {}:\n{}".format(
            " (modified)" if message.content != old_content else "",
            "client" if message.from_client else "server",
            "server" if message.from_client else "client",
            strutils.bytes_to_escaped_str(message.content))
    )


if __name__ == '__main__':
    sys.argv = ["", "-p", "5038", "--rawtcp", "--mode", "reverse:http://localhost:5037/", "-s", sys.argv[0], "-vv"]
    mitmdump()

WireMock

The flexible tool for building mock APIs.
Create stable development environments, isolate yourself from flakey 3rd parties and simulate APIs that don't exist yet.

image.png

wiremock stub

java -jar wiremock-jre8-standalone-2.33.2.jar
{
   
     "request": {
   
       "method": "GET",    "url": "/wiremock"  },
  "response": {
   
       "status": 200,    "body": "Easy!"  }}

mock on stub


@Test
public void exactUrlOnly() {
   
   
    stubFor(get(urlEqualTo("/some/thing"))
            .willReturn(aResponse()
                .withHeader("Content-Type", "text/plain")
                .withBody("Hello world!")));

    assertThat(testClient.get("/some/thing").statusCode(), is(200));
    assertThat(testClient.get("/some/thing/else").statusCode(), is(404));
}

mock on proxy


wm.stubFor(get(urlPathEqualTo("/templated"))
  .willReturn(aResponse()
      .proxiedFrom("$!request.headers.X-WM-Proxy-Url")
      .withTransformers("response-template")));

-


public class ExampleTransformer extends ResponseDefinitionTransformer {
   
   


    @Override
    public ResponseDefinition transform(Request request, ResponseDefinition responseDefinition, FileSource files, Parameters parameters) {
   
   
        String content=responseDefinition.getTextBody().replace("霍格沃兹", "mock");
        System.out.println(responseDefinition.getTextBody());
        System.out.println(content);
        return new ResponseDefinitionBuilder()
                .withHeader("MyHeader", "Transformed")
                .withStatus(200)
                .withBody(content)
                .build();
    }


    @Override
    public String getName() {
   
   
        return "hogwarts_mock";
    }
}

总结

  • 了解测试替身的实现方式,统一沟通概念
  • 了解 Mock 的常见应用场景
相关文章
|
测试技术 程序员 C++
C++单元测试GoogleTest和GoogleMock十分钟快速上手(gtest&gmock)
gtest是Google开源的一个跨平台的(Liunx、Mac OS X、Windows等)的 C++ 单元测试框架,可以帮助程序员测试 C++ 程序的结果预期。它提供了丰富的断言、致命和非致命判断、参数化、”死亡测试”等等。另一方面,gmock并不是一个独立的测试框架,而是gtest的辅助框架,主要用于模拟没有实现的类的操作,以便在没有完整类的情况下进行测试。通过配合使用gtest和gmock,开发者可以编写出更为复杂且健壮的C++单元测试。
2641 0
|
Java jenkins 测试技术
如何利用Allure报告提升你的测试效率?
如何利用Allure报告提升你的测试效率?
如何利用Allure报告提升你的测试效率?
|
6月前
|
人工智能 测试技术 持续交付
GPT-Image 2 + Seedance 2,普通人做短视频的门槛又被打穿了
近期AI影像领域两大突破性工具引发关注:OpenAI的GPT-Image 2.0强化文字渲染与视觉推理,专注高质量静态图生成;字节Seedance 2.0则基于统一多模态架构,支持图文音视频输入,实现可控动态视频生成。二者协同,正将短视频创作从“团队协作”降维为“单人闭环”,大幅降低普通人做自媒体副业的内容生产门槛。
|
10月前
|
弹性计算 网络协议 Linux
阿里云ECS云服务器详细新手购买流程步骤(图文详解)
新手怎么购买阿里云服务器ECS?今天出一期阿里云服务器ECS自定义购买流程:图文全解析,阿里云服务器ECS购买流程图解,自定义购买ECS的设置选项是最复杂的,以自定义购买云服务器ECS为例,包括付费类型、地域、网络及可用区、实例、镜像、系统盘、数据盘、公网IP、安全组及登录凭证详细设置教程:
643 114
|
关系型数据库 MySQL 网络安全
如何在宝塔mysql修改掉3306端口
在宝塔面板管理MySQL时,默认使用3306端口。为提升安全或避免冲突,可修改端口。步骤如下:1. 登录宝塔面板;2. 进入数据库管理;3. 找到并编辑my.cnf配置文件,修改`port`值;4. 保存并重启MySQL服务;5. 开放防火墙新端口;6. 测试连接。具体命令和流程图详见正文。
1794 1
|
前端开发 架构师 算法
技术一号位的方法论《个人篇》——人成长的本质以及如何构建个人成长路线图
不论你是职场新人还是35岁的职场“老人”,成长是每个职场人都绕不开的话题,同时也是贯穿每个人职业生涯的痛点。本文主要帮助读者建立起对个人成长的认知,然后在此认知的基础上让大家理解成长的本质,最终通过文章的引导,来帮助读者完成个人成长路线图的确定以及落地实践。
14531 3
技术一号位的方法论《个人篇》——人成长的本质以及如何构建个人成长路线图
|
机器学习/深度学习 数据采集 算法
基于mediapipe深度学习的运动人体姿态提取系统python源码
本内容介绍了基于Mediapipe的人体姿态提取算法。包含算法运行效果图、软件版本说明、核心代码及详细理论解析。Mediapipe通过预训练模型检测人体关键点,并利用部分亲和场(PAFs)构建姿态骨架,具有模块化架构,支持高效灵活的数据处理流程。
|
存储 移动开发 安全
支付宝H5下载被拦截的原因排查与解决指南
在支付宝H5页面中,“请确保该下载文件来源安全”的提示通常源于支付宝的安全拦截机制。原因可能包括:1) 安全策略限制,如非HTTPS协议或未通过白名单审核;2) 文件下载方式不规范,如自动触发下载;3) CSP配置不当。解决方案包括:确保使用HTTPS协议、让用户主动触发下载、正确配置CSP、检查文件类型与存储位置、申请支付宝白名单以及遵循官方文档规范。调试时可查看控制台日志和网络请求状态,必要时联系支付宝技术支持协助排查。
1325 0
|
数据可视化 API Python
Matplotlib深度解析
【10月更文挑战第7天】
|
存储 JSON Linux
探索Linux文件系统的奥秘:`lsblk`命令详解
`lsblk`是Linux下用于列出块设备详情的命令,显示设备名、大小、类型、挂载点等信息,尤其适合查看磁盘分区和挂载状态。它以树形结构展示设备间的依赖,且支持多种输出格式。常用参数如`-a`显示所有设备,`-f`显示文件系统信息,`-o`定制输出列。结合其他命令使用能有效管理文件系统。注意权限和输出格式选择。