测试基础篇

一、测试文档

1. 软件缺陷报告

要求: 把发现的缺陷准确无歧义地表达清楚,不易过长

“准确无歧义地表达”意味着,开发工程师可以根据缺陷报告快速理解缺陷,并精确定位问题。同时,通过这个缺陷报告,开发经理可以准确预估缺陷修复的优先级产品经理可以了解缺陷对用户或业务的影响以及严重性

包含内容:

  • 缺陷标题
    -对缺陷的概括性描述,通常采用“在什么情况下发生了什么问题”的模式

“什么问题”的描述标准:清晰、具体、以及问题出现的场景。

  • 缺陷概述
    -提供更多概括性的缺陷本质与现象的描述,是缺陷标题的细化

可以在这部分列出同一类型的缺陷可能出现的所有场景 或 可以描述同样的问题是否会在之前的版本中重现

  • 尽量避免以缺陷重现步骤的形式来描述,而应该使用概括性的语句
  • 缺陷影响 (优先级(Priority)和严重程度(Severity))
    -缺陷影响描述的是缺陷引起的问题对用户或者对业务的影响范围以及严重程度
    -测试工程师准确描述缺陷影响的前提是必须对软件的应用场景以及需求有深入的理解
  • 缺陷的优先级(Priority)
    优先级是缺陷的工程属性,会随着项目进度、解决缺陷的成本等因素而变动
  • 严重程度(Severity)
    严重程度是缺陷本身的属性,通常确定后就不再变化
  • 缺陷越严重,优先级就越高;
  • 缺陷影响的范围越大,优先级也会越高;
  • 会妨碍测试或者是自动化测试的执行,这类缺陷优先级高;
  • 有些缺陷虽然严重程度比较高,但是考虑到修复成本以及技术难度,也会出现优先级较低的情况。
  • 变通方案的有无以及实施的难易程度,是决定缺陷优先级和严重程度的重要依据
  • 环境配置
    -环境配置的内容通常是按需描述,也就是说通常只描述那些重现缺陷的环境敏感信息。
  • 前置条件
    -目的是减少缺陷重现步骤的描述
  • 缺陷重现步骤
    -目的在于用简洁的语言向开发工程师展示缺陷重现的具体操作步骤

每个步骤都应该是可操作并且是连贯的

  • 写缺陷重现步骤前,需要反复执行这些步骤 3 次以上:一是,确保缺陷的可重现性;二是,找到最短的重现路径,过滤掉那些非必要的步骤,避免产生不必要的干扰。
  • 对于缺陷重现步骤的描述应该尽量避免以下 3 个常见问题:1.笼统的描述,缺乏可操作的具体步骤。2.出现与缺陷重现不相关的步骤。3.缺乏对测试数据的相关描述。
  • 期望结果和实际结果
  • 附件(Attachment)

下面这些内容,个人认为不属于正式缺陷报告的内容,属于实际工作里的方式

  • 变通方案(Workaround)【提供一种临时绕开当前缺陷而不影响产品功能的方式】
  • 根原因分析(Root Cause Analysis)【定位出问题的根本原因】

2. 测试计划

敏捷项目中没有正式计划,但是不代表计划不制定
包含内容:

  • 测试范围
    -描述的是被测对象以及主要的测试内容
    -明确“测什么”和“不测什么”
  • 测试策略
    -明确“先测什么后测什么”
    -如何来测————采用什么样的测试类型和测试方法【给出为什么要选用这个测试类型;具体的实施方法】

测试类型:
功能测试、兼容性测试、性能测试、接口测试、集成测试、安全测试、容量验证、安装测试、故障恢复测试

  • 测试资源
    -明确“谁来测”和“在哪里测”

  • 测试进度
    -描述各类测试的开始时间,所需工作量,预计完成时间,并以此为依据来建议最终产品的上线发布时间。

  • 测试风险预估
    -明确如何有效应对各种潜在的变化

二、测试用例

测试用例的评判标准:“好的”测试用例一定是一个完备的集合,它能够覆盖所有等价类以及各种边界值,而跟能否发现缺陷无关

  • 整体完备 —— 完全覆盖测试需求
  • 等价类划分准确 —— 一个代表通过,其他全能通过
  • 等价类集合的完备性 —— 边界覆盖

1. 设计前提

  • 对被测系统的设计有深入的理解 (需求覆盖率和代码覆盖率把控)

    • 深入理解被测软件的设计与实现细节,深入理解软件内部的处理逻辑
    • 深入理解被测试软件的架构(数据库连接方式、数据库的读写分离、消息中间件 Kafka 的配置、缓存系统的层级分布、第三方系统的集成)
  • 安全攻击的基本原理

  • 性能测试的基本设计方法

2. 设计思路

  • 显式功能性需求
  • 隐式功能性需求(即非功能性需求)
    1. 安全性
    2. 兼容性
    3. 性能

先确认需求点,再确认测试点 【与需求点关系:多对1】,最后依据测试点编写测试用例 【与测试点关系:1:1

通常会使用需求追踪管理工具(比如 ALM、DOORS、JIRA、TestLink 等)来管理,并以此来衡量测试用例对业务需求、软件功能需求的覆盖率

测试覆盖率及代码覆盖率工具

3. 设计方法

(等价类划分法、边界值分析法、错误推测方法、因果图方法、判定表驱动分析法、正交实验设计方法、功能图分析方法、场景设计方法、形式化方法、扩展有限状态机方法)

常用方法:

  • 等价类
    是将所有可能的输入数据划分成若干个子集,在每个子集中,如果任意一个输入数据对于揭露程序中潜在错误都具有同等效果,那么这样的子集就构成了一个等价类。后续只要从每个等价类中任意选取一个值进行测试,就可以用少量具有代表性的测试输入取得较好的测试覆盖结果。
关键点:1.要找出所有“无效等价类”2.正确划定“有效等价类”
  • 边界值——对等价类划分的补充,一般组合使用
    边界值分析方法,是选取输入、输出的边界值进行测试。因为通常大量的软件错误是发生在输入或输出范围的边界上,所以需要对边界值进行重点测试,通常选取正好等于、刚刚大于或刚刚小于边界的值作为测试数据
  • 错误推测法
  • 场景法

4. 设计原则

  • 软件测试的用例设计是不可穷尽的,工程实践中难免受制于时间成本和经济成本,需要兼顾缺陷风险和研发成本之间的平衡

5. 实例

  • 用户登录

三、自动化测试

自动化测试适合:

  1. 需求稳定,不会频繁变更的项目;
  2. 研发和维护周期长,需要频繁执行回归测试的项目;
  3. 需要在多种平台上重复运行相同测试的场景的项目;
  4. 某些测试项目通过手工测试无法实现,或者手工成本太高;
  5. 被测软件的开发较为规范,能够保证系统的可测试性

1.自动化测试优劣势

@优势:

  • 自动化测试可以替代大量的手工机械重复性操作;
  • 自动化测试可以大幅提升回归测试的效率,非常适合敏捷开发过程;
  • 自动化测试可以更好地利用无人值守时间,去更频繁地执行测试,特别适合现在非工作时间执行测试,工作时间分析失败用例的工作模式;
  • 自动化测试可以高效实现某些手工测试无法完成或者代价巨大的测试类型,比如关键业务 7×24 小时持续运行的系统稳定性测试和高并发场景的压力测试等;
  • 自动化测试还可以保证每次测试执行的操作以及验证的一致性和可重复性,避免人为的遗漏或疏忽。

@劣势:

  • 自动测试远比手动测试脆弱,无法应对被测系统的变化,自动化测试用例的维护成本高;
  • 自动化测试用例的开发工作量远大于单次的手工测试,所以只有当开发完成的测试用例的有效执行次数大于等于 5 次时,才能收回自动化测试的成本;
  • 自动化测试仅仅能发现回归测试范围的缺陷;
  • 测试的效率很大程度上依赖自动化测试用例的设计以及实现质量,不稳定的自动化测试用例实现比没有自动化更糟糕。
  • 自动化测试开发人员必须具备一定的编程能力;
  • 实行自动化测试的初期,用例开发效率通常都很低,大量初期开发的用例通常会在整个自动化测试体系成熟,和测试工程师全面掌握测试工具后,需要重构。

2.软件开发各阶段的自动化测试技术

~单元测试的自动化技术

  • 用例框架代码生成的自动化;

  • 部分测试输入数据的自动化生成;
    例如:不正确格式/超范围的数据

  • 自动桩代码的生成;
    *必要的时候,自动化工具还需要实现 “抽桩”,以适应后续的代码级集成测试的需求。

  • 被测代码的自动化静态分析;

    *比较常用的代码静态分析工具有 Sonar 和 Coverity
    *其他代码分析工具

  • 测试覆盖率的自动统计与分析

~ Web Service 测试的自动化技术

主要是指 SOAP API 和 REST API 这两类 API 测试

  • API 自动化测试框架
  1. 测试脚手架代码的自动化生成;
    通常包含了被测试 API 的调用、测试数据与脚本的分离,以及 Response 验证的空实现。
  2. 部分测试输入数据的自动生成;
  3. Response 验证的自动化;
    通常关注的点是返回状态码(status code)、Scheme 结构以及具体的字段值
  4. 基于 SoapUI 或者 Postman 的自动化脚本生成。
    GUI 测试的自动化技术

~ GUI 测试的自动化技术

基于页面元素识别技术,对页面元素进行自动化操作,以模拟实际终端用户的行为并验证软件功能的正确性。

  • 对于传统 Web 浏览器的 GUI 自动化测试,业内主流的开源方案采用 Selenium,商业方案采用 Micro Focus 的 UFT(前身是 HP 的 QTP);
  • 对于移动端原生应用,通常采用主流的 Appium,它对 iOS 环境集成了 XCUITest,对 Android 环境集成了 UIAutomator 和 Espresso。

四、单元测试

单元测试是指,对软件中的最小可测试单元在与程序其他部分相隔离的情况下进行检查和验证的工作,这里的最小可测试单元通常是指函数或者类。

1. 输入数据

  • 被测试函数的输入参数;

  • 被测试函数内部需要读取的全局静态变量;

  • 被测试函数内部需要读取的成员变量;

  • 函数内部调用子函数获得的数据;

  • 函数内部调用子函数改写的数据;

  • 嵌入式系统中,在中断调用时改写的数据;

    2.预计输出 —— 必须严格根据代码的功能逻辑来设定

  • 被测试函数的返回值;

  • 被测试函数的输出参数;

  • 被测试函数所改写的成员变量;

  • 被测试函数所改写的全局变量;

  • 被测试函数中进行的文件更新;

  • 被测试函数中进行的数据库更新;

  • 被测试函数中进行的消息队列更新;

3.驱动代码、桩代码、Mock代码

  1. 驱动代码(Driver)
    指调用被测函数的代码

  2. 桩代码(Stub)
    是用来代替真实代码的临时代码

  • 起到了隔离和补齐的作用
  • 具有控制被测函数执行路径的作用

编写桩代码原则

  1. 桩函数要具有与原函数完全相同的原形,仅仅是内部实现不同;
  2. 用于实现隔离和补齐的桩函数比较简单,只需保持原函数的声明,加一个空的实现,目的是通过编译链接;
  3. 实现控制功能的桩函数是应用最广泛的,要根据测试用例的需要,输出合适的数据作为被测函数的内部输入。

Mock代码与桩代码的区别: 测试期待结果的验证
参考文献:参考马丁·福勒(Martin Fowler)–《Mock 代码不是桩代码》(Mocks Aren’t Stubs)

  • 对于 Mock 代码来说,我们的关注点是 Mock 方法有没有被调用,以什么样的参数被调用,被调用的次数,以及多个 Mock 函数的先后调用顺序。所以,在使用 Mock 代码的测试中,对于结果的验证(也就是 assert),通常出现在 Mock 函数中。
  • 对于桩代码来说,我们的关注点是 利用 Stub 来控制被测函数的执行路径,不会去关注 Stub 是否被调用以及怎么样被调用。 所以,你在使用 Stub 的测试中,对于结果的验证(也就是 assert),通常出现在驱动代码中。

4. 实际软件项目中如何开展单元测试 —— 通常只有底层模块或者核心模块的测试中才会采用单元测试。

  • 确定单元测试框架的选型——开发语言直接相关。比如,Java 最常用的单元测试框架是 Junit 和 TestNG;C/C++ 最常用的单元测试框架是 CppTest 和 Parasoft C/C++test;
  • 框架选型完成后,需要对桩代码框架和 Mock 代码框架选型,*选型的主要依据是开发所采用的具体技术栈。*通常,单元测试框架、桩代码 /Mock 代码的选型工作由开发架构师和测试架构师共同决定。
  • 为了能够衡量单元测试的代码覆盖率,需要引入计算代码覆盖率的工具。不同的语言会有不同的代码覆盖率统计工具,比如 Java 的 JaCoCo,JavaScript 的 Istanbul。
  • 需要把单元测试执行、代码覆盖率统计和持续集成流水线做集成,以确保每次代码递交,都会自动触发单元测试,并在单元测试执行过程中自动统计代码覆盖率,最后以“单元测试通过率”和“代码覆盖率”为标准来决定本次代码递交是否能够被接受。

代码级集成测试:
1.代码级集成测试也是针对代码层级,但其属于自动化测试范畴。与单元测试最大的区别只是,代码级集成测试中被测函数内部调用的其他函数必须是真实的,不允许使用桩代码代替,而单元测试中允许使用桩代码来模拟内部调用的其他函数。
2.代码级集成测试对测试框架的要求非常高,这个框架除了可以顺利装载自己的软件模块外,还必须能装载其他相互依赖的模块,做到被测软件模块可运行(Runnable)。
3.代码级集成测试主要应用在早期非互联网的传统软件企业

互联网产品测试思路

互联网产品往往采用菱形模型。
菱形模型有以下四个关键点:

  1. 以中间层的 API 测试为重点做全面的测试
  2. 轻量级的 GUI 测试,只覆盖最核心直接影响主营业务流程的 E2E 场景
  3. 最上层的 GUI 测试通常利用探索式测试思维,以人工测试的方式发现尽可能多的潜在问题。
  4. 单元测试采用“分而治之”的思想,只对那些相对稳定并且核心的服务和模块开展全面的单元测试,而应用层或者上层业务只会做少量的单元测试

学习清单

  • Linux/Unix/Windows 操作系统的基础知识
  • Oracle/MySQL 等传统关系型数据库技术,NoSQL 非关系型数据库技术
  • 中间件技术
  • Shell/Python 脚本开发
  • 版本管理工具与策略
  • CI/CD 流水线设计
  • F5 负载均衡技术
  • Fiddler/Wireshark/Tcpdump 等抓包工具
  • 浏览器 Developer Tool
  • 网站架构设计 【性能测试、稳定性测试、全链路压测、故障切换(Failover)测试、动态集群容量伸缩测试、服务降级测试和安全渗透测试】{至少需要理解架构相关的基本知识以及核心原理}

分布式缓存集群
缓存击穿
缓存雪崩
缓存预热
缓存集群扩容局限性
可伸缩性架构设计
应用服务器的各种负载均衡实现的基本原理
数据库的读写分离技术

  • 容器技术——掌握 Docker 和 Kubernetes 的原理和使用方法
  • 微服务架构
  • 服务网格(Service Mesh)
  • DevOps

从深入掌握 Jenkins 之类的工具开始,到熟练应用和组合各种 plugin 来完成灵活高效的流水线搭建,之后再将更多的工具逐渐集成到流水线中以完成更多的任务。

  • 云计算——理解服务在云端部署的技术细节,如何使用云提供的基础设施以及服务

尝试用云服务去部署自己的应用,同时还可以结合云平台提供的各类服务(配置服务,数据库服务等)和自己的应用做集成。另外,建议尝试用云平台建立自己的小应用集群,体验集群规模的动态收缩与扩展。还可以尝试在云平台上直接使用 Docker 部署发布服务
尝试在云端建立自己的 Selenium Gird 集群

  • 大数据
  • 人工智能
  • 区块链技术
  • 前端应用技术

需要掌握最基本的 JavaScript、CSS、JQuery 和 HTML5 等知识,然后再去学习一些主流的前端开发框架,比如 Angular.js、Backbone.js 等。当然现在的 Node.js 的生态圈非常发达,你如果能够掌握 Node.js,那么很多东西实现起来都可以得心应手。我个人推荐从网上下载一些样例代码进行学习,同时学习使用脚手架从无到有去建立自己的前端应用。

附录

课程中涉及的名词解释
wiki

测试52讲学习总结之测试基础篇相关推荐

  1. 菜鸟学习笔记:Java基础篇5(抽象类与接口、回调函数、内部类)

    菜鸟学习笔记:Java面向对象篇下 抽象类 接口 回调函数 内部类 成员内部类 匿名内部类 抽象类 通过前面知识的学习,抽象类这个概念应该不难理解,但比较容易和后面要说的接口混淆,而且在面试中也比较爱 ...

  2. 菜鸟学习笔记:Java基础篇7(包装类、时间相关类、文件类、异常处理类)

    菜鸟学习笔记:Java其他常用类 基本数据类型包装类 时间处理和文件处理相关类 Date时间类 SimpleDateFormat Calendar日历类 文件类 异常机制 异常的概念 Java异常处理 ...

  3. 菜鸟学习笔记:Java基础篇6(数组、字符串)

    菜鸟学习笔记:Java常用类(数组.字符串) 数组 概述 数组的定义 二维数组 数组查找和排序 查找 排序 数组运用--字符串 不可变字符序列(String) 可变字符序列(StringBuilder ...

  4. 菜鸟学习笔记:Java基础篇4(面向对象三大特征)

    菜鸟学习笔记:Java面向对象篇中 继承 概念 方法重写(override) Object类 Super关键字 组合 final关键字补充 封装 访问控制符 多态 继承 概念 继续上一篇的例子: #m ...

  5. 菜鸟学习笔记:Java基础篇3(面向对象思想、程序执行过程内存分析、面向对象重要概念)

    菜鸟学习笔记:Java面向对象篇上 Java面向对象的思想 Java程序执行过程内存分析 Java垃圾回收机制 构造方法 方法重载(overload) static关键字 this关键字 Java面向 ...

  6. 菜鸟学习笔记:Java基础篇2(变量、运算符、流程控制语句、方法)

    菜鸟学习笔记:Java基础篇2 变量 基本概念 变量作用域 final关键字 运算符 算术运算符 比较运算符 逻辑运算符 位运算符 赋值运算符 条件运算符 运算符优先级 Java三种流程控制语句 顺序 ...

  7. 深度学习word2vec笔记之基础篇

    深度学习word2vec笔记之基础篇 声明: 1)该博文是多位博主以及多位文档资料的主人所无私奉献的论文资料整理的.具体引用的资料请看参考文献.具体的版本声明也参考原文献 2)本文仅供学术交流,非商用 ...

  8. Vue学习之路(基础篇)

    Vue学习之路(基础篇)

  9. invader的java学习第三天基础篇

    invader的java学习第三天基础篇 一.整数的取值范围表 类型名称 数据类型 所占空间 表数范围 字节型 byte 1字节 -128-127 短整型 short 2字节 +-3w(-2^15-2 ...

最新文章

  1. 条款9:不要在构造和析构过程中调用virtual函数
  2. 点(Dot)与像素(Pixel)的区别
  3. LeetCode 523. Continuous Subarray Sum
  4. Spring AOP知识详解
  5. c语言编程车速里程测量,电子车速里程表设计开题报告.doc
  6. java遍历map集合_Java 遍历Map集合
  7. 2019_WSDM_Session-Based Social Recommendation via Dynamic Graph Attention Networks
  8. 图像特征提取现成的方法
  9. 用函数画出可爱的卡通猫
  10. 谁说码农不懂浪漫?(js写的'老婆生日快乐'特效)
  11. 设计模式 - 创建型模式_工厂方法模式
  12. 梅森数形如2 ​n ​​ −1的素数称为梅森数(Mersenne Number)。例如2 ​2 ​​ −1=3、2 ​3 ​​ −1=7都是梅森数。1722年,双目失明的瑞士数学大师欧拉证明了2 ​3
  13. ios手机python编译器免费_适用与IOS手机的python编辑器,让你不限空间,地点都能玩转pyhton代码 !...
  14. 【Java基础】集合总结(三)——Queue集合、Map集合
  15. html果壳网文本框,打造你的个人网站:CSS来助你美化页面
  16. Linux centOS学习笔记(文件处理命令)
  17. 泡面吧” “计蒜客” 挑战难题 第16题:爬楼梯
  18. 2.45GHz天线初始尺寸设定
  19. 华为交换机实现mac地址与ip地址一一绑定
  20. 小学奥数思维训练题(五)

热门文章

  1. curl配置host
  2. mysql 培训天通苑_天通苑
  3. 用Canvas制作剪纸效果
  4. 华清远见-重庆中心-前端阶段技术总结
  5. php实现换一换功能
  6. window.localStorage.setItem的理解与使用
  7. 使用localStorage存储数据每次调用setItem()它都会添加或覆盖现有值
  8. 第六章 Linux 文件与目录配置
  9. vim配置及插件安装管理(超级详细)
  10. 将其他程序中的大纲文本插入到 PowerPoint 演示文稿中