From 7e90279a2b608ed91b33300f01081efb2f151305 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Tue, 14 Sep 2021 10:02:04 +0800 Subject: [PATCH 01/30] =?UTF-8?q?=E6=8C=89=E8=A2=81=E5=B8=85=E4=BF=AE?= =?UTF-8?q?=E6=94=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .DS_Store | Bin 8196 -> 8196 bytes README.md | 137 +++++++++++++++++++++++++++--------------------------- 2 files changed, 68 insertions(+), 69 deletions(-) diff --git a/.DS_Store b/.DS_Store index d6f7925d3dc71334773cbf73508839ab1382c98b..a9d5eb04e5fcb8704779b43f4aefa75b089e5836 100644 GIT binary patch delta 88 zcmZp1XmOa}&nU7nU^hRb$YvgaUKUdxh9Cx421f=L245hp%TUQs%%I1R%aG!klb@WF jlb^)Ez#zcDzzC!m{=>lLX(E=)o7pA4v1~pn!p;l;2k{#1 delta 40 wcmZp1XmOa}&nUbxU^hRb@Ma!?UY5-lMa-BdHdt(Cm-xoA*;Mor)5Hc-025pdxBvhE diff --git a/README.md b/README.md index 9815ab9..66f6e73 100644 --- a/README.md +++ b/README.md @@ -17,7 +17,7 @@ 学时安排:72课时(理论36+实践36) 教材:清华大学出版社 《软件测试》(第2版) 周元哲 编著 ### 4 课程资源 -* 课程内容文档 [gitee课程地址](https://gitee.com/XiaFuXiangFei/software-testing) +* 课程内容文档 [gitee 课程地址](https://gitee.com/XiaFuXiangFei/software-testing) * 课程思维导图 * 测试相关文档模板 * 测试工具:[禅道](http://zentao.zrise.top/) @@ -29,12 +29,12 @@ **软件 ≠ 程序(代码)** 软件包含如下内容: 1. 运行时,能够提供所要求功能和性能的指令或计算机程序。 -2. 程序能够处理信息的数据结构 -3. 描述程序功能需求、程序如何操作和如何使用所要求的文档 +2. 程序能够处理信息的数据结构。 +3. 用于描述程序功能需求、程序如何操作和如何使用的文档。 #### 1.1.2 文档 ##### 开发文档 -开发文档是描述软件开发过程,包括软件需求、软件设计、软件测试、保证软件质量的一类文档,开发文档也包括软件的详细技术描述、程序逻辑程序间相互关系、数据格式和存储等。 +开发文档是描述软件开发过程,包括软件需求、软件设计、软件测试、保证软件质量的一类文档,开发文档也包括软件的详细技术描述、程序逻辑、程序间相互关系、数据格式和存储等。 * 《可行性研究》 * 《项目任务书》 @@ -46,7 +46,7 @@ * 《开发计划》 ##### 管理文档 -从管理的角度规定涉及软件生存的信息: +从管理的角度规定涉及软件生存的信息: 1. 职责定义 2. 开发过程的每个阶段的进度和进度变更的记录 3. 软件变更情况的记录 @@ -60,7 +60,7 @@ * 《实施方案》 ##### 产品文档 -为使用和运行软件产品的任何人规定培训和参考信息,促进软件产品的市场流通或提高可接受性。使得那些未参加开发本软件的程序员维护它。 +为使用和运行软件产品的任何人规定培训和参考信息,促进软件产品的市场流通或提高可接受性。使得那些未参加开发本软件的程序员维护它。 * 《产品手册》 * 《用户指南》 @@ -84,27 +84,27 @@ ### 1.2 软件生命周期 1. 需求定义 -**描述:** 定义出本次任务都需要做什么,做成什么样子 -**参与者:** 产品经理,需求分析,客户 +**描述:** 定义出本次任务都需要做什么,做成什么样子。 +**参与者:** 产品经理、需求分析、客户 2. 可行性分析 -**描述:** 由项目组相关成员去研究需求是否可行,能不能做出来 -**参与者:** 产品经理,架构师,项目经理,开发 +**描述:** 由项目组相关成员去研究需求是否可行,能不能做出来。 +**参与者:** 产品经理、架构师、项目经理、开发 3. 需求分析 -**描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个框每个按钮的样式,输入输出等各项值 -**参与者:** 产品经理,架构师,项目经理,测试/质量管理员(很多公司把这个统称为QA),开发 +**描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个框每个按钮的样式,输入输出等各项值。 +**参与者:** 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发 **输出:**《需求规格说明书》 4. 评审 -**描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与 +**描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。 **参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等 5. 设计 -**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口参数、参数等。此处设计会形成概要设计文档和详细设计文档 -**参与者:** 项目经理,架构师,开发,测试 +**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口参数、参数等。此处设计会形成概要设计文档和详细设计文档。 +**参与者:** 项目经理、架构师、开发、测试 6. 编码 -**描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现 +**描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。 **参与者:** 开发 7. 提测 -**描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具任务流方式向测试部门通知xxx模块/功能可以测试 -**参与者:** 任务责任人(开发)、测试 +**描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具任务流方式向测试部门通知xxx模块/功能可以测试。 +**参与者:** 任务责任人(开发)、测试 8. 测试 - 测试需求 - 测试计划 @@ -113,8 +113,8 @@ - 回归测试 - 测试评估 9. 部署/发版 -**描述:** 经过前面的各个阶段,产品已经可以出售或者面见大众了;配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 -**参与人:** 配置管理人员,测试 +**描述:** 经过前面的各个阶段,产品已经可以出售或者面见大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 +**参与人:** 配置管理人员、测试 10. 支持维护 **描述:** 支持维护类似于我们日常中的售后,主要是对已卖出的产品/已上线的项目进行日常维护。包括纠错性维护和改进性维护两个方面。 **参与人:** 支持维护人员/售后工程师 @@ -122,12 +122,11 @@ ### 1.3 软件测试概述 #### 1.3.1 软件测试定义 软件测试的经典定义是:在规定的条件下对程序进行操作,以发现程序错误,衡量软件质量,并对其是否能满足设计要求进行评估的过程。 - -IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别 +IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。 #### 1.3.2 测试发展历程 1. 1957年之前-调试为主(Debugging Oriented) -软件规模小,复杂度低,开发人员承担需求分析,设计,开发,测试等所有工作,等同于调试。 +软件规模小,复杂度低,开发人员承担需求分析、设计、开发、测试等所有工作,等同于调试。 2. 1957–1978-证明为主(Demonstration Oriented) 与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。 3. 1979–1982-破坏为主(Destruction Oriented) @@ -138,7 +137,7 @@ The process of executing a program with the intent of finding errors. ``` 这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。 4. 1983–1987-评估为主(Evaluation Oriented) -软件行业进入了大发展时期,软件趋向大型化、到复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析,评审,测试来评估产品的理论。 +软件行业进入了大发展时期,软件趋向大型化、复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 5. 1988–至今-预防为主(Prevention Oriented) 尽量早的介入,尽量早的发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 @@ -165,7 +164,7 @@ The process of executing a program with the intent of finding errors. **优点:** 相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。 **缺点:** -虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析,系统设计的验证,时间效率上也大打折扣。 +虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。 ##### W模型(双V模型) ![W模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/w-model.png) @@ -173,7 +172,7 @@ The process of executing a program with the intent of finding errors. **优点:** W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。 **缺点:** -W 模型是顺序性的,不可逆,需求的变更和调整,依旧不方便。 +W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。 ##### 螺旋模型 ![螺旋模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/lx-model.png) @@ -223,7 +222,7 @@ W 模型是顺序性的,不可逆,需求的变更和调整,依旧不方便 ### 1.4 软件缺陷 #### 1.4.1 缺陷定义 -IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 +IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 符合下面4个条件之一就是缺陷 1. 软件未达到规格说明书中规定的功能 @@ -232,10 +231,10 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 4. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。 #### 1.4.2 产生原因 -1. 软件本身复杂性,产生大量不确定因素 +1. 软件本身复杂性,产生大量不确定因素。 2. 成本、时间限制,导致流程不够完善,文档缺失,缺乏严谨的评审。 -3. 人员本身技能水平,责任心,交流沟通不顺畅 -4. 不全面或者没有复审 +3. 人员本身技能水平、责任心、交流沟通不顺畅。 +4. 不全面或者没有复审。 #### 1.4.3 缺陷来源 | 缺陷来源 | 描述 | @@ -250,10 +249,10 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 | 缺陷类型 | 描述 | | -------- | ------------------------------------------------ | | 功能 | 未达到规格说明书中规定的功能,影响系统使用 | - | 用户界面 | 为按照原型设计,影响交互,如:显示格式,按钮位置 | + | 用户界面 | 未按照原型设计,影响交互,如:显示格式,按钮位置 | | 文档 | 文档内容不完整或不正确,影响发布和维护 | | 软件包 | 由于软件配置库、变更管理或版本控制引发的错误 | - | 性能 | 执行时间,处理速度,负载等方面 | + | 性能 | 执行时间、处理速度、负载等方面 | | 接口 | 与其他模块参数不匹配 | #### 1.4.5 缺陷级别 @@ -261,11 +260,11 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 **优先级:** 表示修复缺陷的重要程度和紧迫程度。 ##### 严重性 -| 级别 | 名称 | 说明 | 示例 | -| :---: | :------: | :----------------------------------------: | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | -| S1 | 致命错误 | 严重阻碍开发或测试工作的进行,必须马上解决 | 安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件 | -| S2 | 严重缺陷 | 系统出现重大问题,影响提供的主要功能使用 | 内存泄露
数据无法保存 | -| S3 | 主要错误 | 主要功能实现有问题,易用性不够好 | 某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码 | +| 级别 | 名称 | 说明 | 示例 | +| :---: | :------: | :----------------------------------------: | ---- | +| S1 | 致命错误 | 严重阻碍开发或测试工作的进行,必须马上解决 | 安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件 | +| S2 | 严重缺陷 | 系统出现重大问题,影响提供的主要功能使用 | 内存泄露
数据无法保存 | +| S3 | 主要错误 | 主要功能实现有问题,易用性不够好 | 某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码 | | S4 | 次要错误 | 次要功能实现有问题或者手册相关问题 | 个别不常用的属性不生效或实现有问题(前提:不影响主要功能使用)
次要功能实现与需求不符或实现有问题(如:日志不能轮转、预警策略不生效、搜索框不能用、快照生成格式有问题等)
错别字
手册描述不合理或样式格式有问题 | | S5 | 轻微缺陷 | 建议,不属于缺陷 | @@ -291,12 +290,12 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 #### 1.4.6 跟踪流程 最优化、最简单的生命周期是:(理想情况) -1. 测试员发现缺陷并记录缺陷报告 -2. 缺陷报告交给程序员,此时缺陷状态是打开(open state) -3. 程序员修改缺陷,此时缺陷状态是解决(resolved state) -4. 缺陷报告交还测试员 -5. 测试员确认已修复 -6. 测试员关闭缺陷报告,此时缺陷状态是关闭(closed state) +1. 测试员发现缺陷并记录缺陷报告。 +2. 缺陷报告交给程序员,此时缺陷状态是打开。(open state) +3. 程序员修改缺陷,此时缺陷状态是解决。(resolved state) +4. 缺陷报告交还测试员。 +5. 测试员确认已修复。 +6. 测试员关闭缺陷报告,此时缺陷状态是关闭。(closed state) 一个缺陷很可能会被反复打开→关闭。在日常工作过程中,由于开发修订其他缺陷影响、需求变更等因素缺陷可能会被反复打开→关闭。 @@ -318,7 +317,7 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 3. bug严重级别,优先级:作为缺陷是否修复以及缺陷修复优先级的决定性因素。 4. bug产生的模块:记录bug所属模块,方便开发定位问题。 5. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题。 -6. bug描述:bug的产生环境、详细步骤,期望结果、实际结果。 +6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。 7. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。 以上是上报bug(创建)bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: 8. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 @@ -341,17 +340,17 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量1。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。 -从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”;于是,软件产品在没有经过严格测试的情况下就发布了;对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象;定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 +从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 当前国内软件测试行业主要存在以下问题: -1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题; -2. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步; -3. 对于分布式系统整体性能还难以进行很好的测试; -4. 对于实时系统缺乏有效的测试手段; -5. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题; -6. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合; -7. 缺乏软件测试意识、对其重视不够; -8. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准; +1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题。 +2. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步。 +3. 对于分布式系统整体性能还难以进行很好的测试。 +4. 对于实时系统缺乏有效的测试手段。 +5. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题。 +6. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合。 +7. 缺乏软件测试意识、对其重视不够。 +8. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准。 9. 高校从师资储备到专业设置再到人才培养的机制薄弱。 国内外软件测试差距 @@ -372,7 +371,7 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 - 敏捷测试专家 - 高级测试开发专家 - 专项测试专家 - - QAOps专家 + - QA-Ops 专家 2. 管理方向 - 测试组长 - 测试经理 @@ -395,7 +394,7 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 2. 存在太多无法测试的东西 3. 软件开发完成后才进行测试 4. 软件发布后发现质量问题,是测试人员的问题 -5. 软件测试很简单,就是点点点,是个人就能做 +5. 软件测试很简单,就是点点点,是个人就能做 6. 软件测试是测试人员的事情和程序员无关 7. 项目进度吃紧时少做测试,时间多时多做测试 8. 测试要进行穷尽测试 @@ -412,24 +411,24 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 ### 2.1 概述 1. 从软件测试的目的来理解 软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。 -2. 从软件测试的性质来理解 -在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的” -3. 从软件开发角度来理解 -软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障 +2. 从软件测试的性质来理解 +在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的”。 +3. 从软件开发角度来理解 +软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障。 4. 从软件工程角度来理解 -软件测试是软件工程的一部分,是软件工程过程中的重要阶段 +软件测试是软件工程的一部分,是软件工程过程中的重要阶段。 5. 从软件质量保证角度来理解 -软件测试是软件质量保证的重要措施 +软件测试是软件质量保证的重要措施。 ### 2.2 测试的目的和原则 #### 2.2.1 测试的目的 -1. 测试不仅仅是找出错误,通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进 +1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进 2. 检测产品是否符合用户要求 3. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法 4. 提升用户体验 #### 2.2.2 测试的原则 -1. 软件测试是证伪而非证真 +1. 软件测试是证伪而非证实 2. 尽早地、不断地进行测试 3. 重视无效数据和非预期的测试 4. 应当对每一个测试结果做全面的检查 @@ -447,12 +446,12 @@ IEEE729-1983对缺陷有一个标准的定义:从产品内部看,缺陷是 5. 验收测试 软件测试阶段对照表: -|测试阶段|主要依据|参与人员/测试方式|主要测试内容| -|----|----|----|----| -|单元测试|《详细设计》|开发小组执行白盒测试|规范、逻辑、路径| -|集成测试|《概要设计》
《需求文档》|开发小组执行白盒测试、黑盒测试|接口、路径、功能、性能| -|系统测试|《需求文档》|独立测试小组执行黑盒测试|功能测试、界面测试、安全测试、兼容性测试、易用性测试、性能测试、压力测试、负载测试| -|验收测试|《需求文档》|用户执行黑盒测试|同上| +| 测试阶段 | 主要依据 | 参与人员/测试方式 | 主要测试内容 | +| -------- | ---------------------------- | ------------------------------ | ---------------------------------------------------------------------------------- | +| 单元测试 | 《详细设计》 | 开发小组执行白盒测试 | 规范、逻辑、路径 | +| 集成测试 | 《概要设计》
《需求文档》 | 开发小组执行白盒测试、黑盒测试 | 接口、路径、功能、性能 | +| 系统测试 | 《需求文档》 | 独立测试小组执行黑盒测试 | 功能测试、界面测试、安全测试、兼容性测试、易用性测试、性能测试、压力测试、负载测试 | +| 验收测试 | 《需求文档》 | 用户执行黑盒测试 | 同上 | #### 2.3.2 按照执行状态划分 1. 静态测试 -- Gitee From f71c3452302286e2522c63310a2025d027d58a1f Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Tue, 14 Sep 2021 10:23:21 +0800 Subject: [PATCH 02/30] =?UTF-8?q?=E5=9B=BE=E7=89=87=E6=8D=A2=E8=A1=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index 66f6e73..fbbd25e 100644 --- a/README.md +++ b/README.md @@ -596,7 +596,9 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 3. 设计一个新的测试用例,使其只覆盖一个无效等价类,重复这一步直到所有无效等价类均被覆盖。 #### 3.2.3 等价类举例 我们要测试学习成绩这一输入框(假设总成绩都是100),那么我们就可以如下图划分,有效的成绩是>=0且<=100的,无效的是<0和>100这两部分。 + ![等价类举例](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/dengjialei.jpg) + 另外图中还有一个无效等价类没有表现出来--非数字字符(比如:英文字母、中文、特殊的符号等单一或者组合,如a、abc、你好、你abc、你=我、\你\a\等;以及他们分别与数字组合,比如:a123、321a、你123、12你、1你2、1\2、1=你等)。 那么根据上述分析,最终设计出来的测试用例如下: @@ -631,9 +633,11 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 1. 一般边界值分析 对于含有n个变量的程序,取值为min、min+、normal,max-、max,测试用例数目为4*N+1。 ![一般边界值分析](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/bianjiezhi1.jpg) + 2. 健壮性边界值分析 健壮性边界值测试是边界值分析的一种扩展。变量除了取min、min+、normal、max-、max 5个边界值外,还要考虑略超过最大值(max+)以及略小于最小值(min-)的取值。因此,对于含有n个变量的程序,健壮性边界值分析产生6*n+1个测试用例。 ![健壮性边界值分析](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/bianjiezhi2.jpg) + #### 3.3.3 应用举例 延伸上节的例子来说明:学生信息系统中有一个“考试成绩”的输入项,成绩的取值范围是0~100之间的整数,考试成绩及格的分数线是60,优秀的分数线是80。那么这个例子中的边界值数据是哪些呢: @@ -761,6 +765,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 原因——结果图使用了简单的逻辑符号,以直线连接左右结点,左结点表示输入状态(原因),右结点表示输出状态(结果)。 ![原因 - 结果图](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/yinguotu.png) + * “恒等”:若原因出现,则结果出现;若原因不出现,则结果不出现。 * “非”:若原因出现,则结果不出现;若原因不出现,则结果出现。 * “或”:若几个原因中有一个出现,则结果出现;若几个原因都不出现,则结果不出现。 @@ -770,6 +775,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 输入输出状态相互之间存在的某些依赖关系,称为约束。 ![约束图](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/yueshutu.png) + * E(互斥):原因不会同时成立,最多1个成立,可以都不成立 * I(包含):原因中至少一个成立,不能同时为0 * O(唯一):原因中有且只有一个成立 @@ -838,6 +844,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 #### 3.6.1 ATM取款流程图 ![ATM取款流程图](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/atm.png) + #### 3.6.2 ATM取款场景设计 | 场景编号 | 流程 | 结果 | | :------: | ---------------------------------------------------------------------------------------- | -------------------- | -- Gitee From 93735f08ee10182d8693aa27d7a03723fd83d81e Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Tue, 14 Sep 2021 10:48:11 +0800 Subject: [PATCH 03/30] =?UTF-8?q?=E6=8C=89=E7=85=A7=E5=91=A8=E8=AF=9A?= =?UTF-8?q?=E7=9A=84=E4=BF=AE=E6=94=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 103 ++++++++++++++++++++++++++++-------------------------- 1 file changed, 54 insertions(+), 49 deletions(-) diff --git a/README.md b/README.md index fbbd25e..52ae92e 100644 --- a/README.md +++ b/README.md @@ -83,37 +83,37 @@ 6. 过程管理重要 ### 1.2 软件生命周期 -1. 需求定义 +#### 1.2.1 需求定义 **描述:** 定义出本次任务都需要做什么,做成什么样子。 **参与者:** 产品经理、需求分析、客户 -2. 可行性分析 +#### 1.2.2 可行性分析 **描述:** 由项目组相关成员去研究需求是否可行,能不能做出来。 **参与者:** 产品经理、架构师、项目经理、开发 -3. 需求分析 -**描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个框每个按钮的样式,输入输出等各项值。 +#### 1.2.3 需求分析 +**描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个输入框、每个按钮的样式,输入输出等各项值。 **参与者:** 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发 **输出:**《需求规格说明书》 -4. 评审 +#### 1.2.4 评审 **描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。 **参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等 -5. 设计 -**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口参数、参数等。此处设计会形成概要设计文档和详细设计文档。 +#### 1.2.5 设计 +**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。 **参与者:** 项目经理、架构师、开发、测试 -6. 编码 +#### 1.2.6 编码 **描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。 **参与者:** 开发 -7. 提测 -**描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具任务流方式向测试部门通知xxx模块/功能可以测试。 +#### 1.2.7 提测 +**描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。 **参与者:** 任务责任人(开发)、测试 -8. 测试 +#### 1.2.8 测试 - 测试需求 - 测试计划 - 测试设计 - 测试执行 - 回归测试 - 测试评估 -9. 部署/发版 -**描述:** 经过前面的各个阶段,产品已经可以出售或者面见大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 +#### 1.2.9 部署/发版 +**描述:** 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 **参与人:** 配置管理人员、测试 10. 支持维护 **描述:** 支持维护类似于我们日常中的售后,主要是对已卖出的产品/已上线的项目进行日常维护。包括纠错性维护和改进性维护两个方面。 @@ -142,42 +142,45 @@ The process of executing a program with the intent of finding errors. 尽量早的介入,尽量早的发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 #### 1.3.3 测试与开发的关系 -##### 瀑布模型 +**瀑布模型** ![瀑布模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/pb-model.png) 这是一种经典模型,提供了软件开发的基本框架。 强调开发工作(计划、设计、开发、测试、维护等)各阶段之间的先后顺序,不可以并行操作。 瀑布模型认为,测试是指代码完成后,处于运行维护阶段之前。如果需求和设计上存在缺陷,就会造成大量返工,增加成本。为了更早的发现问题,测试应延伸到需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。 -**优点:** +**优点:** 1. 各阶段划分清晰 2. 强调计划与需求分析 3. 适合需求稳定的产品开发 -**缺点:** +**缺点:** 1. 单一流程,不可逆 2. 风险显露得晚,纠正机会少 3. 测试只是其中一个阶段,缺乏全过程测试思想 -##### V模型 + +**V模型** ![V模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/v-model.png) 强调将测试和开发同等重要,对于开发阶段都有与之对应的测试阶段。 -**优点:** +**优点:** 相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。 -**缺点:** -虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。 -##### W模型(双V模型) +**缺点:** +虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。 + +**W模型(双V模型)** ![W模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/w-model.png) 明确表示出了测试与开发的并行关系 **优点:** W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。 **缺点:** -W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。 -##### 螺旋模型 +W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。 + +**螺旋模型** ![螺旋模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/lx-model.png) 大型软件项目通常有很多不确定性和风险,如果采用瀑布式线性过程模型,失败风险很大,因此需要采取一种渐进式的演化过程模型。将产品分解成增量版本,每个版本单独测试。 -##### 敏捷模型 +**敏捷模型** ![敏捷模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/mj-model.png) 敏捷开发以用户的需求进化为核心,采用迭代、循序渐进的方法进行软件开发。专注于交付对客户有价值的软件(可以工作的)。 @@ -202,17 +205,17 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 **解读:** -* 个体和互动高于流程和工具 +* 个体和互动高于流程和工具 以人为本,没有比面对面交流更高效的沟通渠道了,基于互相信任的前提,敏捷提倡自治的全功能团队。 在工作形式上,整个团队平时坐在一起工作,从物理空间上创造了更加便捷面对面的沟通机会。在团队职责上,团队内部具备完成软件交付的角色(能力),团队所有人对软件的质量负责,开发过程由团队内部把控,业务价值团队内部快速流动,在任何环节都能及时获得反馈。同时,每个角色都更容易从全局视角去思考软件,避免了传统部门墙模式下的视角割裂和协作障碍。 -* 工作的软件高于详尽的文档 +* 工作的软件高于详尽的文档 为客户交付可工作的软件是我们的核心目标,我们应该尽早交付可进行端到端测试的代码,该目标决定了我们不应该花过多精力在面面俱到的文档上,但这不代表我们要抵制任何文档。实践证明,轻量级的文档策略有助于团队高质量交付可工作的软件。 -* 客户合作高于合同谈判 +* 客户合作高于合同谈判 主动拥抱变化,及时响应,持续交付。 -* 响应变化高于遵循计划 +* 响应变化高于遵循计划 通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费 **缺点:** @@ -252,7 +255,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | 用户界面 | 未按照原型设计,影响交互,如:显示格式,按钮位置 | | 文档 | 文档内容不完整或不正确,影响发布和维护 | | 软件包 | 由于软件配置库、变更管理或版本控制引发的错误 | - | 性能 | 执行时间、处理速度、负载等方面 | + | 性能 | 执行时间长、处理速度慢、负载高等方面 | | 接口 | 与其他模块参数不匹配 | #### 1.4.5 缺陷级别 @@ -277,7 +280,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | P3 | 高 | 影响整个测试的继续进行,要马上修改 | | P4 | 急 | 系统无法继续执行下去,必须立即修改 | -严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为1这样的缺陷着手,而不是优先修复简单的,有简到难。 +严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为1这样的缺陷着手,而不是优先修复简单的,由简到难。 综合使用重要性等级和严重性双标准的优先顺序: @@ -319,13 +322,15 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 5. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题。 6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。 7. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。 -以上是上报bug(创建)bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: -8. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 -9. bug修订人:bug修订人员。 -10. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。 -11. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。 -12. bug复测说明:由复测人员来写,说明复测过程,复测结果等。 -13. bug备注:备注,以便记录一些额外信息。 + +以上是上报bug、创建bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: + +1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 +2. bug修订人:bug修订人员。 +3. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。 +4. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。 +5. bug复测说明:由复测人员来写,说明复测过程,复测结果等。 +6. bug备注:备注,以便记录一些额外信息。 #### 1.4.8 缺陷预防 差错:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) @@ -422,20 +427,20 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 ### 2.2 测试的目的和原则 #### 2.2.1 测试的目的 -1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进 -2. 检测产品是否符合用户要求 -3. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法 -4. 提升用户体验 +1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进。 +2. 检测产品是否符合用户要求。 +3. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法。 +4. 提升用户体验。 #### 2.2.2 测试的原则 -1. 软件测试是证伪而非证实 -2. 尽早地、不断地进行测试 -3. 重视无效数据和非预期的测试 -4. 应当对每一个测试结果做全面的检查 -5. 测试现场保护和资料归档 -6. 程序员应避免检查自己的程序 -7. 充分注意测试中的集群现象 -8. 用例要定期评审,适时补充修改用例 +1. 软件测试是证伪而非证实。 +2. 尽早地、不断地进行测试。 +3. 重视无效数据和非预期的测试。 +4. 应当对每一个测试结果做全面的检查。 +5. 测试现场保护和资料归档。 +6. 程序员应避免检查自己的程序。 +7. 充分注意测试中的集群现象。 +8. 用例要定期评审,适时补充修改用例。 ### 2.3 测试分类 #### 2.3.1 按照测试阶段划分 -- Gitee From 62ca084b69116e3054c243d12e198aae895e0907 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Tue, 14 Sep 2021 11:00:03 +0800 Subject: [PATCH 04/30] =?UTF-8?q?=E9=9F=A9=E6=99=93=E5=BD=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 33 ++++++++++++++++++--------------- 1 file changed, 18 insertions(+), 15 deletions(-) diff --git a/README.md b/README.md index 52ae92e..b56ecbe 100644 --- a/README.md +++ b/README.md @@ -68,7 +68,7 @@ * 《软件支持手册》 #### 1.1.3 软件发展史 -1. 程序设计阶段:个体化生产,专用软件,规模小功能单一,开发者即使用者。软件 = 程序 +1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。软件 = 程序 2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 3. 软件工程阶段:以软件的产品化,系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 4. 多层分布结构,面向服务架构 @@ -85,7 +85,7 @@ ### 1.2 软件生命周期 #### 1.2.1 需求定义 **描述:** 定义出本次任务都需要做什么,做成什么样子。 -**参与者:** 产品经理、需求分析、客户 +**参与者:** 产品经理、需求分析师、客户 #### 1.2.2 可行性分析 **描述:** 由项目组相关成员去研究需求是否可行,能不能做出来。 **参与者:** 产品经理、架构师、项目经理、开发 @@ -97,7 +97,7 @@ **描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。 **参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等 #### 1.2.5 设计 -**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。 +**描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此基础上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。 **参与者:** 项目经理、架构师、开发、测试 #### 1.2.6 编码 **描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。 @@ -130,12 +130,15 @@ IEEE:使用人工或自动手段来运行或测定某个软件系统的过程, 2. 1957–1978-证明为主(Demonstration Oriented) 与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。 3. 1979–1982-破坏为主(Destruction Oriented) -1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义: +1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义: + ``` The process of executing a program with the intent of finding errors. 测试是为发现错误而执行程序的过程。 ``` -这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。 + +这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。 + 4. 1983–1987-评估为主(Evaluation Oriented) 软件行业进入了大发展时期,软件趋向大型化、复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 5. 1988–至今-预防为主(Prevention Oriented) @@ -163,7 +166,7 @@ The process of executing a program with the intent of finding errors. 强调将测试和开发同等重要,对于开发阶段都有与之对应的测试阶段。 **优点:** -相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。 +相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。 **缺点:** 虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。 @@ -172,7 +175,7 @@ The process of executing a program with the intent of finding errors. 明确表示出了测试与开发的并行关系 **优点:** -W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。 +W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。 **缺点:** W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。 @@ -227,10 +230,10 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 #### 1.4.1 缺陷定义 IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 -符合下面4个条件之一就是缺陷 -1. 软件未达到规格说明书中规定的功能 -2. 软件出现了产品说明数中指明的不会出现的错误 -3. 软件功能超出了产品说明书中指明的范围 +符合下面4个条件之一就是缺陷: +1. 软件未达到规格说明书中规定的功能。 +2. 软件出现了产品说明数中指明的不会出现的错误。 +3. 软件功能超出了产品说明书中指明的范围。 4. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。 #### 1.4.2 产生原因 @@ -364,14 +367,14 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 3. 测试工具的使用 4. 测试人员的培养 -#### 1.5.3 未来趋势 -1. 以软件为代表的计算机行业正在以一种井喷式的发展趋势 +#### 1.5.2 未来趋势 +1. 以软件为代表的计算机行业正在以一种井喷式的趋势发展 2. 人才缺口大 3. 女性员工受到青睐 4. 未来发展空间大 5. 外包为主 -#### 1.5.2 软件测试职业发展 +#### 1.5.3 软件测试职业发展 1. 技术方向 - 敏捷测试专家 - 高级测试开发专家 @@ -386,7 +389,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 - 项目经理 - 产品经理 -#### 1.5.3 测试思维方式 +#### 1.5.4 测试思维方式 1. 逆向思维方式 2. 组合思维方式 3. 全局思维方式 -- Gitee From 1795da980a74e1d51c45ae1f706b97a573173584 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Tue, 14 Sep 2021 11:03:57 +0800 Subject: [PATCH 05/30] =?UTF-8?q?=E8=AE=B8=E7=94=9C=E7=94=9C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index b56ecbe..5bd826c 100644 --- a/README.md +++ b/README.md @@ -403,16 +403,17 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 3. 软件开发完成后才进行测试 4. 软件发布后发现质量问题,是测试人员的问题 5. 软件测试很简单,就是点点点,是个人就能做 -6. 软件测试是测试人员的事情和程序员无关 -7. 项目进度吃紧时少做测试,时间多时多做测试 -8. 测试要进行穷尽测试 -9. 采样是随机抽取过程 -10. 测试和开发是对头 -11. 测试少报bug开发就会高兴点,报告也会好看点 -12. 自动化测试终会取代手工测试 -13. 规范化软件测试是增加项目成本 -14. 越多测试越有效 -15. 软件测试工作只负责项目上线/产品发布之前的部分 +6. 软件测试没有前途,只有程序员才是软件高手 +7. 软件测试是测试人员的事情和程序员无关 +8. 项目进度吃紧时少做测试,时间多时多做测试 +9. 测试要进行穷尽测试 +10. 采样是随机抽取过程 +11. 测试和开发是对头 +12. 测试少报bug开发就会高兴点,报告也会好看点 +13. 自动化测试终会取代手工测试 +14. 规范化软件测试是增加项目成本 +15. 越多测试越有效 +16. 软件测试工作只负责项目上线/产品发布之前的部分 ### 1.7 知识点总结 ## 第2章 软件测试基础知识 -- Gitee From aff6f0eea0ad9d6d7cdb2e34c71da145e9bf5642 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=91=A8=E8=AF=9A?= Date: Tue, 14 Sep 2021 18:47:33 +0800 Subject: [PATCH 06/30] add preview --- .DS_Store | Bin 8196 -> 6148 bytes README.html | 2063 +++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 2063 insertions(+) create mode 100644 README.html diff --git a/.DS_Store b/.DS_Store index a9d5eb04e5fcb8704779b43f4aefa75b089e5836..f164f471049cc4843ce648fc54f74f0a1c69533f 100644 GIT binary patch delta 121 zcmZp1XfcprU|?W$DortDU=RQ@Ie-{MGjUEV6q~50$jH7iU^gQp`(z#g?akprx{RAI zikLBPY{+F?%+A3f$P82p1OnVZ!WE=zW8rt^$^0^oAY&OA85meVG!w*Ju-N8!o;l0_ DH+`AHyCfOtI+>-`4?AtDG(jSVLYGn=Y|)gxO4 zG>?ZNh{2V?k->$*7f9 + + +README.md + + + + + + + + + + + + +

软件测试

+

写在最前面

+

1 课程目标

+
    +
  • 掌握基础的软件测试理论、测试方法和策略
  • +
  • 掌握常用工具使用
  • +
  • 根据需求和设计文档独立编写测试计划、测试方案、测试用例以及测试报告
  • +
+

2 主要内容

+
    +
  • 软件测试基础知识
  • +
  • 软件测试通用技术
  • +
  • 软件测试流程
  • +
  • 黑盒测试
  • +
  • 白盒测试
  • +
  • 性能测试
  • +
  • 软件测试自动化
  • +
  • 软件测试管理
  • +
+

3 课程安排

+

学时安排:72课时(理论36+实践36)
+教材:清华大学出版社 《软件测试》(第2版) 周元哲 编著

+

4 课程资源

+ +

第1章 软件测试概论

+

1.1 软件

+

1.1.1 软件定义

+

软件是一系列按照特定顺序组织的计算机数据和指令的集合。
+软件 ≠ 程序(代码)
+软件包含如下内容:

+
    +
  1. 运行时,能够提供所要求功能和性能的指令或计算机程序。
  2. +
  3. 程序能够处理信息的数据结构。
  4. +
  5. 用于描述程序功能需求、程序如何操作和如何使用的文档。
  6. +
+

1.1.2 文档

+
开发文档
+

开发文档是描述软件开发过程,包括软件需求、软件设计、软件测试、保证软件质量的一类文档,开发文档也包括软件的详细技术描述、程序逻辑、程序间相互关系、数据格式和存储等。

+
    +
  • 《可行性研究》
  • +
  • 《项目任务书》
  • +
  • 《需求规格说明书》
  • +
  • 《概要设计》
  • +
  • 《详细设计》
  • +
  • 《代码规范说明书》
  • +
  • 《数据字典》
  • +
  • 《开发计划》
  • +
+
管理文档
+

从管理的角度规定涉及软件生存的信息:

+
    +
  1. 职责定义
  2. +
  3. 开发过程的每个阶段的进度和进度变更的记录
  4. +
  5. 软件变更情况的记录
  6. +
  7. 相对于开发的判定记录
  8. +
+
    +
  • 《工作报告》
  • +
  • 《工作日志》
  • +
  • 《会议记录》
  • +
  • 《里程碑报告》
  • +
  • 《软件项目配置管理计划》
  • +
  • 《实施方案》
  • +
+
产品文档
+

为使用和运行软件产品的任何人规定培训和参考信息,促进软件产品的市场流通或提高可接受性。使得那些未参加开发本软件的程序员维护它。

+
    +
  • 《产品手册》
  • +
  • 《用户指南》
  • +
  • 《培训手册》
  • +
  • 《软件支持手册》
  • +
+

1.1.3 软件发展史

+
    +
  1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。软件 = 程序
  2. +
  3. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。
  4. +
  5. 软件工程阶段:以软件的产品化,系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。
  6. +
  7. 多层分布结构,面向服务架构
  8. +
+

1.1.4 软件项目

+

软件项目是一种特殊的项目,具有如下特点:

+
    +
  1. 知识密集型,技术含量高
  2. +
  3. 涉及多个专业领域,多种技术综合应用
  4. +
  5. 项目范围和目标的灵活性
  6. +
  7. 风险大,收益大
  8. +
  9. 客户化程度高
  10. +
  11. 过程管理重要
  12. +
+

1.2 软件生命周期

+

1.2.1 需求定义

+

描述: 定义出本次任务都需要做什么,做成什么样子。
+参与者: 产品经理、需求分析师、客户

+

1.2.2 可行性分析

+

描述: 由项目组相关成员去研究需求是否可行,能不能做出来。
+参与者: 产品经理、架构师、项目经理、开发

+

1.2.3 需求分析

+

描述: 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个输入框、每个按钮的样式,输入输出等各项值。
+参与者: 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发
+输出:《需求规格说明书》

+

1.2.4 评审

+

描述: 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。
+参与者: 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等

+

1.2.5 设计

+

描述: 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此基础上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。
+参与者: 项目经理、架构师、开发、测试

+

1.2.6 编码

+

描述: 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。
+参与者: 开发

+

1.2.7 提测

+

描述: 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。
+参与者: 任务责任人(开发)、测试

+

1.2.8 测试

+
- 测试需求
+- 测试计划
+- 测试设计
+- 测试执行
+- 回归测试
+- 测试评估
+
+

1.2.9 部署/发版

+

描述: 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。
+参与人: 配置管理人员、测试 +10. 支持维护
+描述: 支持维护类似于我们日常中的售后,主要是对已卖出的产品/已上线的项目进行日常维护。包括纠错性维护和改进性维护两个方面。
+参与人: 支持维护人员/售后工程师

+

1.3 软件测试概述

+

1.3.1 软件测试定义

+

软件测试的经典定义是:在规定的条件下对程序进行操作,以发现程序错误,衡量软件质量,并对其是否能满足设计要求进行评估的过程。
+IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。

+

1.3.2 测试发展历程

+
    +
  1. 1957年之前-调试为主(Debugging Oriented)
    +软件规模小,复杂度低,开发人员承担需求分析、设计、开发、测试等所有工作,等同于调试。
  2. +
  3. 1957–1978-证明为主(Demonstration Oriented)
    +与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。
  4. +
  5. 1979–1982-破坏为主(Destruction Oriented)
    +1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义:
  6. +
+
The process of executing a program with the intent of finding errors. +测试是为发现错误而执行程序的过程。 +
+

这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。

+
    +
  1. 1983–1987-评估为主(Evaluation Oriented)
    +软件行业进入了大发展时期,软件趋向大型化、复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。
  2. +
  3. 1988–至今-预防为主(Prevention Oriented)
    +尽量早的介入,尽量早的发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。
  4. +
+

1.3.3 测试与开发的关系

+

瀑布模型
+瀑布模型

+

这是一种经典模型,提供了软件开发的基本框架。
+强调开发工作(计划、设计、开发、测试、维护等)各阶段之间的先后顺序,不可以并行操作。
+瀑布模型认为,测试是指代码完成后,处于运行维护阶段之前。如果需求和设计上存在缺陷,就会造成大量返工,增加成本。为了更早的发现问题,测试应延伸到需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。
+优点:

+
    +
  1. 各阶段划分清晰
  2. +
  3. 强调计划与需求分析
  4. +
  5. 适合需求稳定的产品开发
  6. +
+

缺点:

+
    +
  1. 单一流程,不可逆
  2. +
  3. 风险显露得晚,纠正机会少
  4. +
  5. 测试只是其中一个阶段,缺乏全过程测试思想
  6. +
+

V模型
+V模型

+

强调将测试和开发同等重要,对于开发阶段都有与之对应的测试阶段。
+优点:
+相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。
+缺点:
+虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。

+

W模型(双V模型)
+W模型

+

明确表示出了测试与开发的并行关系
+优点:
+W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。
+缺点: +W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。

+

螺旋模型
+螺旋模型

+

大型软件项目通常有很多不确定性和风险,如果采用瀑布式线性过程模型,失败风险很大,因此需要采取一种渐进式的演化过程模型。将产品分解成增量版本,每个版本单独测试。 +敏捷模型
+敏捷模型

+

敏捷开发以用户的需求进化为核心,采用迭代、循序渐进的方法进行软件开发。专注于交付对客户有价值的软件(可以工作的)。

+

强调以人为核心,程序员团队和业务专家之间的紧密联系,频繁交付新的软件版本,紧凑的自我组织型团队,更注重软件开发中人的作用。

+

在敏捷开发中,软件项目在构建初期被切分成多个子项目,各个子项目的成果都经过测试,具备可视、可集成和可运行使用的特征。换言之,就是把一个大项目分为多个相互联系,但也可独立运行的小项目,并分别完成,在此过程中软件一直处于可使用状态。

+

《联盟敏捷宣言》

+
    +
  1. 最重要的是通过尽早和不断交付有价值的软件满足客户需要。
  2. +
  3. 我们欢迎需求的变化,即使在开发后期。敏捷过程能够驾驭变化,保持客户的竞争优势。
  4. +
  5. 经常交付可以工作的软件,从几星期到几个月,时间尺度越短越好。
  6. +
  7. 业务人员和开发者应该在整个项目过程中始终朝夕在一起工作。
  8. +
  9. 围绕斗志高昂的人进行软件开发,给开发者提供适宜的环境,满足他们的需要,并相信他们能够完成任务。
  10. +
  11. 在开发小组中最有效率也最有效果的信息传达方式是面对面的交谈。
  12. +
  13. 可以工作的软件是进度的主要度量标准。
  14. +
  15. 敏捷过程提倡可持续开发。出资人、开发人员和用户应该总是维持不变的节奏。
  16. +
  17. 对卓越技术与良好设计的不断追求将有助于提高敏捷性。
  18. +
  19. 简单——尽可能减少工作量的艺术至关重要。
  20. +
  21. 最好的架构、需求和设计都源自自我组织的团队。
  22. +
  23. 每隔一定时间,团队都要总结如何更有效率,然后相应地调整自己的行为。
  24. +
+

解读:

+
    +
  • +

    个体和互动高于流程和工具
    +以人为本,没有比面对面交流更高效的沟通渠道了,基于互相信任的前提,敏捷提倡自治的全功能团队。 +在工作形式上,整个团队平时坐在一起工作,从物理空间上创造了更加便捷面对面的沟通机会。在团队职责上,团队内部具备完成软件交付的角色(能力),团队所有人对软件的质量负责,开发过程由团队内部把控,业务价值团队内部快速流动,在任何环节都能及时获得反馈。同时,每个角色都更容易从全局视角去思考软件,避免了传统部门墙模式下的视角割裂和协作障碍。

    +
  • +
  • +

    工作的软件高于详尽的文档
    +为客户交付可工作的软件是我们的核心目标,我们应该尽早交付可进行端到端测试的代码,该目标决定了我们不应该花过多精力在面面俱到的文档上,但这不代表我们要抵制任何文档。实践证明,轻量级的文档策略有助于团队高质量交付可工作的软件。

    +
  • +
  • +

    客户合作高于合同谈判
    +主动拥抱变化,及时响应,持续交付。

    +
  • +
  • +

    响应变化高于遵循计划
    +通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费

    +
  • +
+

缺点:
+由于其项目周期很长,所以很难保证开发的人员不更换,而缺少文档就会造成在交接的过程中出现很大的困难。

+

敏捷开发流程

+

1.4 软件缺陷

+

1.4.1 缺陷定义

+

IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。

+

符合下面4个条件之一就是缺陷:

+
    +
  1. 软件未达到规格说明书中规定的功能。
  2. +
  3. 软件出现了产品说明数中指明的不会出现的错误。
  4. +
  5. 软件功能超出了产品说明书中指明的范围。
  6. +
  7. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。
  8. +
+

1.4.2 产生原因

+
    +
  1. 软件本身复杂性,产生大量不确定因素。
  2. +
  3. 成本、时间限制,导致流程不够完善,文档缺失,缺乏严谨的评审。
  4. +
  5. 人员本身技能水平、责任心、交流沟通不顺畅。
  6. +
  7. 不全面或者没有复审。
  8. +
+

1.4.3 缺陷来源

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
缺陷来源描述
需求说明书需求说明书错误或描述不清
设计文档设计文档描述不准确,与需求不一致
系统集成接口各模块参数不匹配
数据流(库)数据字典、数据库中的错误
程序代码编码问题
+

1.4.4 缺陷类型

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
缺陷类型描述
功能未达到规格说明书中规定的功能,影响系统使用
用户界面未按照原型设计,影响交互,如:显示格式,按钮位置
文档文档内容不完整或不正确,影响发布和维护
软件包由于软件配置库、变更管理或版本控制引发的错误
性能执行时间长、处理速度慢、负载高等方面
接口与其他模块参数不匹配
+

1.4.5 缺陷级别

+

严重性: 表示软件缺陷的恶劣程度,当用户碰到该缺陷时影响的可能性和程度。
+优先级: 表示修复缺陷的重要程度和紧迫程度。

+
严重性
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
级别名称说明示例
S1致命错误严重阻碍开发或测试工作的进行,必须马上解决安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件
S2严重缺陷系统出现重大问题,影响提供的主要功能使用内存泄露
数据无法保存
S3主要错误主要功能实现有问题,易用性不够好某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码
S4次要错误次要功能实现有问题或者手册相关问题个别不常用的属性不生效或实现有问题(前提:不影响主要功能使用)
次要功能实现与需求不符或实现有问题(如:日志不能轮转、预警策略不生效、搜索框不能用、快照生成格式有问题等)
错别字
手册描述不合理或样式格式有问题
S5轻微缺陷建议,不属于缺陷
+
优先级
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
级别名称说明
P1不影响整个系统的正常运行,一般指建议性的问题
P2不影响继续测试,但也是必须要修改的,对功能的实现有所影响,如果时间允许应该修复
P3影响整个测试的继续进行,要马上修改
P4系统无法继续执行下去,必须立即修改
+

严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为1这样的缺陷着手,而不是优先修复简单的,由简到难。

+

综合使用重要性等级和严重性双标准的优先顺序:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
S1. 致命错误S2. 严重缺陷S3. 主要错误S4. 次要错误S5. 轻微缺陷
P4. 急立即修复
3小时内
第2修复
1天内
第4修复
2天内
第7修复
3天内
第11修复
4天内
P3. 高第3修复
1-2天内
第5修复
2-3天内
第8修复
3-4天内
第12修复
4-5天内
第15修复
5-6天内
P2. 中第6修复
3-4天内
第9修复
4-5天内
第13修复
5-6天内
第16修复
6-7天内
第18修复
2-3周内
P1. 低第10修复
8-7天内
第14修复
7-9天内
第17修复
8-12天内
第19修复
3-4周内
第20修复
择期
+

1.4.6 跟踪流程

+

最优化、最简单的生命周期是:(理想情况)

+
    +
  1. 测试员发现缺陷并记录缺陷报告。
  2. +
  3. 缺陷报告交给程序员,此时缺陷状态是打开。(open state)
  4. +
  5. 程序员修改缺陷,此时缺陷状态是解决。(resolved state)
  6. +
  7. 缺陷报告交还测试员。
  8. +
  9. 测试员确认已修复。
  10. +
  11. 测试员关闭缺陷报告,此时缺陷状态是关闭。(closed state)
  12. +
+

一个缺陷很可能会被反复打开→关闭。在日常工作过程中,由于开发修订其他缺陷影响、需求变更等因素缺陷可能会被反复打开→关闭。

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
缺陷状态描述
打开确认提交的缺陷,等待处理
已分配分配开发人员进行修复
已解决经过开发人员修复,等待测试人员验证
已验证测试人员验证修复成功
已关闭修复完成,确认测试通过
重新打开测试验证依然存在缺陷,等待开发修复
推迟暂不解决,可能在下一个版本修复
保留条件不允许,不能修复
不能重现开发不能复现这个缺陷,需要测试人员检查缺陷发现步骤
+

1.4.7 缺陷记录内容

+
    +
  1. bug编号:bug的唯一id,以方便尽快找到此bug。
  2. +
  3. bug标题:bug摘要,阐述bug大体内容。
  4. +
  5. bug严重级别,优先级:作为缺陷是否修复以及缺陷修复优先级的决定性因素。
  6. +
  7. bug产生的模块:记录bug所属模块,方便开发定位问题。
  8. +
  9. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题。
  10. +
  11. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。
  12. +
  13. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。
  14. +
+

以上是上报bug、创建bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含:

+
    +
  1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。
  2. +
  3. bug修订人:bug修订人员。
  4. +
  5. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。
  6. +
  7. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。
  8. +
  9. bug复测说明:由复测人员来写,说明复测过程,复测结果等。
  10. +
  11. bug备注:备注,以便记录一些额外信息。
  12. +
+

1.4.8 缺陷预防

+

差错:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源)
+错误:软件内部问题,设计错误、编码错误。(内部原因)
+失效:软件系统运行时偏离了用户需求。(外部表现)

+

1.5 软件测试行业

+

1.5.1 行业现状

+

软件系统越来越复杂,一个软件不能够由单独的软件工程师单独编写,而是由团队进行配合,每个人可能只负责一个模块,对于全局没有过多的了解,这时如果运行软件就会容易产生很多的错误。在行业内将这些错误叫做BUG。并且每一个软件工程师都会有思维的死角,自己不容易发现自己编写出来的错误。所以这个时候就需要专门的软件测试工程师用专业的测试方式来检查软件。检查该软件是否符合客户要求的产品设计,是否能够符合大多数用户的使用习惯,如果发现异常状态及时进行处理。软件市场虽然远远没有达到饱和但是各种各样功能的软件也层出不穷竞争激烈,对软件开发的质量要求也是日益增高。

+

我国软件测试行业起步较晚,发展较慢,直到21世纪初期,我国才逐步开始重视软件测试行业。但近年来,软件行业的快速发展为软件测试行业的发展提供了良好的基础,随着我国软件测试行业的发展,行业内企业向规模化发展将获得规模效应,可以有效降低企业的单位成本;而软件测试技术的不断发展,也将淘汰那些技术实力较弱的企业,促使行业内企业向专业化方向发展。

+

在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量1。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。

+

从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。

+

当前国内软件测试行业主要存在以下问题:

+
    +
  1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题。
  2. +
  3. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步。
  4. +
  5. 对于分布式系统整体性能还难以进行很好的测试。
  6. +
  7. 对于实时系统缺乏有效的测试手段。
  8. +
  9. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题。
  10. +
  11. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合。
  12. +
  13. 缺乏软件测试意识、对其重视不够。
  14. +
  15. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准。
  16. +
  17. 高校从师资储备到专业设置再到人才培养的机制薄弱。
  18. +
+

国内外软件测试差距

+
    +
  1. 测试的理解认识
  2. +
  3. 测试过程的管理
  4. +
  5. 测试工具的使用
  6. +
  7. 测试人员的培养
  8. +
+

1.5.2 未来趋势

+
    +
  1. 以软件为代表的计算机行业正在以一种井喷式的趋势发展
  2. +
  3. 人才缺口大
  4. +
  5. 女性员工受到青睐
  6. +
  7. 未来发展空间大
  8. +
  9. 外包为主
  10. +
+

1.5.3 软件测试职业发展

+
    +
  1. 技术方向 +
      +
    • 敏捷测试专家
    • +
    • 高级测试开发专家
    • +
    • 专项测试专家
    • +
    • QA-Ops 专家
    • +
    +
  2. +
  3. 管理方向 +
      +
    • 测试组长
    • +
    • 测试经理
    • +
    • 项目测试负责人
    • +
    • 测试总监
    • +
    +
  4. +
  5. 易转型方向 +
      +
    • 项目经理
    • +
    • 产品经理
    • +
    +
  6. +
+

1.5.4 测试思维方式

+
    +
  1. 逆向思维方式
  2. +
  3. 组合思维方式
  4. +
  5. 全局思维方式
  6. +
  7. 两级思维方式
  8. +
  9. 比较思维方式
  10. +
  11. 发散思维方式
  12. +
+

1.6 测试认识的误区

+
    +
  1. 使用了测试工具,就进行了有效的测试
  2. +
  3. 存在太多无法测试的东西
  4. +
  5. 软件开发完成后才进行测试
  6. +
  7. 软件发布后发现质量问题,是测试人员的问题
  8. +
  9. 软件测试很简单,就是点点点,是个人就能做
  10. +
  11. 软件测试没有前途,只有程序员才是软件高手
  12. +
  13. 软件测试是测试人员的事情和程序员无关
  14. +
  15. 项目进度吃紧时少做测试,时间多时多做测试
  16. +
  17. 测试要进行穷尽测试
  18. +
  19. 采样是随机抽取过程
  20. +
  21. 测试和开发是对头
  22. +
  23. 测试少报bug开发就会高兴点,报告也会好看点
  24. +
  25. 自动化测试终会取代手工测试
  26. +
  27. 规范化软件测试是增加项目成本
  28. +
  29. 越多测试越有效
  30. +
  31. 软件测试工作只负责项目上线/产品发布之前的部分
  32. +
+

1.7 知识点总结

+

第2章 软件测试基础知识

+

2.1 概述

+
    +
  1. 从软件测试的目的来理解
    +软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。
  2. +
  3. 从软件测试的性质来理解 +在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的”。
  4. +
  5. 从软件开发角度来理解 +软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障。
  6. +
  7. 从软件工程角度来理解
    +软件测试是软件工程的一部分,是软件工程过程中的重要阶段。
  8. +
  9. 从软件质量保证角度来理解
    +软件测试是软件质量保证的重要措施。
  10. +
+

2.2 测试的目的和原则

+

2.2.1 测试的目的

+
    +
  1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进。
  2. +
  3. 检测产品是否符合用户要求。
  4. +
  5. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法。
  6. +
  7. 提升用户体验。
  8. +
+

2.2.2 测试的原则

+
    +
  1. 软件测试是证伪而非证实。
  2. +
  3. 尽早地、不断地进行测试。
  4. +
  5. 重视无效数据和非预期的测试。
  6. +
  7. 应当对每一个测试结果做全面的检查。
  8. +
  9. 测试现场保护和资料归档。
  10. +
  11. 程序员应避免检查自己的程序。
  12. +
  13. 充分注意测试中的集群现象。
  14. +
  15. 用例要定期评审,适时补充修改用例。
  16. +
+

2.3 测试分类

+

2.3.1 按照测试阶段划分

+
    +
  1. 单元测试
  2. +
  3. 集成测试
  4. +
  5. 确认测试
  6. +
  7. 系统测试
  8. +
  9. 验收测试
  10. +
+

软件测试阶段对照表:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
测试阶段主要依据参与人员/测试方式主要测试内容
单元测试《详细设计》开发小组执行白盒测试规范、逻辑、路径
集成测试《概要设计》
《需求文档》
开发小组执行白盒测试、黑盒测试接口、路径、功能、性能
系统测试《需求文档》独立测试小组执行黑盒测试功能测试、界面测试、安全测试、兼容性测试、易用性测试、性能测试、压力测试、负载测试
验收测试《需求文档》用户执行黑盒测试同上
+

2.3.2 按照执行状态划分

+
    +
  1. 静态测试
  2. +
  3. 动态测试
  4. +
+

2.3.3 按照测试技术划分

+
    +
  1. 白盒测试
  2. +
  3. 黑盒测试
  4. +
  5. 灰盒测试
  6. +
+

2.3.4 按照执行主体划分

+
    +
  1. α测试
  2. +
  3. β测试
  4. +
  5. 第三方测试
  6. +
+

2.3.5 按照测试内容划分

+
    +
  1. 界面测试
  2. +
  3. 功能测试
  4. +
  5. 安全测试
  6. +
  7. 兼容性测试
  8. +
  9. 易用性测试
  10. +
  11. 性能测试
  12. +
+

2.3.6 按照是否手工操作划分

+
    +
  1. 手工测试
  2. +
  3. 自动化测试
  4. +
+

2.4 测试用例

+

2.4.1 简介

+

测试用例是指对一项特定的软件产品进行测试任务的描述,体现测试方案、方法、技术和策略。其内容包括:测试目标、测试环境、输入数据、测试步骤、预期结果、测试脚本等,最终形成文档。

+

简单的认为,测试用例是为某个特定目标而编制的一组测试输入、执行条件和预期结果,用于核实是否满足某个特定的软件需求。

+

选择测试用例是软件测试员最重要的一项任务,不正确的选择可能导致测试量过大或者过小,甚至测试目标不对。准确评估风险,把无穷尽的可能性减少到可以控制的范围是软件测试成功的诀窍。

+

2.4.2 测试用例的作用

+
    +
  1. 指导测试的实施
  2. +
  3. 评估测试结果的度量基准
  4. +
  5. 保证软件的可维护性和可复用性
  6. +
  7. 分析缺陷的标准
  8. +
+

2.4.3 测试用例设计准则

+
    +
  1. 有效性
  2. +
  3. 经济性
  4. +
  5. 完备性
  6. +
  7. 可判定性
  8. +
  9. 可再现性
  10. +
+

2.4.4 测试用例维护

+

术语

+
    +
  1. 测试编号:测试用例的编号
  2. +
  3. 测试项:测试的功能点说明
  4. +
  5. 前置条件:该测试用例的前提条件,比如测试wangdachui/dachui12345(用户名/密码)账户是否能正确登录进去,那前提wangdachui/dachui12345已定是注册过的
  6. +
  7. 测试步骤:就是测试的所有操作步骤,最好是每一个步骤应该对应一个期望结果,最少也得一个测试用例对应一个期望结果
  8. +
  9. 期望结果:就是希望得到的结果(正确的结果)
  10. +
  11. 测试结果:实际测试的结果,可选项有:通过、不通过、暂时挂起/锁定(就是暂时不测试);
  12. +
  13. 对应的bug:当期望结果与实际结果不符时测试不通过,此时需要上报bug(纪录缺陷),bug需要与测试用例对应
  14. +
  15. 测试执行人:实际由谁来执行测试用例;也有任务分配人的选项,就是测试用例分配给哪个测试员来测试
  16. +
  17. 备注:做一些备注或者测试的说明
  18. +
  19. 合法用户:就是已经注册过的用户
  20. +
  21. 非法用户:没有注册过;注册过但是用户名/密码不匹配的;本文特指未注册过的用户
  22. +
+

测试用例维护一般分为以下几种情况:

+
    +
  1. 产品特性没变:漏测或者环境变更,这个时候版本没变,测试用例增加和修改均可
  2. +
  3. 原有特性变化:功能变化,只能新增,不能修改,还要兼容老版本
  4. +
  5. 原有功能取消:测试用例在新版本上置为“空”标志或者“无效状态”,对于先前版本有效
  6. +
  7. 新增功能:新增用例,对应新版本标志
  8. +
+

2.4.5 测试用例设计误区

+
    +
  1. 测试用例设计等同于测试输入数据设计
  2. +
  3. 测试用例设计越详细越好
  4. +
  5. 追求测试用例设计“一步到位”
  6. +
  7. 将多个测试条件混在一个用例中
  8. +
+

2.5 测试停止标准

+

2.5.1 软件测试停止总体标准

+
    +
  1. 测试超过了预定时间
  2. +
  3. 执行了所有的测试用例,并没有发现故障
  4. +
  5. 使用特定的测试用例设计方法作为判断测试停止的基础
  6. +
  7. 给出测试停止的要求
  8. +
  9. 根据经单位时间内查出故障的数量决定是否停止测试
  10. +
  11. 软件系统经过了单元、集成、系统测试,分别达到停止标准。通过验收测试,得出验收测试结论。
  12. +
  13. 软件项目暂停以进行调整,测试应随之暂停,并备份暂停点数据。或者软件项目开发生命周期内出现重大估算、进度偏差,需暂停或终止时,测试应随之暂停或终止,并备份数据
  14. +
+

2.5.2 软件测试各阶段停止标准

+
单元测试停止标准
+
    +
  1. 单元测试用例已经通过评审
  2. +
  3. 按照单元测试计划完成了所有规定单元测试
  4. +
  5. 达到了测试计划中关于单元测试所规定的覆盖率要求
  6. +
  7. 被测试的单元每千行代码必须发现至少3个错误
  8. +
  9. 软件单元功能与设计一致
  10. +
  11. 单元测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. +
+
集成测试停止标准
+
    +
  1. 集成测试用例已经通过评审
  2. +
  3. 按照集成测试计划和增量集成策略完成了整个系统的集成测试
  4. +
  5. 达到了测试计划中关于集成测试所规定的覆盖率要求
  6. +
  7. 被测试的集成工作版本每千行代码必须发现至少2个错误
  8. +
  9. 集成工作版本满足设计定义的各项功能、性能要求
  10. +
  11. 在集成测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. +
+
系统测试停止标准
+
    +
  1. 系统测试用例已经通过评审
  2. +
  3. 按照系统测试计划完成了系统测试
  4. +
  5. 达到了测试计划中关于系统测试所规定的覆盖率要求
  6. +
  7. 被测试的系统每千行代码必须发现至少1个错误
  8. +
  9. 系统测试满足设计需求规格说明书要求
  10. +
  11. 在系统测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. +
+

2.6 知识点总结

+

第3章 黑盒测试

+

3.1 概述

+

黑盒测试也称功能测试,通过测试来检测每个功能是否都能正常使用。

+

着眼于程序外部结构,不考虑内部逻辑结构,通过测试检验每个功能是否能正常使用。在程序接口进行测试,只检查程序功能是否按照需求规格说明书的规定正常使用,程序是否能适当的接受输入数据而产生正确的输出信息。

+

黑盒测试从用户的角度出发,以输入数据与输出数据的对应关系进行测试,数据驱动。

+

黑盒测试注重测试软件的功能需求,主要视图发现下列几类错误

+
    +
  1. 功能不正确或遗漏
  2. +
  3. 界面错误
  4. +
  5. 数据库访问错误
  6. +
  7. 性能错误
  8. +
  9. 初始化和终值错误
  10. +
+

3.2 等价类划分

+

等价类是指某个输入域的子集合。在该子集合中,测试某等价类的代表值就等于对这类其他值的测试,对于揭露程序的错误是等效的。

+

要注意的是,在进行等价类划分的过程中,我们不仅要考虑有效等价类划分,也要考虑无效等价类划分。

+

有效等价类:是指输入完全符合程序规格说明的数据集合。利用有效等价类可以测试程序是否满足规格说明书规定的功能和性能。

+

无效等价类:和有效等价类相反,是指对程序的规格说明无意义、不合理的输入数据构成的集合。

+

3.2.1 划分原则

+
    +
  1. 在输入条件规定了取值范围的情况下,可以确立一个有效等价类(在取值范围之内)和两个无效等价类(小于取值范围和大于取值范围)。
  2. +
  3. 在输入条件规定了取回个数的情况下,可以确立一个有效等价类(在取值个数范围之内)和两个无效等价类(小于取值个数和大于取值个数)。
  4. +
  5. 在输入条件规定了输入值的集合的情况下,可以确立一个有效等价类和一个无效等价类。
  6. +
  7. 在输入条件规定了“必须如何”条件的情况下,可以确立一个有效等价类和一个无效等价类。
  8. +
  9. 在输入条件是一个布尔值的情况下,可以确立一个有效等价类和一个无效等价类。
  10. +
  11. 在规定了输入数据的一组值(假定n个),并且程序要对每一个输入值分别处理的将情况下,可以确立n个有效等价类和一个无效等价类。
  12. +
  13. 在规定了输入数据必须遵守规则的情况下,可以确立一个有效等价类(符合规则)和若干个无效等价类(从不同角度违反规则)。
  14. +
  15. 在确知已划分的等价类中各元素在程序处理中的方式不同的情况下,则应再将改等价类进一步划分为更小的等价类。
  16. +
+

3.2.2 设计测试用例步骤

+
    +
  1. 形成等价类表,每一等价类规定一个唯一编号
  2. +
  3. 设计测试用例,使其尽可能多的覆盖尚未覆盖的有效等价类
  4. +
  5. 设计一个新的测试用例,使其只覆盖一个无效等价类,重复这一步直到所有无效等价类均被覆盖。
  6. +
+

3.2.3 等价类举例

+

我们要测试学习成绩这一输入框(假设总成绩都是100),那么我们就可以如下图划分,有效的成绩是>=0且<=100的,无效的是<0和>100这两部分。

+

等价类举例

+

另外图中还有一个无效等价类没有表现出来--非数字字符(比如:英文字母、中文、特殊的符号等单一或者组合,如a、abc、你好、你abc、你=我、\你\a\等;以及他们分别与数字组合,比如:a123、321a、你123、12你、1你2、1\2、1=你等)。

+

那么根据上述分析,最终设计出来的测试用例如下:

+
    +
  1. 有效等价类1:0~100(包含0和100)之间的任意数,比如:19;
  2. +
  3. 无效等价类1:小于0的负数,比如:-1;
  4. +
  5. 无效等价类2:大于100的数,比如:121;
  6. +
  7. 无效等价类3:其他任意非数字字符,比如:a、你、\;
  8. +
  9. 无效等价类4:空字符
  10. +
+

等价类最终必须是分割到最小单位,只有这样才能保障测试覆盖全面。
+非数字字符可以是包含英文字符、中文、特殊符号的字符串或者字符,所以其实它又可以分为三个无效等价类,分别是:

+
    +
  1. 无效等价类:包含英文字符的字符串,比如:a、a123、a=、b你a;
  2. +
  3. 无效等价类:包含中文的字符串,比如:你、你12、1你2、你=;
  4. +
  5. 无效等价类:包含特殊字符的字符串,比如:\ 。
  6. +
+

3.3 边界值分析

+

边界值分析法是等价类划分法的补充。顾名思义,边界值分析法是对输入的边界值进行测试。从实践中我们可以发现,人们无论是在生活中还是在工作中往往会忽略边界值的条件,所以在输入或者输出的边界上会发生大量的错误。因此,在测试用例设计中,需要对输入的条件进行分析并且提取其中的边界值条件,通过对这些边界值的测试来查出更多的错误。

+

常见的边界值:

+
    +
  1. 文本框接受字符个数,比如用户名长度、密码长度等。
  2. +
  3. 报表的第1行和最后1行。
  4. +
  5. 数组元素的第1个和最后1个。
  6. +
  7. 循环的第1次、第2次和倒数第1次、最后1次。
  8. +
+

3.3.1 设计原则

+
    +
  1. 如果输入条件规定了值的范围,则应取刚达到这个范围边界的值,以及刚刚超越这个范围边界的值作为测试输入数据。
  2. +
  3. 如果输入条件规定了值的个数,则用最大个数、最小个数、比最小个数少1、比最大个数多1的数作为测试数据。
  4. +
  5. 如果规格说明书给出的输入域或输出域是有序集合,则应选取集合的第1个元素和最后1个元素作为测试用例。
  6. +
  7. 如果程序中使用了内部数据结构,则应选择内部数据结构边界上的值作为测试用例。
  8. +
  9. 分析规格说明,找出其他可能的边界条件。
  10. +
+

3.3.2 两类方法

+
    +
  1. +

    一般边界值分析 +对于含有n个变量的程序,取值为min、min+、normal,max-、max,测试用例数目为4*N+1。 +一般边界值分析

    +
  2. +
  3. +

    健壮性边界值分析 +健壮性边界值测试是边界值分析的一种扩展。变量除了取min、min+、normal、max-、max 5个边界值外,还要考虑略超过最大值(max+)以及略小于最小值(min-)的取值。因此,对于含有n个变量的程序,健壮性边界值分析产生6*n+1个测试用例。 +健壮性边界值分析

    +
  4. +
+

3.3.3 应用举例

+

延伸上节的例子来说明:学生信息系统中有一个“考试成绩”的输入项,成绩的取值范围是0~100之间的整数,考试成绩及格的分数线是60,优秀的分数线是80。那么这个例子中的边界值数据是哪些呢:

+
+

选取的边界值数据应该包括:

+

-1,0,1,59,60,61,79,80,81,99,100,101

+
+

通常情况下,软件测试所包含的边界检验有以下几种类型:数字、字符、位置、质量、大小、速度、方位、尺寸、空间等,而相应地,这些类型的边界值应该在最大/最小,首位/末尾,上/下,最快/最慢,最高/最低,最短/最长,空/满等情况下。

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
测试项边界值测试用例设计思路
数字起始位数-1
结束位数+1
成绩,正确0-100,边界-1,0,100,101
字符起始-1个字符
结束+1个字符
用户名输入框,正确1-32位,边界0、1、32、33,注意中文字符占位不同
方向刚差一点
刚超一点
游戏,通过门口,边界值门内一步和门外一步
空间小于空余空间一点
大于满空间一点
磁盘剩余20G,边界19.9G和20.1G
位置上下左右里面一点
外面一点
按钮,四边内四点,外四点
+

3.3.4 局限性

+

如果被测程序是多个独立变量的函数,这些变量受物理量的限制,则较适合采用边界值分析。这里的关键是 “独立”的“物理量” 。例如,Date是3个变量(年、月、日)的函数,对其采用边界分析测试用例,就会发现测试用例是不充分的,例如,没强调2月和闰年。其存在问题是因为没有考虑月份、日期和年变量之间存在的依赖关系。由于边界值分析假设变量是完全独立的,因此边界值分析测试用例是对物理量的边界独立导出变量极值,不考虑函数的性质,也不考虑变量的语义含义。 +边界值分析对布尔变量和逻辑变量没有多大意义。例如,布尔变量的极值是true和false,但是其余3个值不明确。

+

3.4 决策表

+

等价类划分法和边界值分析法只是孤立地考虑各个输人数据的测试效果,没有考虑输入数据的组合及其相互制约关系,而决策表考虑了多种条件的组合情况。决策表又称为判定表,分析多种逻辑条件(if-else、switch-case等)与执行动之间的关系。

+

决策表由4部分组成:

+
    +
  1. 条件桩:列出了问题的所有条件,通常认为列出的条件次序无关紧要。
  2. +
  3. 动作桩:列出了问题规定可能采取的操作,这些操作的排列顺序没有约束。
  4. +
  5. 条件项:列出针对条件桩的取值,在所有可能情况下的真假值。
  6. +
  7. 动作项:列出在条件项的各种取值情况下应该采取的动作。
  8. +
+

规则:任何条件组合的特定取值及其相应要执行的操作。在决策表中贯穿条件项和动作项的列就是规则。显然,决策表中列出多少条件取值,也就有多少规则,条件项和动作项就有多少列。

+

决策表组成

+

所有条件都是逻辑结果(即真/假、是/否、0/1)的决策表称为有限条件决策表。如果条件有多个值,则对应的决策表叫做扩展条目决策表。决策表设计测试用例,条件解释为输入,动作解释为输出。

+

决策表适合以下特征的应用程序:

+
    +
  1. if-then-else分支逻辑突出。
  2. +
  3. 输入变量之间存在逻辑关系。
  4. +
  5. 涉及输入变量子集的计算。
  6. +
  7. 输入和输出之间存在因果关系。
  8. +
  9. 很高的圈复杂度。
  10. +
+

3.4.1 应用举例

+

决策表(判定表)设计测试用例的具体步骤如下:

+
    +
  1. 确定规则的个数。假如有n个条件,每个条件有两个取值(0,1),故有2种规则。
  2. +
  3. 列出所有的条件桩和动作桩。
  4. +
  5. 填入条件项。
  6. +
  7. 填入动作项,得到初始判定表。
  8. +
  9. 简化,合并相似规则(相同动作)。 +简化就是合并多条具有相同的动作的规则,并且其条件项之间存在极为相似的关系。 +简化规则
  10. +
+

需求:输入三边值,判定是哪种三角形:非三角形、不等边三角形、等腰三角形、等边三角形

+
    +
  1. 绘制初始三角形判定决策表
  2. +
  3. 优化1的产出
  4. +
  5. 设计测试用例
  6. +
+

条件桩:

+
    +
  • abc能构成三角形 +
      +
    • a+b>c
    • +
    • a+c>b
    • +
    • b+c>a
    • +
    +
  • +
  • a=b?
  • +
  • a=c?
  • +
  • b=c?
  • +
+

动作桩:

+
    +
  • 非三角形
  • +
  • 不等边三角形
  • +
  • 等腰三角形
  • +
  • 等边三角形
  • +
+

决策表:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
12345678
a+b>c?NYYYYYYY
a+c>b?NYYYYYY
b+c>a?NYYYYY
a=b?YYNNN
a=c?YNYNN
b=c?YN
非三角形
不等边三角形
等腰三角形
等边三角形
+

测试用例:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
用例IDabc预期输出
TC1124非三角形
TC2142非三角形
TC3421非三角形
TC4333等边三角形
TC5334等腰三角形
TC6343等腰三角形
TC7433等腰三角形
TC8345不等边三角形
+

3.4.2 优点和缺点

+

决策表把复杂问题的各种可能情况一一列出,易于理解。但是,决策表不能表达重复执行动作的缺点。

+

使用判定表设计测试用例的条件如下:

+
    +
  1. 规格说明以判定表形式给出,或很容易转换成判定表。
  2. +
  3. 条件的排列顺序不会也不影响执行哪些操作。
  4. +
  5. 规则的排列顺序不会也不影响执行哪些操作。
  6. +
  7. 每当某一规则的条件已经满足,并确定要执行的操作后,不必检验别的规则。
  8. +
  9. 如果某一规则得到满足要执行多个操作,这些操作的执行顺序无关紧要。
  10. +
+

这5个必要条件使得操作的执行完全依赖于条件的组合。对于不满足条件的判定表,可增加其他的测试用例。

+

3.5 因果图

+

前面我们介绍的等价类划分法和边界值分析法都没有考虑到输入情况的组合。这样虽然各种输入条件可能出错的情况已经看到了,但是多个输入情况组合起来可能出错的情况却被忽视了

+
+

地铁自动充值机充值

+

假设自动充值机每次只能投入面值50或者面值100的人民币,投入钱后会有充值50和充值100两个选项

+
+

等价类划分法和边界值分析法可能不会测试到投入面值50的人民币,然后点击充值100这种异常情况;因此,当程序的输入条件有多个的话,就需要用到因果图法来设计测试用例了。

+

因果图利用图解法分析输入的各种组合情况,适合描述多种输入条件的组合、相应产生多不动作的方法。因果图法最终生成的是判定表。

+

3.5.1 基本术语

+
    +
  1. 原因结果图: +原因——结果图使用了简单的逻辑符号,以直线连接左右结点,左结点表示输入状态(原因),右结点表示输出状态(结果)。
  2. +
+

原因 - 结果图

+
    +
  • “恒等”:若原因出现,则结果出现;若原因不出现,则结果不出现。
  • +
  • “非”:若原因出现,则结果不出现;若原因不出现,则结果出现。
  • +
  • “或”:若几个原因中有一个出现,则结果出现;若几个原因都不出现,则结果不出现。
  • +
  • “与”:若几个原因都出现,结果才出现;若其中有一个原因不出现,则结果不出现。
  • +
+
    +
  1. 约束图: +输入输出状态相互之间存在的某些依赖关系,称为约束。
  2. +
+

约束图

+
    +
  • E(互斥):原因不会同时成立,最多1个成立,可以都不成立
  • +
  • I(包含):原因中至少一个成立,不能同时为0
  • +
  • O(唯一):原因中有且只有一个成立
  • +
  • R(要求):原因中a出现,b必须出现,a=1则b=1,a=0的话,b随便。QQ登录的例子a为自动登录,b是记住密码
  • +
  • M(屏蔽):a为1时,b必须是0,a=1,则b=0,如果a=0,b随便
  • +
+

3.5.2 设计因果图测试用例步骤

+
    +
  1. 分析软件规格说明,哪些是原因(即输入条件或输入条件的等价类),哪些是结果(即输出条件),给每个原因和结果赋予标识符。
  2. +
  3. 分析原因与结果之间、原因与原因之间对应的逻辑关系,用因果图表示。
  4. +
  5. 由于语法或环境限制,有些原因与原因之间、原因与结果之间的组合情况不可能出现,在因果图上用一些记号表明这些特殊情况的约束或限制条件,把因果图转换为判定表。
  6. +
  7. 从判定表的每一列产生出测试用例。
  8. +
+

对于逻辑结构复杂软件,先用因果图进行图形分析,再用判定表进行统计,最后设计测试用例。当然,对于比较简单的测试对象,可以忽略因果图,直接使用决策表。

+

3.5.3 应用举例

+

需求:第一列字符必须是A或者B,第二列为数字,才允许进行文件修改。如果第一列字符不正确,输出提示L,第二列不是数字,输出提示M,采用因果图设计测试用例

+

原因:

+
    +
  1. 第一列是A
  2. +
  3. 第一列是B
  4. +
  5. 第二列是数字
  6. +
+

结果:

+
    +
  1. 修改文件
  2. +
  3. 输出提示L
  4. +
  5. 输出提示M
  6. +
+

因果图: +因果图

+

决策表:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
123456
A110000
B001100
数字101010
修改文件101000
提示L000011
提示M010101
+

测试用例:

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
用例ID第一列第二列预期输出
TC1A1修改文件
TC2AC、汉、#提示M
TC3B2修改文件
TC4BD、字、!提示M
TC5E、符、%3提示L
TC6F、特、@G、殊、*提示L和M
+

3.5.4 优点和缺点

+

优点:

+
    +
  1. 考虑多个输入之间的相互组合、相互制约的关系
  2. +
  3. 指出需求规格说明书中存在的不完整性和二义性
  4. +
  5. 帮助测试人员按照一定的步骤高效的开发测试用例
  6. +
+

缺点:

+
    +
  1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到
  2. +
  3. 此方法得到的用例数量规模大
  4. +
+

3.6 场景法

+

通过尝尽该描述的业务流程(业务逻辑),设计用例来遍历场景(路径),验证系统功能的正确性。 +场景法重点是测试流程,因此每个流程用一个用例验证即可,流程测试没问题不代表系统功能没问题,还需要单步进行测试,结合前面的方法。

+

流程图:

+
    +
  • 矩形:步骤
  • +
  • 菱形:判断条件
  • +
  • 箭头:流向
  • +
+

3.6.1 ATM取款流程图

+

ATM取款流程图

+

3.6.2 ATM取款场景设计

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
场景编号流程结果
1插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额充足
ATM现金充足
成功提款
2插入不合法的卡提示错误,退卡
3插入合法的卡
输入密码点取消
退卡
4插入合法的卡
输入错误的密码(还有机会)
提示错误,重新输入
5插入合法的卡
输入错误的密码(超出限制次数)
提示错误,退卡/吞卡
6插入合法的卡
输入正确的密码
ATM没有现金
提款选项不可用,退出
7插入合法的卡
输入正确的密码
ATM有现金
输入不合法的金额
提示错误,重新输入
8插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额不足
提示错误,重新输入
9插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额充足
ATM现金不足
提示错误,重新输入
+

3.6.3 测试用例

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
用例ID场景/条件卡片密码ATM内金额账户余额输入金额预期结果
TC1场景1:成功提款合法卡1234562000.005000.00100成功提款,账户余额400.00
TC2场景2:非法的卡非法卡n/a2000.005000.00n/a提示错误,退卡
TC3场景3:点取消合法卡n/a2000.005000.00n/a退卡
TC4场景4:密码错误(还有机会)合法卡6543212000.005000.00n/a提示错误,重新输入
TC5场景5:密码错误(超过限制次数)合法卡2345162000.005000.00n/a提示错误,退卡/吞卡
TC6场景6:ATM无现金合法卡1234560.005000.00n/a提款选项不可用,用例结束
TC7场景7:金额错误合法卡1234562000.005000.0020提示错误,重新输入
TC8场景8:卡内余额不足合法卡1234562000.005000.00600提示错误,重新输入
TC9场景9:ATM现金不足合法卡1234562000.005000.002500提示错误,重新输入
+

3.7 错误推测法

+

3.7.1 概念

+

错误推测法是利用经验和直觉推测出出错的可能类型,列举出程序中所有可能的错误和容易发生错误情况的清单,根据清单设计测试用例。所谓凭经验,是指人们对过去所作测试结果的分析,对所揭示缺陷的规律性直觉的推测来发现缺陷。

+

该方法强调的是对被测试软件的需求理解以及设计实现的细节把握,当然还有个人的能力。那么显而易见地,这个方法的缺点就是太过依赖个人能力,难以系统化。因此,这个方法一般是作为测试用例设计的补充,而不是单独用来设计测试用例。在回归测试中应用较多。

+

错误推测法一般采用如下技术:

+
    +
  1. 有关软件设计方法和实现技术。
  2. +
  3. 有关前期测试阶段结果的知识。
  4. +
  5. 测试类似或相关系统的经验,了解以前这些系统曾在哪些地方出现缺陷。
  6. +
  7. 典型的产生错误的知识,如被零除错误。
  8. +
+

3.7.2 优点和缺点

+

优点:

+
    +
  1. 不用设计等价类的测试用例,将多个等价类的测试合成一个随机测试,可以以较少代码实现测试代码的编写。
  2. +
  3. 当等价类设计不确切或不完全时,测试会产生遗漏,而使用错误推测法则是按照概率进行等价类覆盖。不论存在多少个等价类,只要随机数据个数足够,就能保证各个等价类被覆盖的概率足够高,能够有效弥补等价类分法设计不充分的缺陷。
  4. +
  5. 采用错误推测法进行测试,每次执行测试时,测试的样本数据可能都不相同,执行次数愈多,错误暴露的概率愈大。
  6. +
+

缺点:

+
    +
  1. 错误推测法中的随机数据很难覆盖到边界值,无法保证测试的充分性。
  2. +
  3. 错误推测法进行自动化测试的难度较大。有些程序很难用程序来自动验证,这使得程序结果的验证工作难度变大。
  4. +
  5. 当等价类的范围较小,这些范围较小的等价类被覆盖的概率也是很小的,错误推测法难以测试到。
  6. +
  7. 随机测试不可以代替常规的功能或非功能测试,因为其随意性大,没有一套完整严格的方法且并非有章可循的测试技术。
  8. +
+

3.7.3 常见错误

+
    +
  1. 页面规范相关部分(跟公司甚至项目需求有关系)
  2. +
+
    +
  • 命名、注释、字体、颜色、缩进等
  • +
  • 文本框长度/范围限制
  • +
  • 支持的浏览器、操作系统、jdk等做兼容性测试
  • +
+
    +
  1. 常识性问题
  2. +
+
    +
  • 密码用密文
  • +
  • 手机号码是11位,且是特定三位数开头
  • +
  • 文本框自动忽略前后空格
  • +
  • 支持模糊查询
  • +
+
    +
  1. 常见的异常测试情况
  2. +
+
    +
  • 输入框不输入任何内容(为空)或者输入空格的情况
  • +
  • 输入框输入非法字符
  • +
  • 用户注销后,是否仍然能操作;再登录是否能成功
  • +
  • 断电重连后是否能继续使用且信息未丢失
  • +
+
    +
  1. 功能相关的常见异常问题
  2. +
+
    +
  • C++软件的内存泄漏、内存分配
  • +
  • web程序的session失效问题
  • +
  • JavaScript字符转义
  • +
+

3.8 综合策略

+

黑盒测试方法有等价类划分、边界值分析、决策表、因果图、场景法、错误推测法等,每种测试方法都有其各自的特点和适用场合。
+软件测试专家Myers给出了黑盒测试方法中各种测试方法的使用策略:

+
    +
  1. 在任何情况下都必须使用边界值分析方法。经验表明,用这种方法设计的测试用例发现程序错误的能力最强。
  2. +
  3. 必要时使用等价类划分方法补充一些测试用例。
  4. +
  5. 用错误推测法再追加一些测试用例。
  6. +
  7. 对照程序逻辑,检查已设计出的测试用例的逻辑覆盖程度,如果没有达到要求的覆盖标准,应当再补充足够的测试用例。
  8. +
  9. 如果程序的功能说明中含有输入条件的组合情况,则一开始就可选用因果图法。
  10. +
+

对于功能性测试技术,可以根据如下条件进行选择:

+
    +
  1. 如果变量是独立的,则可以用定义域测试和等价类测试。
  2. +
  3. 如果变量不是独立的,可采用决策表测试。
  4. +
  5. 如果为单缺陷假设,则可采用边界值分析和健壮性测试。
  6. +
  7. 如果为多缺陷假设,可采用最坏情况测试、健壮最坏情况测试和决策表测试。
  8. +
  9. 如果程序包含大量例外处理,可采用健壮性测试和决策表测试。
  10. +
  11. 如果变量引用的是逻辑量,可采用等价类测试用例和决策表测试。
  12. +
+

第4章 白盒测试

+

4.1 概述

+

4.2 静态测试

+

4.3 逻辑覆盖

+

4.4 路径分析

+

4.5 控制结构测试

+

4.6 数据流测试

+

4.7 程序插桩

+

4.8 测试方法综述

+

4.9 知识点总结

+

第5章 性能测试

+

5.1 基本概念

+

5.2 性能测试分类

+

5.2.1 负载测试

+

5.2.2 压力测试

+

5.2.3 可靠性测试

+

5.2.4 数据库测试

+

5.2.5 安全性测试

+

5.2.6 兼容性测试

+

5.2.7 可用性测试

+

5.3 性能测试步骤

+

5.4 Web测试

+

5.5知识点总结

+

第6章 软件测试流程

+

6.1 软件测试流程概述

+

6.2 测试需求

+

6.3 测试计划

+

6.4 测试设计

+

6.5 测试执行

+

6.5.1 单元测试

+

6.5.2 集成测试

+

6.5.3 系统测试

+

6.5.4 验收测试

+

6.5.5 α测试

+

6.5.6 β测试

+

6.6 回归测试

+

6.7 测试评估

+

6.8 知识点总结

+

第7章 软件测试自动化

+

7.1 自动化测试和手工测试

+

7.2 测试成熟度模型

+

7.3 自动化测试体系

+

7.4 测试工具介绍

+

7.5 知识点总结

+

第8章 软件测试管理

+

8.1 软件测试管理概述

+

8.2 测试过程改进

+

8.3 人力资源

+

8.4 知识点总结

+ + + -- Gitee From d1c0fd2e60b09d63c843d1a49ba6552748a5fb71 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=91=A8=E8=AF=9A?= Date: Tue, 14 Sep 2021 10:48:45 +0000 Subject: [PATCH 07/30] add LICENSE. --- LICENSE | 127 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 127 insertions(+) create mode 100644 LICENSE diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000..ee58399 --- /dev/null +++ b/LICENSE @@ -0,0 +1,127 @@ + 木兰宽松许可证, 第2版 + + 木兰宽松许可证, 第2版 + 2020年1月 http://license.coscl.org.cn/MulanPSL2 + + + 您对“软件”的复制、使用、修改及分发受木兰宽松许可证,第2版(“本许可证”)的如下条款的约束: + + 0. 定义 + + “软件”是指由“贡献”构成的许可在“本许可证”下的程序和相关文档的集合。 + + “贡献”是指由任一“贡献者”许可在“本许可证”下的受版权法保护的作品。 + + “贡献者”是指将受版权法保护的作品许可在“本许可证”下的自然人或“法人实体”。 + + “法人实体”是指提交贡献的机构及其“关联实体”。 + + “关联实体”是指,对“本许可证”下的行为方而言,控制、受控制或与其共同受控制的机构,此处的控制是指有受控方或共同受控方至少50%直接或间接的投票权、资金或其他有价证券。 + + 1. 授予版权许可 + + 每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的版权许可,您可以复制、使用、修改、分发其“贡献”,不论修改与否。 + + 2. 授予专利许可 + + 每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的(根据本条规定撤销除外)专利许可,供您制造、委托制造、使用、许诺销售、销售、进口其“贡献”或以其他方式转移其“贡献”。前述专利许可仅限于“贡献者”现在或将来拥有或控制的其“贡献”本身或其“贡献”与许可“贡献”时的“软件”结合而将必然会侵犯的专利权利要求,不包括对“贡献”的修改或包含“贡献”的其他结合。如果您或您的“关联实体”直接或间接地,就“软件”或其中的“贡献”对任何人发起专利侵权诉讼(包括反诉或交叉诉讼)或其他专利维权行动,指控其侵犯专利权,则“本许可证”授予您对“软件”的专利许可自您提起诉讼或发起维权行动之日终止。 + + 3. 无商标许可 + + “本许可证”不提供对“贡献者”的商品名称、商标、服务标志或产品名称的商标许可,但您为满足第4条规定的声明义务而必须使用除外。 + + 4. 分发限制 + + 您可以在任何媒介中将“软件”以源程序形式或可执行形式重新分发,不论修改与否,但您必须向接收者提供“本许可证”的副本,并保留“软件”中的版权、商标、专利及免责声明。 + + 5. 免责声明与责任限制 + + “软件”及其中的“贡献”在提供时不带任何明示或默示的担保。在任何情况下,“贡献者”或版权所有者不对任何人因使用“软件”或其中的“贡献”而引发的任何直接或间接损失承担责任,不论因何种原因导致或者基于何种法律理论,即使其曾被建议有此种损失的可能性。 + + 6. 语言 + “本许可证”以中英文双语表述,中英文版本具有同等法律效力。如果中英文版本存在任何冲突不一致,以中文版为准。 + + 条款结束 + + 如何将木兰宽松许可证,第2版,应用到您的软件 + + 如果您希望将木兰宽松许可证,第2版,应用到您的新软件,为了方便接收者查阅,建议您完成如下三步: + + 1, 请您补充如下声明中的空白,包括软件名、软件的首次发表年份以及您作为版权人的名字; + + 2, 请您在软件包的一级目录下创建以“LICENSE”为名的文件,将整个许可证文本放入该文件中; + + 3, 请将如下声明文本放入每个源文件的头部注释中。 + + Copyright (c) [Year] [name of copyright holder] + [Software Name] is licensed under Mulan PSL v2. + You can use this software according to the terms and conditions of the Mulan PSL v2. + You may obtain a copy of Mulan PSL v2 at: + http://license.coscl.org.cn/MulanPSL2 + THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. + See the Mulan PSL v2 for more details. + + + Mulan Permissive Software License,Version 2 + + Mulan Permissive Software License,Version 2 (Mulan PSL v2) + January 2020 http://license.coscl.org.cn/MulanPSL2 + + Your reproduction, use, modification and distribution of the Software shall be subject to Mulan PSL v2 (this License) with the following terms and conditions: + + 0. Definition + + Software means the program and related documents which are licensed under this License and comprise all Contribution(s). + + Contribution means the copyrightable work licensed by a particular Contributor under this License. + + Contributor means the Individual or Legal Entity who licenses its copyrightable work under this License. + + Legal Entity means the entity making a Contribution and all its Affiliates. + + Affiliates means entities that control, are controlled by, or are under common control with the acting entity under this License, ‘control’ means direct or indirect ownership of at least fifty percent (50%) of the voting power, capital or other securities of controlled or commonly controlled entity. + + 1. Grant of Copyright License + + Subject to the terms and conditions of this License, each Contributor hereby grants to you a perpetual, worldwide, royalty-free, non-exclusive, irrevocable copyright license to reproduce, use, modify, or distribute its Contribution, with modification or not. + + 2. Grant of Patent License + + Subject to the terms and conditions of this License, each Contributor hereby grants to you a perpetual, worldwide, royalty-free, non-exclusive, irrevocable (except for revocation under this Section) patent license to make, have made, use, offer for sale, sell, import or otherwise transfer its Contribution, where such patent license is only limited to the patent claims owned or controlled by such Contributor now or in future which will be necessarily infringed by its Contribution alone, or by combination of the Contribution with the Software to which the Contribution was contributed. The patent license shall not apply to any modification of the Contribution, and any other combination which includes the Contribution. If you or your Affiliates directly or indirectly institute patent litigation (including a cross claim or counterclaim in a litigation) or other patent enforcement activities against any individual or entity by alleging that the Software or any Contribution in it infringes patents, then any patent license granted to you under this License for the Software shall terminate as of the date such litigation or activity is filed or taken. + + 3. No Trademark License + + No trademark license is granted to use the trade names, trademarks, service marks, or product names of Contributor, except as required to fulfill notice requirements in Section 4. + + 4. Distribution Restriction + + You may distribute the Software in any medium with or without modification, whether in source or executable forms, provided that you provide recipients with a copy of this License and retain copyright, patent, trademark and disclaimer statements in the Software. + + 5. Disclaimer of Warranty and Limitation of Liability + + THE SOFTWARE AND CONTRIBUTION IN IT ARE PROVIDED WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED. IN NO EVENT SHALL ANY CONTRIBUTOR OR COPYRIGHT HOLDER BE LIABLE TO YOU FOR ANY DAMAGES, INCLUDING, BUT NOT LIMITED TO ANY DIRECT, OR INDIRECT, SPECIAL OR CONSEQUENTIAL DAMAGES ARISING FROM YOUR USE OR INABILITY TO USE THE SOFTWARE OR THE CONTRIBUTION IN IT, NO MATTER HOW IT’S CAUSED OR BASED ON WHICH LEGAL THEORY, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. + + 6. Language + + THIS LICENSE IS WRITTEN IN BOTH CHINESE AND ENGLISH, AND THE CHINESE VERSION AND ENGLISH VERSION SHALL HAVE THE SAME LEGAL EFFECT. IN THE CASE OF DIVERGENCE BETWEEN THE CHINESE AND ENGLISH VERSIONS, THE CHINESE VERSION SHALL PREVAIL. + + END OF THE TERMS AND CONDITIONS + + How to Apply the Mulan Permissive Software License,Version 2 (Mulan PSL v2) to Your Software + + To apply the Mulan PSL v2 to your work, for easy identification by recipients, you are suggested to complete following three steps: + + i Fill in the blanks in following statement, including insert your software name, the year of the first publication of your software, and your name identified as the copyright owner; + + ii Create a file named “LICENSE” which contains the whole context of this License in the first directory of your software package; + + iii Attach the statement to the appropriate annotated syntax at the beginning of each source file. + + + Copyright (c) [Year] [name of copyright holder] + [Software Name] is licensed under Mulan PSL v2. + You can use this software according to the terms and conditions of the Mulan PSL v2. + You may obtain a copy of Mulan PSL v2 at: + http://license.coscl.org.cn/MulanPSL2 + THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. + See the Mulan PSL v2 for more details. -- Gitee From 8852db024f6071135bec77f01bc63a50105c17d4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=91=A8=E8=AF=9A?= Date: Tue, 14 Sep 2021 19:00:28 +0800 Subject: [PATCH 08/30] modify --- README.md | 21 +++++++++++---------- 1 file changed, 11 insertions(+), 10 deletions(-) diff --git a/README.md b/README.md index 5bd826c..dbaae73 100644 --- a/README.md +++ b/README.md @@ -68,9 +68,9 @@ * 《软件支持手册》 #### 1.1.3 软件发展史 -1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。软件 = 程序 +1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序) 2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 -3. 软件工程阶段:以软件的产品化,系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 +3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 4. 多层分布结构,面向服务架构 #### 1.1.4 软件项目 @@ -106,12 +106,12 @@ **描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。 **参与者:** 任务责任人(开发)、测试 #### 1.2.8 测试 - - 测试需求 - - 测试计划 - - 测试设计 - - 测试执行 - - 回归测试 - - 测试评估 + - 测试需求 + - 测试计划 + - 测试设计 + - 测试执行 + - 回归测试 + - 测试评估 #### 1.2.9 部署/发版 **描述:** 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 **参与人:** 配置管理人员、测试 @@ -140,9 +140,9 @@ The process of executing a program with the intent of finding errors. 这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。 4. 1983–1987-评估为主(Evaluation Oriented) -软件行业进入了大发展时期,软件趋向大型化、复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 +软件行业进入了大发展时期,软件趋向大型化、复杂化,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 5. 1988–至今-预防为主(Prevention Oriented) -尽量早的介入,尽量早的发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 +尽量早的介入并发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 #### 1.3.3 测试与开发的关系 **瀑布模型** @@ -183,6 +183,7 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 ![螺旋模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/lx-model.png) 大型软件项目通常有很多不确定性和风险,如果采用瀑布式线性过程模型,失败风险很大,因此需要采取一种渐进式的演化过程模型。将产品分解成增量版本,每个版本单独测试。 + **敏捷模型** ![敏捷模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/mj-model.png) -- Gitee From 63711303b5527bd0de1aacfd985c66b2330f0ab4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=91=A8=E8=AF=9A?= Date: Tue, 14 Sep 2021 19:01:39 +0800 Subject: [PATCH 09/30] modify --- LICENSE | 127 ---- README.html | 2063 --------------------------------------------------- 2 files changed, 2190 deletions(-) delete mode 100644 LICENSE delete mode 100644 README.html diff --git a/LICENSE b/LICENSE deleted file mode 100644 index ee58399..0000000 --- a/LICENSE +++ /dev/null @@ -1,127 +0,0 @@ - 木兰宽松许可证, 第2版 - - 木兰宽松许可证, 第2版 - 2020年1月 http://license.coscl.org.cn/MulanPSL2 - - - 您对“软件”的复制、使用、修改及分发受木兰宽松许可证,第2版(“本许可证”)的如下条款的约束: - - 0. 定义 - - “软件”是指由“贡献”构成的许可在“本许可证”下的程序和相关文档的集合。 - - “贡献”是指由任一“贡献者”许可在“本许可证”下的受版权法保护的作品。 - - “贡献者”是指将受版权法保护的作品许可在“本许可证”下的自然人或“法人实体”。 - - “法人实体”是指提交贡献的机构及其“关联实体”。 - - “关联实体”是指,对“本许可证”下的行为方而言,控制、受控制或与其共同受控制的机构,此处的控制是指有受控方或共同受控方至少50%直接或间接的投票权、资金或其他有价证券。 - - 1. 授予版权许可 - - 每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的版权许可,您可以复制、使用、修改、分发其“贡献”,不论修改与否。 - - 2. 授予专利许可 - - 每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的(根据本条规定撤销除外)专利许可,供您制造、委托制造、使用、许诺销售、销售、进口其“贡献”或以其他方式转移其“贡献”。前述专利许可仅限于“贡献者”现在或将来拥有或控制的其“贡献”本身或其“贡献”与许可“贡献”时的“软件”结合而将必然会侵犯的专利权利要求,不包括对“贡献”的修改或包含“贡献”的其他结合。如果您或您的“关联实体”直接或间接地,就“软件”或其中的“贡献”对任何人发起专利侵权诉讼(包括反诉或交叉诉讼)或其他专利维权行动,指控其侵犯专利权,则“本许可证”授予您对“软件”的专利许可自您提起诉讼或发起维权行动之日终止。 - - 3. 无商标许可 - - “本许可证”不提供对“贡献者”的商品名称、商标、服务标志或产品名称的商标许可,但您为满足第4条规定的声明义务而必须使用除外。 - - 4. 分发限制 - - 您可以在任何媒介中将“软件”以源程序形式或可执行形式重新分发,不论修改与否,但您必须向接收者提供“本许可证”的副本,并保留“软件”中的版权、商标、专利及免责声明。 - - 5. 免责声明与责任限制 - - “软件”及其中的“贡献”在提供时不带任何明示或默示的担保。在任何情况下,“贡献者”或版权所有者不对任何人因使用“软件”或其中的“贡献”而引发的任何直接或间接损失承担责任,不论因何种原因导致或者基于何种法律理论,即使其曾被建议有此种损失的可能性。 - - 6. 语言 - “本许可证”以中英文双语表述,中英文版本具有同等法律效力。如果中英文版本存在任何冲突不一致,以中文版为准。 - - 条款结束 - - 如何将木兰宽松许可证,第2版,应用到您的软件 - - 如果您希望将木兰宽松许可证,第2版,应用到您的新软件,为了方便接收者查阅,建议您完成如下三步: - - 1, 请您补充如下声明中的空白,包括软件名、软件的首次发表年份以及您作为版权人的名字; - - 2, 请您在软件包的一级目录下创建以“LICENSE”为名的文件,将整个许可证文本放入该文件中; - - 3, 请将如下声明文本放入每个源文件的头部注释中。 - - Copyright (c) [Year] [name of copyright holder] - [Software Name] is licensed under Mulan PSL v2. - You can use this software according to the terms and conditions of the Mulan PSL v2. - You may obtain a copy of Mulan PSL v2 at: - http://license.coscl.org.cn/MulanPSL2 - THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. - See the Mulan PSL v2 for more details. - - - Mulan Permissive Software License,Version 2 - - Mulan Permissive Software License,Version 2 (Mulan PSL v2) - January 2020 http://license.coscl.org.cn/MulanPSL2 - - Your reproduction, use, modification and distribution of the Software shall be subject to Mulan PSL v2 (this License) with the following terms and conditions: - - 0. Definition - - Software means the program and related documents which are licensed under this License and comprise all Contribution(s). - - Contribution means the copyrightable work licensed by a particular Contributor under this License. - - Contributor means the Individual or Legal Entity who licenses its copyrightable work under this License. - - Legal Entity means the entity making a Contribution and all its Affiliates. - - Affiliates means entities that control, are controlled by, or are under common control with the acting entity under this License, ‘control’ means direct or indirect ownership of at least fifty percent (50%) of the voting power, capital or other securities of controlled or commonly controlled entity. - - 1. Grant of Copyright License - - Subject to the terms and conditions of this License, each Contributor hereby grants to you a perpetual, worldwide, royalty-free, non-exclusive, irrevocable copyright license to reproduce, use, modify, or distribute its Contribution, with modification or not. - - 2. Grant of Patent License - - Subject to the terms and conditions of this License, each Contributor hereby grants to you a perpetual, worldwide, royalty-free, non-exclusive, irrevocable (except for revocation under this Section) patent license to make, have made, use, offer for sale, sell, import or otherwise transfer its Contribution, where such patent license is only limited to the patent claims owned or controlled by such Contributor now or in future which will be necessarily infringed by its Contribution alone, or by combination of the Contribution with the Software to which the Contribution was contributed. The patent license shall not apply to any modification of the Contribution, and any other combination which includes the Contribution. If you or your Affiliates directly or indirectly institute patent litigation (including a cross claim or counterclaim in a litigation) or other patent enforcement activities against any individual or entity by alleging that the Software or any Contribution in it infringes patents, then any patent license granted to you under this License for the Software shall terminate as of the date such litigation or activity is filed or taken. - - 3. No Trademark License - - No trademark license is granted to use the trade names, trademarks, service marks, or product names of Contributor, except as required to fulfill notice requirements in Section 4. - - 4. Distribution Restriction - - You may distribute the Software in any medium with or without modification, whether in source or executable forms, provided that you provide recipients with a copy of this License and retain copyright, patent, trademark and disclaimer statements in the Software. - - 5. Disclaimer of Warranty and Limitation of Liability - - THE SOFTWARE AND CONTRIBUTION IN IT ARE PROVIDED WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED. IN NO EVENT SHALL ANY CONTRIBUTOR OR COPYRIGHT HOLDER BE LIABLE TO YOU FOR ANY DAMAGES, INCLUDING, BUT NOT LIMITED TO ANY DIRECT, OR INDIRECT, SPECIAL OR CONSEQUENTIAL DAMAGES ARISING FROM YOUR USE OR INABILITY TO USE THE SOFTWARE OR THE CONTRIBUTION IN IT, NO MATTER HOW IT’S CAUSED OR BASED ON WHICH LEGAL THEORY, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. - - 6. Language - - THIS LICENSE IS WRITTEN IN BOTH CHINESE AND ENGLISH, AND THE CHINESE VERSION AND ENGLISH VERSION SHALL HAVE THE SAME LEGAL EFFECT. IN THE CASE OF DIVERGENCE BETWEEN THE CHINESE AND ENGLISH VERSIONS, THE CHINESE VERSION SHALL PREVAIL. - - END OF THE TERMS AND CONDITIONS - - How to Apply the Mulan Permissive Software License,Version 2 (Mulan PSL v2) to Your Software - - To apply the Mulan PSL v2 to your work, for easy identification by recipients, you are suggested to complete following three steps: - - i Fill in the blanks in following statement, including insert your software name, the year of the first publication of your software, and your name identified as the copyright owner; - - ii Create a file named “LICENSE” which contains the whole context of this License in the first directory of your software package; - - iii Attach the statement to the appropriate annotated syntax at the beginning of each source file. - - - Copyright (c) [Year] [name of copyright holder] - [Software Name] is licensed under Mulan PSL v2. - You can use this software according to the terms and conditions of the Mulan PSL v2. - You may obtain a copy of Mulan PSL v2 at: - http://license.coscl.org.cn/MulanPSL2 - THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE. - See the Mulan PSL v2 for more details. diff --git a/README.html b/README.html deleted file mode 100644 index 21201f8..0000000 --- a/README.html +++ /dev/null @@ -1,2063 +0,0 @@ - - - -README.md - - - - - - - - - - - - -

软件测试

-

写在最前面

-

1 课程目标

-
    -
  • 掌握基础的软件测试理论、测试方法和策略
  • -
  • 掌握常用工具使用
  • -
  • 根据需求和设计文档独立编写测试计划、测试方案、测试用例以及测试报告
  • -
-

2 主要内容

-
    -
  • 软件测试基础知识
  • -
  • 软件测试通用技术
  • -
  • 软件测试流程
  • -
  • 黑盒测试
  • -
  • 白盒测试
  • -
  • 性能测试
  • -
  • 软件测试自动化
  • -
  • 软件测试管理
  • -
-

3 课程安排

-

学时安排:72课时(理论36+实践36)
-教材:清华大学出版社 《软件测试》(第2版) 周元哲 编著

-

4 课程资源

- -

第1章 软件测试概论

-

1.1 软件

-

1.1.1 软件定义

-

软件是一系列按照特定顺序组织的计算机数据和指令的集合。
-软件 ≠ 程序(代码)
-软件包含如下内容:

-
    -
  1. 运行时,能够提供所要求功能和性能的指令或计算机程序。
  2. -
  3. 程序能够处理信息的数据结构。
  4. -
  5. 用于描述程序功能需求、程序如何操作和如何使用的文档。
  6. -
-

1.1.2 文档

-
开发文档
-

开发文档是描述软件开发过程,包括软件需求、软件设计、软件测试、保证软件质量的一类文档,开发文档也包括软件的详细技术描述、程序逻辑、程序间相互关系、数据格式和存储等。

-
    -
  • 《可行性研究》
  • -
  • 《项目任务书》
  • -
  • 《需求规格说明书》
  • -
  • 《概要设计》
  • -
  • 《详细设计》
  • -
  • 《代码规范说明书》
  • -
  • 《数据字典》
  • -
  • 《开发计划》
  • -
-
管理文档
-

从管理的角度规定涉及软件生存的信息:

-
    -
  1. 职责定义
  2. -
  3. 开发过程的每个阶段的进度和进度变更的记录
  4. -
  5. 软件变更情况的记录
  6. -
  7. 相对于开发的判定记录
  8. -
-
    -
  • 《工作报告》
  • -
  • 《工作日志》
  • -
  • 《会议记录》
  • -
  • 《里程碑报告》
  • -
  • 《软件项目配置管理计划》
  • -
  • 《实施方案》
  • -
-
产品文档
-

为使用和运行软件产品的任何人规定培训和参考信息,促进软件产品的市场流通或提高可接受性。使得那些未参加开发本软件的程序员维护它。

-
    -
  • 《产品手册》
  • -
  • 《用户指南》
  • -
  • 《培训手册》
  • -
  • 《软件支持手册》
  • -
-

1.1.3 软件发展史

-
    -
  1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。软件 = 程序
  2. -
  3. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。
  4. -
  5. 软件工程阶段:以软件的产品化,系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。
  6. -
  7. 多层分布结构,面向服务架构
  8. -
-

1.1.4 软件项目

-

软件项目是一种特殊的项目,具有如下特点:

-
    -
  1. 知识密集型,技术含量高
  2. -
  3. 涉及多个专业领域,多种技术综合应用
  4. -
  5. 项目范围和目标的灵活性
  6. -
  7. 风险大,收益大
  8. -
  9. 客户化程度高
  10. -
  11. 过程管理重要
  12. -
-

1.2 软件生命周期

-

1.2.1 需求定义

-

描述: 定义出本次任务都需要做什么,做成什么样子。
-参与者: 产品经理、需求分析师、客户

-

1.2.2 可行性分析

-

描述: 由项目组相关成员去研究需求是否可行,能不能做出来。
-参与者: 产品经理、架构师、项目经理、开发

-

1.2.3 需求分析

-

描述: 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个输入框、每个按钮的样式,输入输出等各项值。
-参与者: 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发
-输出:《需求规格说明书》

-

1.2.4 评审

-

描述: 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。
-参与者: 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等

-

1.2.5 设计

-

描述: 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此基础上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。
-参与者: 项目经理、架构师、开发、测试

-

1.2.6 编码

-

描述: 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。
-参与者: 开发

-

1.2.7 提测

-

描述: 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。
-参与者: 任务责任人(开发)、测试

-

1.2.8 测试

-
- 测试需求
-- 测试计划
-- 测试设计
-- 测试执行
-- 回归测试
-- 测试评估
-
-

1.2.9 部署/发版

-

描述: 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。
-参与人: 配置管理人员、测试 -10. 支持维护
-描述: 支持维护类似于我们日常中的售后,主要是对已卖出的产品/已上线的项目进行日常维护。包括纠错性维护和改进性维护两个方面。
-参与人: 支持维护人员/售后工程师

-

1.3 软件测试概述

-

1.3.1 软件测试定义

-

软件测试的经典定义是:在规定的条件下对程序进行操作,以发现程序错误,衡量软件质量,并对其是否能满足设计要求进行评估的过程。
-IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。

-

1.3.2 测试发展历程

-
    -
  1. 1957年之前-调试为主(Debugging Oriented)
    -软件规模小,复杂度低,开发人员承担需求分析、设计、开发、测试等所有工作,等同于调试。
  2. -
  3. 1957–1978-证明为主(Demonstration Oriented)
    -与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。
  4. -
  5. 1979–1982-破坏为主(Destruction Oriented)
    -1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义:
  6. -
-
The process of executing a program with the intent of finding errors. -测试是为发现错误而执行程序的过程。 -
-

这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。

-
    -
  1. 1983–1987-评估为主(Evaluation Oriented)
    -软件行业进入了大发展时期,软件趋向大型化、复杂度,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。
  2. -
  3. 1988–至今-预防为主(Prevention Oriented)
    -尽量早的介入,尽量早的发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。
  4. -
-

1.3.3 测试与开发的关系

-

瀑布模型
-瀑布模型

-

这是一种经典模型,提供了软件开发的基本框架。
-强调开发工作(计划、设计、开发、测试、维护等)各阶段之间的先后顺序,不可以并行操作。
-瀑布模型认为,测试是指代码完成后,处于运行维护阶段之前。如果需求和设计上存在缺陷,就会造成大量返工,增加成本。为了更早的发现问题,测试应延伸到需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。
-优点:

-
    -
  1. 各阶段划分清晰
  2. -
  3. 强调计划与需求分析
  4. -
  5. 适合需求稳定的产品开发
  6. -
-

缺点:

-
    -
  1. 单一流程,不可逆
  2. -
  3. 风险显露得晚,纠正机会少
  4. -
  5. 测试只是其中一个阶段,缺乏全过程测试思想
  6. -
-

V模型
-V模型

-

强调将测试和开发同等重要,对于开发阶段都有与之对应的测试阶段。
-优点:
-相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。
-缺点:
-虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。

-

W模型(双V模型)
-W模型

-

明确表示出了测试与开发的并行关系
-优点:
-W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。
-缺点: -W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。

-

螺旋模型
-螺旋模型

-

大型软件项目通常有很多不确定性和风险,如果采用瀑布式线性过程模型,失败风险很大,因此需要采取一种渐进式的演化过程模型。将产品分解成增量版本,每个版本单独测试。 -敏捷模型
-敏捷模型

-

敏捷开发以用户的需求进化为核心,采用迭代、循序渐进的方法进行软件开发。专注于交付对客户有价值的软件(可以工作的)。

-

强调以人为核心,程序员团队和业务专家之间的紧密联系,频繁交付新的软件版本,紧凑的自我组织型团队,更注重软件开发中人的作用。

-

在敏捷开发中,软件项目在构建初期被切分成多个子项目,各个子项目的成果都经过测试,具备可视、可集成和可运行使用的特征。换言之,就是把一个大项目分为多个相互联系,但也可独立运行的小项目,并分别完成,在此过程中软件一直处于可使用状态。

-

《联盟敏捷宣言》

-
    -
  1. 最重要的是通过尽早和不断交付有价值的软件满足客户需要。
  2. -
  3. 我们欢迎需求的变化,即使在开发后期。敏捷过程能够驾驭变化,保持客户的竞争优势。
  4. -
  5. 经常交付可以工作的软件,从几星期到几个月,时间尺度越短越好。
  6. -
  7. 业务人员和开发者应该在整个项目过程中始终朝夕在一起工作。
  8. -
  9. 围绕斗志高昂的人进行软件开发,给开发者提供适宜的环境,满足他们的需要,并相信他们能够完成任务。
  10. -
  11. 在开发小组中最有效率也最有效果的信息传达方式是面对面的交谈。
  12. -
  13. 可以工作的软件是进度的主要度量标准。
  14. -
  15. 敏捷过程提倡可持续开发。出资人、开发人员和用户应该总是维持不变的节奏。
  16. -
  17. 对卓越技术与良好设计的不断追求将有助于提高敏捷性。
  18. -
  19. 简单——尽可能减少工作量的艺术至关重要。
  20. -
  21. 最好的架构、需求和设计都源自自我组织的团队。
  22. -
  23. 每隔一定时间,团队都要总结如何更有效率,然后相应地调整自己的行为。
  24. -
-

解读:

-
    -
  • -

    个体和互动高于流程和工具
    -以人为本,没有比面对面交流更高效的沟通渠道了,基于互相信任的前提,敏捷提倡自治的全功能团队。 -在工作形式上,整个团队平时坐在一起工作,从物理空间上创造了更加便捷面对面的沟通机会。在团队职责上,团队内部具备完成软件交付的角色(能力),团队所有人对软件的质量负责,开发过程由团队内部把控,业务价值团队内部快速流动,在任何环节都能及时获得反馈。同时,每个角色都更容易从全局视角去思考软件,避免了传统部门墙模式下的视角割裂和协作障碍。

    -
  • -
  • -

    工作的软件高于详尽的文档
    -为客户交付可工作的软件是我们的核心目标,我们应该尽早交付可进行端到端测试的代码,该目标决定了我们不应该花过多精力在面面俱到的文档上,但这不代表我们要抵制任何文档。实践证明,轻量级的文档策略有助于团队高质量交付可工作的软件。

    -
  • -
  • -

    客户合作高于合同谈判
    -主动拥抱变化,及时响应,持续交付。

    -
  • -
  • -

    响应变化高于遵循计划
    -通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费

    -
  • -
-

缺点:
-由于其项目周期很长,所以很难保证开发的人员不更换,而缺少文档就会造成在交接的过程中出现很大的困难。

-

敏捷开发流程

-

1.4 软件缺陷

-

1.4.1 缺陷定义

-

IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。

-

符合下面4个条件之一就是缺陷:

-
    -
  1. 软件未达到规格说明书中规定的功能。
  2. -
  3. 软件出现了产品说明数中指明的不会出现的错误。
  4. -
  5. 软件功能超出了产品说明书中指明的范围。
  6. -
  7. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。
  8. -
-

1.4.2 产生原因

-
    -
  1. 软件本身复杂性,产生大量不确定因素。
  2. -
  3. 成本、时间限制,导致流程不够完善,文档缺失,缺乏严谨的评审。
  4. -
  5. 人员本身技能水平、责任心、交流沟通不顺畅。
  6. -
  7. 不全面或者没有复审。
  8. -
-

1.4.3 缺陷来源

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
缺陷来源描述
需求说明书需求说明书错误或描述不清
设计文档设计文档描述不准确,与需求不一致
系统集成接口各模块参数不匹配
数据流(库)数据字典、数据库中的错误
程序代码编码问题
-

1.4.4 缺陷类型

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
缺陷类型描述
功能未达到规格说明书中规定的功能,影响系统使用
用户界面未按照原型设计,影响交互,如:显示格式,按钮位置
文档文档内容不完整或不正确,影响发布和维护
软件包由于软件配置库、变更管理或版本控制引发的错误
性能执行时间长、处理速度慢、负载高等方面
接口与其他模块参数不匹配
-

1.4.5 缺陷级别

-

严重性: 表示软件缺陷的恶劣程度,当用户碰到该缺陷时影响的可能性和程度。
-优先级: 表示修复缺陷的重要程度和紧迫程度。

-
严重性
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
级别名称说明示例
S1致命错误严重阻碍开发或测试工作的进行,必须马上解决安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件
S2严重缺陷系统出现重大问题,影响提供的主要功能使用内存泄露
数据无法保存
S3主要错误主要功能实现有问题,易用性不够好某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码
S4次要错误次要功能实现有问题或者手册相关问题个别不常用的属性不生效或实现有问题(前提:不影响主要功能使用)
次要功能实现与需求不符或实现有问题(如:日志不能轮转、预警策略不生效、搜索框不能用、快照生成格式有问题等)
错别字
手册描述不合理或样式格式有问题
S5轻微缺陷建议,不属于缺陷
-
优先级
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
级别名称说明
P1不影响整个系统的正常运行,一般指建议性的问题
P2不影响继续测试,但也是必须要修改的,对功能的实现有所影响,如果时间允许应该修复
P3影响整个测试的继续进行,要马上修改
P4系统无法继续执行下去,必须立即修改
-

严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为1这样的缺陷着手,而不是优先修复简单的,由简到难。

-

综合使用重要性等级和严重性双标准的优先顺序:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
S1. 致命错误S2. 严重缺陷S3. 主要错误S4. 次要错误S5. 轻微缺陷
P4. 急立即修复
3小时内
第2修复
1天内
第4修复
2天内
第7修复
3天内
第11修复
4天内
P3. 高第3修复
1-2天内
第5修复
2-3天内
第8修复
3-4天内
第12修复
4-5天内
第15修复
5-6天内
P2. 中第6修复
3-4天内
第9修复
4-5天内
第13修复
5-6天内
第16修复
6-7天内
第18修复
2-3周内
P1. 低第10修复
8-7天内
第14修复
7-9天内
第17修复
8-12天内
第19修复
3-4周内
第20修复
择期
-

1.4.6 跟踪流程

-

最优化、最简单的生命周期是:(理想情况)

-
    -
  1. 测试员发现缺陷并记录缺陷报告。
  2. -
  3. 缺陷报告交给程序员,此时缺陷状态是打开。(open state)
  4. -
  5. 程序员修改缺陷,此时缺陷状态是解决。(resolved state)
  6. -
  7. 缺陷报告交还测试员。
  8. -
  9. 测试员确认已修复。
  10. -
  11. 测试员关闭缺陷报告,此时缺陷状态是关闭。(closed state)
  12. -
-

一个缺陷很可能会被反复打开→关闭。在日常工作过程中,由于开发修订其他缺陷影响、需求变更等因素缺陷可能会被反复打开→关闭。

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
缺陷状态描述
打开确认提交的缺陷,等待处理
已分配分配开发人员进行修复
已解决经过开发人员修复,等待测试人员验证
已验证测试人员验证修复成功
已关闭修复完成,确认测试通过
重新打开测试验证依然存在缺陷,等待开发修复
推迟暂不解决,可能在下一个版本修复
保留条件不允许,不能修复
不能重现开发不能复现这个缺陷,需要测试人员检查缺陷发现步骤
-

1.4.7 缺陷记录内容

-
    -
  1. bug编号:bug的唯一id,以方便尽快找到此bug。
  2. -
  3. bug标题:bug摘要,阐述bug大体内容。
  4. -
  5. bug严重级别,优先级:作为缺陷是否修复以及缺陷修复优先级的决定性因素。
  6. -
  7. bug产生的模块:记录bug所属模块,方便开发定位问题。
  8. -
  9. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题。
  10. -
  11. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。
  12. -
  13. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。
  14. -
-

以上是上报bug、创建bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含:

-
    -
  1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。
  2. -
  3. bug修订人:bug修订人员。
  4. -
  5. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。
  6. -
  7. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。
  8. -
  9. bug复测说明:由复测人员来写,说明复测过程,复测结果等。
  10. -
  11. bug备注:备注,以便记录一些额外信息。
  12. -
-

1.4.8 缺陷预防

-

差错:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源)
-错误:软件内部问题,设计错误、编码错误。(内部原因)
-失效:软件系统运行时偏离了用户需求。(外部表现)

-

1.5 软件测试行业

-

1.5.1 行业现状

-

软件系统越来越复杂,一个软件不能够由单独的软件工程师单独编写,而是由团队进行配合,每个人可能只负责一个模块,对于全局没有过多的了解,这时如果运行软件就会容易产生很多的错误。在行业内将这些错误叫做BUG。并且每一个软件工程师都会有思维的死角,自己不容易发现自己编写出来的错误。所以这个时候就需要专门的软件测试工程师用专业的测试方式来检查软件。检查该软件是否符合客户要求的产品设计,是否能够符合大多数用户的使用习惯,如果发现异常状态及时进行处理。软件市场虽然远远没有达到饱和但是各种各样功能的软件也层出不穷竞争激烈,对软件开发的质量要求也是日益增高。

-

我国软件测试行业起步较晚,发展较慢,直到21世纪初期,我国才逐步开始重视软件测试行业。但近年来,软件行业的快速发展为软件测试行业的发展提供了良好的基础,随着我国软件测试行业的发展,行业内企业向规模化发展将获得规模效应,可以有效降低企业的单位成本;而软件测试技术的不断发展,也将淘汰那些技术实力较弱的企业,促使行业内企业向专业化方向发展。

-

在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量1。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。

-

从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。

-

当前国内软件测试行业主要存在以下问题:

-
    -
  1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题。
  2. -
  3. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步。
  4. -
  5. 对于分布式系统整体性能还难以进行很好的测试。
  6. -
  7. 对于实时系统缺乏有效的测试手段。
  8. -
  9. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题。
  10. -
  11. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合。
  12. -
  13. 缺乏软件测试意识、对其重视不够。
  14. -
  15. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准。
  16. -
  17. 高校从师资储备到专业设置再到人才培养的机制薄弱。
  18. -
-

国内外软件测试差距

-
    -
  1. 测试的理解认识
  2. -
  3. 测试过程的管理
  4. -
  5. 测试工具的使用
  6. -
  7. 测试人员的培养
  8. -
-

1.5.2 未来趋势

-
    -
  1. 以软件为代表的计算机行业正在以一种井喷式的趋势发展
  2. -
  3. 人才缺口大
  4. -
  5. 女性员工受到青睐
  6. -
  7. 未来发展空间大
  8. -
  9. 外包为主
  10. -
-

1.5.3 软件测试职业发展

-
    -
  1. 技术方向 -
      -
    • 敏捷测试专家
    • -
    • 高级测试开发专家
    • -
    • 专项测试专家
    • -
    • QA-Ops 专家
    • -
    -
  2. -
  3. 管理方向 -
      -
    • 测试组长
    • -
    • 测试经理
    • -
    • 项目测试负责人
    • -
    • 测试总监
    • -
    -
  4. -
  5. 易转型方向 -
      -
    • 项目经理
    • -
    • 产品经理
    • -
    -
  6. -
-

1.5.4 测试思维方式

-
    -
  1. 逆向思维方式
  2. -
  3. 组合思维方式
  4. -
  5. 全局思维方式
  6. -
  7. 两级思维方式
  8. -
  9. 比较思维方式
  10. -
  11. 发散思维方式
  12. -
-

1.6 测试认识的误区

-
    -
  1. 使用了测试工具,就进行了有效的测试
  2. -
  3. 存在太多无法测试的东西
  4. -
  5. 软件开发完成后才进行测试
  6. -
  7. 软件发布后发现质量问题,是测试人员的问题
  8. -
  9. 软件测试很简单,就是点点点,是个人就能做
  10. -
  11. 软件测试没有前途,只有程序员才是软件高手
  12. -
  13. 软件测试是测试人员的事情和程序员无关
  14. -
  15. 项目进度吃紧时少做测试,时间多时多做测试
  16. -
  17. 测试要进行穷尽测试
  18. -
  19. 采样是随机抽取过程
  20. -
  21. 测试和开发是对头
  22. -
  23. 测试少报bug开发就会高兴点,报告也会好看点
  24. -
  25. 自动化测试终会取代手工测试
  26. -
  27. 规范化软件测试是增加项目成本
  28. -
  29. 越多测试越有效
  30. -
  31. 软件测试工作只负责项目上线/产品发布之前的部分
  32. -
-

1.7 知识点总结

-

第2章 软件测试基础知识

-

2.1 概述

-
    -
  1. 从软件测试的目的来理解
    -软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。
  2. -
  3. 从软件测试的性质来理解 -在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的”。
  4. -
  5. 从软件开发角度来理解 -软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障。
  6. -
  7. 从软件工程角度来理解
    -软件测试是软件工程的一部分,是软件工程过程中的重要阶段。
  8. -
  9. 从软件质量保证角度来理解
    -软件测试是软件质量保证的重要措施。
  10. -
-

2.2 测试的目的和原则

-

2.2.1 测试的目的

-
    -
  1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进。
  2. -
  3. 检测产品是否符合用户要求。
  4. -
  5. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法。
  6. -
  7. 提升用户体验。
  8. -
-

2.2.2 测试的原则

-
    -
  1. 软件测试是证伪而非证实。
  2. -
  3. 尽早地、不断地进行测试。
  4. -
  5. 重视无效数据和非预期的测试。
  6. -
  7. 应当对每一个测试结果做全面的检查。
  8. -
  9. 测试现场保护和资料归档。
  10. -
  11. 程序员应避免检查自己的程序。
  12. -
  13. 充分注意测试中的集群现象。
  14. -
  15. 用例要定期评审,适时补充修改用例。
  16. -
-

2.3 测试分类

-

2.3.1 按照测试阶段划分

-
    -
  1. 单元测试
  2. -
  3. 集成测试
  4. -
  5. 确认测试
  6. -
  7. 系统测试
  8. -
  9. 验收测试
  10. -
-

软件测试阶段对照表:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
测试阶段主要依据参与人员/测试方式主要测试内容
单元测试《详细设计》开发小组执行白盒测试规范、逻辑、路径
集成测试《概要设计》
《需求文档》
开发小组执行白盒测试、黑盒测试接口、路径、功能、性能
系统测试《需求文档》独立测试小组执行黑盒测试功能测试、界面测试、安全测试、兼容性测试、易用性测试、性能测试、压力测试、负载测试
验收测试《需求文档》用户执行黑盒测试同上
-

2.3.2 按照执行状态划分

-
    -
  1. 静态测试
  2. -
  3. 动态测试
  4. -
-

2.3.3 按照测试技术划分

-
    -
  1. 白盒测试
  2. -
  3. 黑盒测试
  4. -
  5. 灰盒测试
  6. -
-

2.3.4 按照执行主体划分

-
    -
  1. α测试
  2. -
  3. β测试
  4. -
  5. 第三方测试
  6. -
-

2.3.5 按照测试内容划分

-
    -
  1. 界面测试
  2. -
  3. 功能测试
  4. -
  5. 安全测试
  6. -
  7. 兼容性测试
  8. -
  9. 易用性测试
  10. -
  11. 性能测试
  12. -
-

2.3.6 按照是否手工操作划分

-
    -
  1. 手工测试
  2. -
  3. 自动化测试
  4. -
-

2.4 测试用例

-

2.4.1 简介

-

测试用例是指对一项特定的软件产品进行测试任务的描述,体现测试方案、方法、技术和策略。其内容包括:测试目标、测试环境、输入数据、测试步骤、预期结果、测试脚本等,最终形成文档。

-

简单的认为,测试用例是为某个特定目标而编制的一组测试输入、执行条件和预期结果,用于核实是否满足某个特定的软件需求。

-

选择测试用例是软件测试员最重要的一项任务,不正确的选择可能导致测试量过大或者过小,甚至测试目标不对。准确评估风险,把无穷尽的可能性减少到可以控制的范围是软件测试成功的诀窍。

-

2.4.2 测试用例的作用

-
    -
  1. 指导测试的实施
  2. -
  3. 评估测试结果的度量基准
  4. -
  5. 保证软件的可维护性和可复用性
  6. -
  7. 分析缺陷的标准
  8. -
-

2.4.3 测试用例设计准则

-
    -
  1. 有效性
  2. -
  3. 经济性
  4. -
  5. 完备性
  6. -
  7. 可判定性
  8. -
  9. 可再现性
  10. -
-

2.4.4 测试用例维护

-

术语

-
    -
  1. 测试编号:测试用例的编号
  2. -
  3. 测试项:测试的功能点说明
  4. -
  5. 前置条件:该测试用例的前提条件,比如测试wangdachui/dachui12345(用户名/密码)账户是否能正确登录进去,那前提wangdachui/dachui12345已定是注册过的
  6. -
  7. 测试步骤:就是测试的所有操作步骤,最好是每一个步骤应该对应一个期望结果,最少也得一个测试用例对应一个期望结果
  8. -
  9. 期望结果:就是希望得到的结果(正确的结果)
  10. -
  11. 测试结果:实际测试的结果,可选项有:通过、不通过、暂时挂起/锁定(就是暂时不测试);
  12. -
  13. 对应的bug:当期望结果与实际结果不符时测试不通过,此时需要上报bug(纪录缺陷),bug需要与测试用例对应
  14. -
  15. 测试执行人:实际由谁来执行测试用例;也有任务分配人的选项,就是测试用例分配给哪个测试员来测试
  16. -
  17. 备注:做一些备注或者测试的说明
  18. -
  19. 合法用户:就是已经注册过的用户
  20. -
  21. 非法用户:没有注册过;注册过但是用户名/密码不匹配的;本文特指未注册过的用户
  22. -
-

测试用例维护一般分为以下几种情况:

-
    -
  1. 产品特性没变:漏测或者环境变更,这个时候版本没变,测试用例增加和修改均可
  2. -
  3. 原有特性变化:功能变化,只能新增,不能修改,还要兼容老版本
  4. -
  5. 原有功能取消:测试用例在新版本上置为“空”标志或者“无效状态”,对于先前版本有效
  6. -
  7. 新增功能:新增用例,对应新版本标志
  8. -
-

2.4.5 测试用例设计误区

-
    -
  1. 测试用例设计等同于测试输入数据设计
  2. -
  3. 测试用例设计越详细越好
  4. -
  5. 追求测试用例设计“一步到位”
  6. -
  7. 将多个测试条件混在一个用例中
  8. -
-

2.5 测试停止标准

-

2.5.1 软件测试停止总体标准

-
    -
  1. 测试超过了预定时间
  2. -
  3. 执行了所有的测试用例,并没有发现故障
  4. -
  5. 使用特定的测试用例设计方法作为判断测试停止的基础
  6. -
  7. 给出测试停止的要求
  8. -
  9. 根据经单位时间内查出故障的数量决定是否停止测试
  10. -
  11. 软件系统经过了单元、集成、系统测试,分别达到停止标准。通过验收测试,得出验收测试结论。
  12. -
  13. 软件项目暂停以进行调整,测试应随之暂停,并备份暂停点数据。或者软件项目开发生命周期内出现重大估算、进度偏差,需暂停或终止时,测试应随之暂停或终止,并备份数据
  14. -
-

2.5.2 软件测试各阶段停止标准

-
单元测试停止标准
-
    -
  1. 单元测试用例已经通过评审
  2. -
  3. 按照单元测试计划完成了所有规定单元测试
  4. -
  5. 达到了测试计划中关于单元测试所规定的覆盖率要求
  6. -
  7. 被测试的单元每千行代码必须发现至少3个错误
  8. -
  9. 软件单元功能与设计一致
  10. -
  11. 单元测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. -
-
集成测试停止标准
-
    -
  1. 集成测试用例已经通过评审
  2. -
  3. 按照集成测试计划和增量集成策略完成了整个系统的集成测试
  4. -
  5. 达到了测试计划中关于集成测试所规定的覆盖率要求
  6. -
  7. 被测试的集成工作版本每千行代码必须发现至少2个错误
  8. -
  9. 集成工作版本满足设计定义的各项功能、性能要求
  10. -
  11. 在集成测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. -
-
系统测试停止标准
-
    -
  1. 系统测试用例已经通过评审
  2. -
  3. 按照系统测试计划完成了系统测试
  4. -
  5. 达到了测试计划中关于系统测试所规定的覆盖率要求
  6. -
  7. 被测试的系统每千行代码必须发现至少1个错误
  8. -
  9. 系统测试满足设计需求规格说明书要求
  10. -
  11. 在系统测试中发现的错误已经得到修改,各级缺陷修复率达到标准
  12. -
-

2.6 知识点总结

-

第3章 黑盒测试

-

3.1 概述

-

黑盒测试也称功能测试,通过测试来检测每个功能是否都能正常使用。

-

着眼于程序外部结构,不考虑内部逻辑结构,通过测试检验每个功能是否能正常使用。在程序接口进行测试,只检查程序功能是否按照需求规格说明书的规定正常使用,程序是否能适当的接受输入数据而产生正确的输出信息。

-

黑盒测试从用户的角度出发,以输入数据与输出数据的对应关系进行测试,数据驱动。

-

黑盒测试注重测试软件的功能需求,主要视图发现下列几类错误

-
    -
  1. 功能不正确或遗漏
  2. -
  3. 界面错误
  4. -
  5. 数据库访问错误
  6. -
  7. 性能错误
  8. -
  9. 初始化和终值错误
  10. -
-

3.2 等价类划分

-

等价类是指某个输入域的子集合。在该子集合中,测试某等价类的代表值就等于对这类其他值的测试,对于揭露程序的错误是等效的。

-

要注意的是,在进行等价类划分的过程中,我们不仅要考虑有效等价类划分,也要考虑无效等价类划分。

-

有效等价类:是指输入完全符合程序规格说明的数据集合。利用有效等价类可以测试程序是否满足规格说明书规定的功能和性能。

-

无效等价类:和有效等价类相反,是指对程序的规格说明无意义、不合理的输入数据构成的集合。

-

3.2.1 划分原则

-
    -
  1. 在输入条件规定了取值范围的情况下,可以确立一个有效等价类(在取值范围之内)和两个无效等价类(小于取值范围和大于取值范围)。
  2. -
  3. 在输入条件规定了取回个数的情况下,可以确立一个有效等价类(在取值个数范围之内)和两个无效等价类(小于取值个数和大于取值个数)。
  4. -
  5. 在输入条件规定了输入值的集合的情况下,可以确立一个有效等价类和一个无效等价类。
  6. -
  7. 在输入条件规定了“必须如何”条件的情况下,可以确立一个有效等价类和一个无效等价类。
  8. -
  9. 在输入条件是一个布尔值的情况下,可以确立一个有效等价类和一个无效等价类。
  10. -
  11. 在规定了输入数据的一组值(假定n个),并且程序要对每一个输入值分别处理的将情况下,可以确立n个有效等价类和一个无效等价类。
  12. -
  13. 在规定了输入数据必须遵守规则的情况下,可以确立一个有效等价类(符合规则)和若干个无效等价类(从不同角度违反规则)。
  14. -
  15. 在确知已划分的等价类中各元素在程序处理中的方式不同的情况下,则应再将改等价类进一步划分为更小的等价类。
  16. -
-

3.2.2 设计测试用例步骤

-
    -
  1. 形成等价类表,每一等价类规定一个唯一编号
  2. -
  3. 设计测试用例,使其尽可能多的覆盖尚未覆盖的有效等价类
  4. -
  5. 设计一个新的测试用例,使其只覆盖一个无效等价类,重复这一步直到所有无效等价类均被覆盖。
  6. -
-

3.2.3 等价类举例

-

我们要测试学习成绩这一输入框(假设总成绩都是100),那么我们就可以如下图划分,有效的成绩是>=0且<=100的,无效的是<0和>100这两部分。

-

等价类举例

-

另外图中还有一个无效等价类没有表现出来--非数字字符(比如:英文字母、中文、特殊的符号等单一或者组合,如a、abc、你好、你abc、你=我、\你\a\等;以及他们分别与数字组合,比如:a123、321a、你123、12你、1你2、1\2、1=你等)。

-

那么根据上述分析,最终设计出来的测试用例如下:

-
    -
  1. 有效等价类1:0~100(包含0和100)之间的任意数,比如:19;
  2. -
  3. 无效等价类1:小于0的负数,比如:-1;
  4. -
  5. 无效等价类2:大于100的数,比如:121;
  6. -
  7. 无效等价类3:其他任意非数字字符,比如:a、你、\;
  8. -
  9. 无效等价类4:空字符
  10. -
-

等价类最终必须是分割到最小单位,只有这样才能保障测试覆盖全面。
-非数字字符可以是包含英文字符、中文、特殊符号的字符串或者字符,所以其实它又可以分为三个无效等价类,分别是:

-
    -
  1. 无效等价类:包含英文字符的字符串,比如:a、a123、a=、b你a;
  2. -
  3. 无效等价类:包含中文的字符串,比如:你、你12、1你2、你=;
  4. -
  5. 无效等价类:包含特殊字符的字符串,比如:\ 。
  6. -
-

3.3 边界值分析

-

边界值分析法是等价类划分法的补充。顾名思义,边界值分析法是对输入的边界值进行测试。从实践中我们可以发现,人们无论是在生活中还是在工作中往往会忽略边界值的条件,所以在输入或者输出的边界上会发生大量的错误。因此,在测试用例设计中,需要对输入的条件进行分析并且提取其中的边界值条件,通过对这些边界值的测试来查出更多的错误。

-

常见的边界值:

-
    -
  1. 文本框接受字符个数,比如用户名长度、密码长度等。
  2. -
  3. 报表的第1行和最后1行。
  4. -
  5. 数组元素的第1个和最后1个。
  6. -
  7. 循环的第1次、第2次和倒数第1次、最后1次。
  8. -
-

3.3.1 设计原则

-
    -
  1. 如果输入条件规定了值的范围,则应取刚达到这个范围边界的值,以及刚刚超越这个范围边界的值作为测试输入数据。
  2. -
  3. 如果输入条件规定了值的个数,则用最大个数、最小个数、比最小个数少1、比最大个数多1的数作为测试数据。
  4. -
  5. 如果规格说明书给出的输入域或输出域是有序集合,则应选取集合的第1个元素和最后1个元素作为测试用例。
  6. -
  7. 如果程序中使用了内部数据结构,则应选择内部数据结构边界上的值作为测试用例。
  8. -
  9. 分析规格说明,找出其他可能的边界条件。
  10. -
-

3.3.2 两类方法

-
    -
  1. -

    一般边界值分析 -对于含有n个变量的程序,取值为min、min+、normal,max-、max,测试用例数目为4*N+1。 -一般边界值分析

    -
  2. -
  3. -

    健壮性边界值分析 -健壮性边界值测试是边界值分析的一种扩展。变量除了取min、min+、normal、max-、max 5个边界值外,还要考虑略超过最大值(max+)以及略小于最小值(min-)的取值。因此,对于含有n个变量的程序,健壮性边界值分析产生6*n+1个测试用例。 -健壮性边界值分析

    -
  4. -
-

3.3.3 应用举例

-

延伸上节的例子来说明:学生信息系统中有一个“考试成绩”的输入项,成绩的取值范围是0~100之间的整数,考试成绩及格的分数线是60,优秀的分数线是80。那么这个例子中的边界值数据是哪些呢:

-
-

选取的边界值数据应该包括:

-

-1,0,1,59,60,61,79,80,81,99,100,101

-
-

通常情况下,软件测试所包含的边界检验有以下几种类型:数字、字符、位置、质量、大小、速度、方位、尺寸、空间等,而相应地,这些类型的边界值应该在最大/最小,首位/末尾,上/下,最快/最慢,最高/最低,最短/最长,空/满等情况下。

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
测试项边界值测试用例设计思路
数字起始位数-1
结束位数+1
成绩,正确0-100,边界-1,0,100,101
字符起始-1个字符
结束+1个字符
用户名输入框,正确1-32位,边界0、1、32、33,注意中文字符占位不同
方向刚差一点
刚超一点
游戏,通过门口,边界值门内一步和门外一步
空间小于空余空间一点
大于满空间一点
磁盘剩余20G,边界19.9G和20.1G
位置上下左右里面一点
外面一点
按钮,四边内四点,外四点
-

3.3.4 局限性

-

如果被测程序是多个独立变量的函数,这些变量受物理量的限制,则较适合采用边界值分析。这里的关键是 “独立”的“物理量” 。例如,Date是3个变量(年、月、日)的函数,对其采用边界分析测试用例,就会发现测试用例是不充分的,例如,没强调2月和闰年。其存在问题是因为没有考虑月份、日期和年变量之间存在的依赖关系。由于边界值分析假设变量是完全独立的,因此边界值分析测试用例是对物理量的边界独立导出变量极值,不考虑函数的性质,也不考虑变量的语义含义。 -边界值分析对布尔变量和逻辑变量没有多大意义。例如,布尔变量的极值是true和false,但是其余3个值不明确。

-

3.4 决策表

-

等价类划分法和边界值分析法只是孤立地考虑各个输人数据的测试效果,没有考虑输入数据的组合及其相互制约关系,而决策表考虑了多种条件的组合情况。决策表又称为判定表,分析多种逻辑条件(if-else、switch-case等)与执行动之间的关系。

-

决策表由4部分组成:

-
    -
  1. 条件桩:列出了问题的所有条件,通常认为列出的条件次序无关紧要。
  2. -
  3. 动作桩:列出了问题规定可能采取的操作,这些操作的排列顺序没有约束。
  4. -
  5. 条件项:列出针对条件桩的取值,在所有可能情况下的真假值。
  6. -
  7. 动作项:列出在条件项的各种取值情况下应该采取的动作。
  8. -
-

规则:任何条件组合的特定取值及其相应要执行的操作。在决策表中贯穿条件项和动作项的列就是规则。显然,决策表中列出多少条件取值,也就有多少规则,条件项和动作项就有多少列。

-

决策表组成

-

所有条件都是逻辑结果(即真/假、是/否、0/1)的决策表称为有限条件决策表。如果条件有多个值,则对应的决策表叫做扩展条目决策表。决策表设计测试用例,条件解释为输入,动作解释为输出。

-

决策表适合以下特征的应用程序:

-
    -
  1. if-then-else分支逻辑突出。
  2. -
  3. 输入变量之间存在逻辑关系。
  4. -
  5. 涉及输入变量子集的计算。
  6. -
  7. 输入和输出之间存在因果关系。
  8. -
  9. 很高的圈复杂度。
  10. -
-

3.4.1 应用举例

-

决策表(判定表)设计测试用例的具体步骤如下:

-
    -
  1. 确定规则的个数。假如有n个条件,每个条件有两个取值(0,1),故有2种规则。
  2. -
  3. 列出所有的条件桩和动作桩。
  4. -
  5. 填入条件项。
  6. -
  7. 填入动作项,得到初始判定表。
  8. -
  9. 简化,合并相似规则(相同动作)。 -简化就是合并多条具有相同的动作的规则,并且其条件项之间存在极为相似的关系。 -简化规则
  10. -
-

需求:输入三边值,判定是哪种三角形:非三角形、不等边三角形、等腰三角形、等边三角形

-
    -
  1. 绘制初始三角形判定决策表
  2. -
  3. 优化1的产出
  4. -
  5. 设计测试用例
  6. -
-

条件桩:

-
    -
  • abc能构成三角形 -
      -
    • a+b>c
    • -
    • a+c>b
    • -
    • b+c>a
    • -
    -
  • -
  • a=b?
  • -
  • a=c?
  • -
  • b=c?
  • -
-

动作桩:

-
    -
  • 非三角形
  • -
  • 不等边三角形
  • -
  • 等腰三角形
  • -
  • 等边三角形
  • -
-

决策表:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
12345678
a+b>c?NYYYYYYY
a+c>b?NYYYYYY
b+c>a?NYYYYY
a=b?YYNNN
a=c?YNYNN
b=c?YN
非三角形
不等边三角形
等腰三角形
等边三角形
-

测试用例:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
用例IDabc预期输出
TC1124非三角形
TC2142非三角形
TC3421非三角形
TC4333等边三角形
TC5334等腰三角形
TC6343等腰三角形
TC7433等腰三角形
TC8345不等边三角形
-

3.4.2 优点和缺点

-

决策表把复杂问题的各种可能情况一一列出,易于理解。但是,决策表不能表达重复执行动作的缺点。

-

使用判定表设计测试用例的条件如下:

-
    -
  1. 规格说明以判定表形式给出,或很容易转换成判定表。
  2. -
  3. 条件的排列顺序不会也不影响执行哪些操作。
  4. -
  5. 规则的排列顺序不会也不影响执行哪些操作。
  6. -
  7. 每当某一规则的条件已经满足,并确定要执行的操作后,不必检验别的规则。
  8. -
  9. 如果某一规则得到满足要执行多个操作,这些操作的执行顺序无关紧要。
  10. -
-

这5个必要条件使得操作的执行完全依赖于条件的组合。对于不满足条件的判定表,可增加其他的测试用例。

-

3.5 因果图

-

前面我们介绍的等价类划分法和边界值分析法都没有考虑到输入情况的组合。这样虽然各种输入条件可能出错的情况已经看到了,但是多个输入情况组合起来可能出错的情况却被忽视了

-
-

地铁自动充值机充值

-

假设自动充值机每次只能投入面值50或者面值100的人民币,投入钱后会有充值50和充值100两个选项

-
-

等价类划分法和边界值分析法可能不会测试到投入面值50的人民币,然后点击充值100这种异常情况;因此,当程序的输入条件有多个的话,就需要用到因果图法来设计测试用例了。

-

因果图利用图解法分析输入的各种组合情况,适合描述多种输入条件的组合、相应产生多不动作的方法。因果图法最终生成的是判定表。

-

3.5.1 基本术语

-
    -
  1. 原因结果图: -原因——结果图使用了简单的逻辑符号,以直线连接左右结点,左结点表示输入状态(原因),右结点表示输出状态(结果)。
  2. -
-

原因 - 结果图

-
    -
  • “恒等”:若原因出现,则结果出现;若原因不出现,则结果不出现。
  • -
  • “非”:若原因出现,则结果不出现;若原因不出现,则结果出现。
  • -
  • “或”:若几个原因中有一个出现,则结果出现;若几个原因都不出现,则结果不出现。
  • -
  • “与”:若几个原因都出现,结果才出现;若其中有一个原因不出现,则结果不出现。
  • -
-
    -
  1. 约束图: -输入输出状态相互之间存在的某些依赖关系,称为约束。
  2. -
-

约束图

-
    -
  • E(互斥):原因不会同时成立,最多1个成立,可以都不成立
  • -
  • I(包含):原因中至少一个成立,不能同时为0
  • -
  • O(唯一):原因中有且只有一个成立
  • -
  • R(要求):原因中a出现,b必须出现,a=1则b=1,a=0的话,b随便。QQ登录的例子a为自动登录,b是记住密码
  • -
  • M(屏蔽):a为1时,b必须是0,a=1,则b=0,如果a=0,b随便
  • -
-

3.5.2 设计因果图测试用例步骤

-
    -
  1. 分析软件规格说明,哪些是原因(即输入条件或输入条件的等价类),哪些是结果(即输出条件),给每个原因和结果赋予标识符。
  2. -
  3. 分析原因与结果之间、原因与原因之间对应的逻辑关系,用因果图表示。
  4. -
  5. 由于语法或环境限制,有些原因与原因之间、原因与结果之间的组合情况不可能出现,在因果图上用一些记号表明这些特殊情况的约束或限制条件,把因果图转换为判定表。
  6. -
  7. 从判定表的每一列产生出测试用例。
  8. -
-

对于逻辑结构复杂软件,先用因果图进行图形分析,再用判定表进行统计,最后设计测试用例。当然,对于比较简单的测试对象,可以忽略因果图,直接使用决策表。

-

3.5.3 应用举例

-

需求:第一列字符必须是A或者B,第二列为数字,才允许进行文件修改。如果第一列字符不正确,输出提示L,第二列不是数字,输出提示M,采用因果图设计测试用例

-

原因:

-
    -
  1. 第一列是A
  2. -
  3. 第一列是B
  4. -
  5. 第二列是数字
  6. -
-

结果:

-
    -
  1. 修改文件
  2. -
  3. 输出提示L
  4. -
  5. 输出提示M
  6. -
-

因果图: -因果图

-

决策表:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
123456
A110000
B001100
数字101010
修改文件101000
提示L000011
提示M010101
-

测试用例:

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
用例ID第一列第二列预期输出
TC1A1修改文件
TC2AC、汉、#提示M
TC3B2修改文件
TC4BD、字、!提示M
TC5E、符、%3提示L
TC6F、特、@G、殊、*提示L和M
-

3.5.4 优点和缺点

-

优点:

-
    -
  1. 考虑多个输入之间的相互组合、相互制约的关系
  2. -
  3. 指出需求规格说明书中存在的不完整性和二义性
  4. -
  5. 帮助测试人员按照一定的步骤高效的开发测试用例
  6. -
-

缺点:

-
    -
  1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到
  2. -
  3. 此方法得到的用例数量规模大
  4. -
-

3.6 场景法

-

通过尝尽该描述的业务流程(业务逻辑),设计用例来遍历场景(路径),验证系统功能的正确性。 -场景法重点是测试流程,因此每个流程用一个用例验证即可,流程测试没问题不代表系统功能没问题,还需要单步进行测试,结合前面的方法。

-

流程图:

-
    -
  • 矩形:步骤
  • -
  • 菱形:判断条件
  • -
  • 箭头:流向
  • -
-

3.6.1 ATM取款流程图

-

ATM取款流程图

-

3.6.2 ATM取款场景设计

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
场景编号流程结果
1插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额充足
ATM现金充足
成功提款
2插入不合法的卡提示错误,退卡
3插入合法的卡
输入密码点取消
退卡
4插入合法的卡
输入错误的密码(还有机会)
提示错误,重新输入
5插入合法的卡
输入错误的密码(超出限制次数)
提示错误,退卡/吞卡
6插入合法的卡
输入正确的密码
ATM没有现金
提款选项不可用,退出
7插入合法的卡
输入正确的密码
ATM有现金
输入不合法的金额
提示错误,重新输入
8插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额不足
提示错误,重新输入
9插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额充足
ATM现金不足
提示错误,重新输入
-

3.6.3 测试用例

- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
用例ID场景/条件卡片密码ATM内金额账户余额输入金额预期结果
TC1场景1:成功提款合法卡1234562000.005000.00100成功提款,账户余额400.00
TC2场景2:非法的卡非法卡n/a2000.005000.00n/a提示错误,退卡
TC3场景3:点取消合法卡n/a2000.005000.00n/a退卡
TC4场景4:密码错误(还有机会)合法卡6543212000.005000.00n/a提示错误,重新输入
TC5场景5:密码错误(超过限制次数)合法卡2345162000.005000.00n/a提示错误,退卡/吞卡
TC6场景6:ATM无现金合法卡1234560.005000.00n/a提款选项不可用,用例结束
TC7场景7:金额错误合法卡1234562000.005000.0020提示错误,重新输入
TC8场景8:卡内余额不足合法卡1234562000.005000.00600提示错误,重新输入
TC9场景9:ATM现金不足合法卡1234562000.005000.002500提示错误,重新输入
-

3.7 错误推测法

-

3.7.1 概念

-

错误推测法是利用经验和直觉推测出出错的可能类型,列举出程序中所有可能的错误和容易发生错误情况的清单,根据清单设计测试用例。所谓凭经验,是指人们对过去所作测试结果的分析,对所揭示缺陷的规律性直觉的推测来发现缺陷。

-

该方法强调的是对被测试软件的需求理解以及设计实现的细节把握,当然还有个人的能力。那么显而易见地,这个方法的缺点就是太过依赖个人能力,难以系统化。因此,这个方法一般是作为测试用例设计的补充,而不是单独用来设计测试用例。在回归测试中应用较多。

-

错误推测法一般采用如下技术:

-
    -
  1. 有关软件设计方法和实现技术。
  2. -
  3. 有关前期测试阶段结果的知识。
  4. -
  5. 测试类似或相关系统的经验,了解以前这些系统曾在哪些地方出现缺陷。
  6. -
  7. 典型的产生错误的知识,如被零除错误。
  8. -
-

3.7.2 优点和缺点

-

优点:

-
    -
  1. 不用设计等价类的测试用例,将多个等价类的测试合成一个随机测试,可以以较少代码实现测试代码的编写。
  2. -
  3. 当等价类设计不确切或不完全时,测试会产生遗漏,而使用错误推测法则是按照概率进行等价类覆盖。不论存在多少个等价类,只要随机数据个数足够,就能保证各个等价类被覆盖的概率足够高,能够有效弥补等价类分法设计不充分的缺陷。
  4. -
  5. 采用错误推测法进行测试,每次执行测试时,测试的样本数据可能都不相同,执行次数愈多,错误暴露的概率愈大。
  6. -
-

缺点:

-
    -
  1. 错误推测法中的随机数据很难覆盖到边界值,无法保证测试的充分性。
  2. -
  3. 错误推测法进行自动化测试的难度较大。有些程序很难用程序来自动验证,这使得程序结果的验证工作难度变大。
  4. -
  5. 当等价类的范围较小,这些范围较小的等价类被覆盖的概率也是很小的,错误推测法难以测试到。
  6. -
  7. 随机测试不可以代替常规的功能或非功能测试,因为其随意性大,没有一套完整严格的方法且并非有章可循的测试技术。
  8. -
-

3.7.3 常见错误

-
    -
  1. 页面规范相关部分(跟公司甚至项目需求有关系)
  2. -
-
    -
  • 命名、注释、字体、颜色、缩进等
  • -
  • 文本框长度/范围限制
  • -
  • 支持的浏览器、操作系统、jdk等做兼容性测试
  • -
-
    -
  1. 常识性问题
  2. -
-
    -
  • 密码用密文
  • -
  • 手机号码是11位,且是特定三位数开头
  • -
  • 文本框自动忽略前后空格
  • -
  • 支持模糊查询
  • -
-
    -
  1. 常见的异常测试情况
  2. -
-
    -
  • 输入框不输入任何内容(为空)或者输入空格的情况
  • -
  • 输入框输入非法字符
  • -
  • 用户注销后,是否仍然能操作;再登录是否能成功
  • -
  • 断电重连后是否能继续使用且信息未丢失
  • -
-
    -
  1. 功能相关的常见异常问题
  2. -
-
    -
  • C++软件的内存泄漏、内存分配
  • -
  • web程序的session失效问题
  • -
  • JavaScript字符转义
  • -
-

3.8 综合策略

-

黑盒测试方法有等价类划分、边界值分析、决策表、因果图、场景法、错误推测法等,每种测试方法都有其各自的特点和适用场合。
-软件测试专家Myers给出了黑盒测试方法中各种测试方法的使用策略:

-
    -
  1. 在任何情况下都必须使用边界值分析方法。经验表明,用这种方法设计的测试用例发现程序错误的能力最强。
  2. -
  3. 必要时使用等价类划分方法补充一些测试用例。
  4. -
  5. 用错误推测法再追加一些测试用例。
  6. -
  7. 对照程序逻辑,检查已设计出的测试用例的逻辑覆盖程度,如果没有达到要求的覆盖标准,应当再补充足够的测试用例。
  8. -
  9. 如果程序的功能说明中含有输入条件的组合情况,则一开始就可选用因果图法。
  10. -
-

对于功能性测试技术,可以根据如下条件进行选择:

-
    -
  1. 如果变量是独立的,则可以用定义域测试和等价类测试。
  2. -
  3. 如果变量不是独立的,可采用决策表测试。
  4. -
  5. 如果为单缺陷假设,则可采用边界值分析和健壮性测试。
  6. -
  7. 如果为多缺陷假设,可采用最坏情况测试、健壮最坏情况测试和决策表测试。
  8. -
  9. 如果程序包含大量例外处理,可采用健壮性测试和决策表测试。
  10. -
  11. 如果变量引用的是逻辑量,可采用等价类测试用例和决策表测试。
  12. -
-

第4章 白盒测试

-

4.1 概述

-

4.2 静态测试

-

4.3 逻辑覆盖

-

4.4 路径分析

-

4.5 控制结构测试

-

4.6 数据流测试

-

4.7 程序插桩

-

4.8 测试方法综述

-

4.9 知识点总结

-

第5章 性能测试

-

5.1 基本概念

-

5.2 性能测试分类

-

5.2.1 负载测试

-

5.2.2 压力测试

-

5.2.3 可靠性测试

-

5.2.4 数据库测试

-

5.2.5 安全性测试

-

5.2.6 兼容性测试

-

5.2.7 可用性测试

-

5.3 性能测试步骤

-

5.4 Web测试

-

5.5知识点总结

-

第6章 软件测试流程

-

6.1 软件测试流程概述

-

6.2 测试需求

-

6.3 测试计划

-

6.4 测试设计

-

6.5 测试执行

-

6.5.1 单元测试

-

6.5.2 集成测试

-

6.5.3 系统测试

-

6.5.4 验收测试

-

6.5.5 α测试

-

6.5.6 β测试

-

6.6 回归测试

-

6.7 测试评估

-

6.8 知识点总结

-

第7章 软件测试自动化

-

7.1 自动化测试和手工测试

-

7.2 测试成熟度模型

-

7.3 自动化测试体系

-

7.4 测试工具介绍

-

7.5 知识点总结

-

第8章 软件测试管理

-

8.1 软件测试管理概述

-

8.2 测试过程改进

-

8.3 人力资源

-

8.4 知识点总结

- - - -- Gitee From 93c6bcc6a6fdaea1b79c1cad6818de9d2e3ffe47 Mon Sep 17 00:00:00 2001 From: Future100 Date: Wed, 15 Sep 2021 00:14:23 +0800 Subject: [PATCH 10/30] =?UTF-8?q?19990124=E9=AD=8F=E6=9D=A5=E4=BF=AE?= =?UTF-8?q?=E6=94=B9README.md?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 149 ++++++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 112 insertions(+), 37 deletions(-) diff --git a/README.md b/README.md index dbaae73..7e1c2f1 100644 --- a/README.md +++ b/README.md @@ -1,10 +1,14 @@ + + # 软件测试 + ## 写在最前面 ### 1 课程目标 * 掌握基础的软件测试理论、测试方法和策略 * 掌握常用工具使用 * 根据需求和设计文档独立编写测试计划、测试方案、测试用例以及测试报告 ### 2 主要内容 +* 软件测试概论 * 软件测试基础知识 * 软件测试通用技术 * 软件测试流程 @@ -68,7 +72,7 @@ * 《软件支持手册》 #### 1.1.3 软件发展史 -1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序) +1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 ≠ 程序) 2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 4. 多层分布结构,面向服务架构 @@ -85,26 +89,41 @@ ### 1.2 软件生命周期 #### 1.2.1 需求定义 **描述:** 定义出本次任务都需要做什么,做成什么样子。 + **参与者:** 产品经理、需求分析师、客户 + #### 1.2.2 可行性分析 **描述:** 由项目组相关成员去研究需求是否可行,能不能做出来。 + **参与者:** 产品经理、架构师、项目经理、开发 + #### 1.2.3 需求分析 **描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个输入框、每个按钮的样式,输入输出等各项值。 + **参与者:** 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发 + **输出:**《需求规格说明书》 + #### 1.2.4 评审 **描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。 + **参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等 + #### 1.2.5 设计 **描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此基础上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。 + **参与者:** 项目经理、架构师、开发、测试 + #### 1.2.6 编码 **描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。 + **参与者:** 开发 + #### 1.2.7 提测 **描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。 + **参与者:** 任务责任人(开发)、测试 + #### 1.2.8 测试 - 测试需求 - 测试计划 @@ -113,10 +132,15 @@ - 回归测试 - 测试评估 #### 1.2.9 部署/发版 + **描述:** 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 + **参与人:** 配置管理人员、测试 -10. 支持维护 + +#### 1.2.10 支持维护 + **描述:** 支持维护类似于我们日常中的售后,主要是对已卖出的产品/已上线的项目进行日常维护。包括纠错性维护和改进性维护两个方面。 + **参与人:** 支持维护人员/售后工程师 ### 1.3 软件测试概述 @@ -126,11 +150,16 @@ IEEE:使用人工或自动手段来运行或测定某个软件系统的过程, #### 1.3.2 测试发展历程 1. 1957年之前-调试为主(Debugging Oriented) -软件规模小,复杂度低,开发人员承担需求分析、设计、开发、测试等所有工作,等同于调试。 + + 软件规模小,复杂度低,开发人员承担需求分析、设计、开发、测试等所有工作,等同于调试。 + 2. 1957–1978-证明为主(Demonstration Oriented) -与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。 + + 与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。 + 3. 1979–1982-破坏为主(Destruction Oriented) -1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义: + + 1979年,《软件测试的艺术》 (The Art of Software Testing)第一版问世,这本书是测试界的经典之作。书中给出了软件测试的经典定义: ``` The process of executing a program with the intent of finding errors. @@ -140,51 +169,74 @@ The process of executing a program with the intent of finding errors. 这个观点较之前证明为主的思路,是一个很大的进步。我们不仅要证明软件做了该做的事情,也要保证它没做不该做的事情,这会使测试更加全面,更容易发现问题。 4. 1983–1987-评估为主(Evaluation Oriented) -软件行业进入了大发展时期,软件趋向大型化、复杂化,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 + + 软件行业进入了大发展时期,软件趋向大型化、复杂化,质量越来越重要。软件测试的基础理论和实用技术开始形成。提出了在软件生命周期中使用分析、评审、测试来评估产品的理论。 + 5. 1988–至今-预防为主(Prevention Oriented) -尽量早的介入并发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 + + 尽量早的介入并发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 #### 1.3.3 测试与开发的关系 **瀑布模型** + ![瀑布模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/pb-model.png) 这是一种经典模型,提供了软件开发的基本框架。 + 强调开发工作(计划、设计、开发、测试、维护等)各阶段之间的先后顺序,不可以并行操作。 -瀑布模型认为,测试是指代码完成后,处于运行维护阶段之前。如果需求和设计上存在缺陷,就会造成大量返工,增加成本。为了更早的发现问题,测试应延伸到需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。 + +瀑布模型认为,测试是指代码完成后,处于运行维护阶段之前。如果需求和设计上存在缺陷,就会造成大量返工,增加成本。 + +为了更早的发现问题,测试应延伸需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。 + **优点:** + 1. 各阶段划分清晰 2. 强调计划与需求分析 3. 适合需求稳定的产品开发 **缺点:** + 1. 单一流程,不可逆 2. 风险显露得晚,纠正机会少 3. 测试只是其中一个阶段,缺乏全过程测试思想 **V模型** + ![V模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/v-model.png) 强调将测试和开发同等重要,对于开发阶段都有与之对应的测试阶段。 + **优点:** + 相对于瀑布模型,V模型测试能够尽早的进入到开发阶段。 + **缺点:** + 虽然测试尽早的进入到开发阶段,但是真正进行软件测试是在编码之后,这样忽视了测试对需求分析、系统设计的验证,时间效率上也大打折扣。 **W模型(双V模型)** + ![W模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/w-model.png) 明确表示出了测试与开发的并行关系 + **优点:** + W 模型相对于 V 模型来说,测试更早的进入到开发阶段,与开发阶段是并行关系,更早的发现问题,能够及时解决问题,各个阶段分工明确,方便管理。 + **缺点:** + W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方便。 **螺旋模型** + ![螺旋模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/lx-model.png) 大型软件项目通常有很多不确定性和风险,如果采用瀑布式线性过程模型,失败风险很大,因此需要采取一种渐进式的演化过程模型。将产品分解成增量版本,每个版本单独测试。 **敏捷模型** + ![敏捷模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/mj-model.png) 敏捷开发以用户的需求进化为核心,采用迭代、循序渐进的方法进行软件开发。专注于交付对客户有价值的软件(可以工作的)。 @@ -210,19 +262,25 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 **解读:** * 个体和互动高于流程和工具 -以人为本,没有比面对面交流更高效的沟通渠道了,基于互相信任的前提,敏捷提倡自治的全功能团队。 -在工作形式上,整个团队平时坐在一起工作,从物理空间上创造了更加便捷面对面的沟通机会。在团队职责上,团队内部具备完成软件交付的角色(能力),团队所有人对软件的质量负责,开发过程由团队内部把控,业务价值团队内部快速流动,在任何环节都能及时获得反馈。同时,每个角色都更容易从全局视角去思考软件,避免了传统部门墙模式下的视角割裂和协作障碍。 + + 以人为本,没有比面对面交流更高效的沟通渠道了,基于互相信任的前提,敏捷提倡自治的全功能团队。 + + 在工作形式上,整个团队平时坐在一起工作,从物理空间上创造了更加便捷面对面的沟通机会。在团队职责上,团队内部具备完成软件交付的角色(能力),团队所有人对软件的质量负责,开发过程由团队内部把控,业务价值团队内部快速流动,在任何环节都能及时获得反馈。同时,每个角色都更容易从全局视角去思考软件,避免了传统部门墙模式下的视角割裂和协作障碍。 * 工作的软件高于详尽的文档 -为客户交付可工作的软件是我们的核心目标,我们应该尽早交付可进行端到端测试的代码,该目标决定了我们不应该花过多精力在面面俱到的文档上,但这不代表我们要抵制任何文档。实践证明,轻量级的文档策略有助于团队高质量交付可工作的软件。 + + 为客户交付可工作的软件是我们的核心目标,我们应该尽早交付可进行端到端测试的代码,该目标决定了我们不应该花过多精力在面面俱到的文档上,但这不代表我们要抵制任何文档。实践证明,轻量级的文档策略有助于团队高质量交付可工作的软件。 * 客户合作高于合同谈判 -主动拥抱变化,及时响应,持续交付。 + + 主动拥抱变化,及时响应,持续交付。 * 响应变化高于遵循计划 -通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费 + + 通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费 **缺点:** + 由于其项目周期很长,所以很难保证开发的人员不更换,而缺少文档就会造成在交接的过程中出现很大的困难。 ![敏捷开发流程](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/mj-process.png) @@ -264,6 +322,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 #### 1.4.5 缺陷级别 **严重性:** 表示软件缺陷的恶劣程度,当用户碰到该缺陷时影响的可能性和程度。 + **优先级:** 表示修复缺陷的重要程度和紧迫程度。 ##### 严重性 @@ -273,7 +332,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | S2 | 严重缺陷 | 系统出现重大问题,影响提供的主要功能使用 | 内存泄露
数据无法保存 | | S3 | 主要错误 | 主要功能实现有问题,易用性不够好 | 某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码 | | S4 | 次要错误 | 次要功能实现有问题或者手册相关问题 | 个别不常用的属性不生效或实现有问题(前提:不影响主要功能使用)
次要功能实现与需求不符或实现有问题(如:日志不能轮转、预警策略不生效、搜索框不能用、快照生成格式有问题等)
错别字
手册描述不合理或样式格式有问题 | -| S5 | 轻微缺陷 | 建议,不属于缺陷 | +| S5 | 轻微缺陷 | 建议,不属于缺陷 || ##### 优先级 @@ -327,7 +386,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。 7. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。 -以上是上报bug、创建bug必须的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: +以上是上报bug、创建bug必须要做的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: 1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 2. bug修订人:bug修订人员。 @@ -337,9 +396,9 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 6. bug备注:备注,以便记录一些额外信息。 #### 1.4.8 缺陷预防 -差错:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) -错误:软件内部问题,设计错误、编码错误。(内部原因) -失效:软件系统运行时偏离了用户需求。(外部表现) +**差错**:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) +**错误**:软件内部问题,设计错误、编码错误。(内部原因) +**失效**:软件系统运行时偏离了用户需求。(外部表现) ### 1.5 软件测试行业 #### 1.5.1 行业现状 @@ -399,7 +458,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 6. 发散思维方式 ### 1.6 测试认识的误区 -1. 使用了测试工具,就进行了有效的测试 +1. 使用了测试工具,就是进行了有效的测试 2. 存在太多无法测试的东西 3. 软件开发完成后才进行测试 4. 软件发布后发现质量问题,是测试人员的问题 @@ -420,15 +479,24 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 ## 第2章 软件测试基础知识 ### 2.1 概述 1. 从软件测试的目的来理解 -软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。 + + 软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。 + 2. 从软件测试的性质来理解 -在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的”。 + + 在软件开发过程中,分析、设计和编码都是“建设性的”,唯有测试是“破坏性的”。 + 3. 从软件开发角度来理解 -软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障。 + + 软件测试以检查产品的内容和功能特性为核心,是软件质量保证的关键步骤,也是成功实现软件开发目标的重要保障。 + 4. 从软件工程角度来理解 -软件测试是软件工程的一部分,是软件工程过程中的重要阶段。 + + 软件测试是软件工程的一部分,是软件工程过程中的重要阶段。 + 5. 从软件质量保证角度来理解 -软件测试是软件质量保证的重要措施。 + + 软件测试是软件质量保证的重要措施。 ### 2.2 测试的目的和原则 #### 2.2.1 测试的目的 @@ -619,7 +687,9 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 5. 无效等价类4:空字符 **等价类最终必须是分割到最小单位,只有这样才能保障测试覆盖全面。** + 非数字字符可以是包含英文字符、中文、特殊符号的字符串或者字符,所以其实它又可以分为三个无效等价类,分别是: + 1. 无效等价类:包含英文字符的字符串,比如:a、a123、a=、b你a; 2. 无效等价类:包含中文的字符串,比如:你、你12、1你2、你=; 3. 无效等价类:包含特殊字符的字符串,比如:\ 。 @@ -666,7 +736,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | 位置 | 上下左右里面一点
外面一点 | 按钮,四边内四点,外四点 | #### 3.3.4 局限性 - 如果被测程序是多个独立变量的函数,这些变量受物理量的限制,则较适合采用边界值分析。这里的关键是 **“独立”的“物理量”** 。例如,Date是3个变量(年、月、日)的函数,对其采用边界分析测试用例,就会发现测试用例是不充分的,例如,没强调2月和闰年。其存在问题是因为没有考虑月份、日期和年变量之间存在的依赖关系。由于边界值分析假设变量是完全独立的,因此边界值分析测试用例是对物理量的边界独立导出变量极值,不考虑函数的性质,也不考虑变量的语义含义。 +如果被测程序是多个独立变量的函数,这些变量受物理量的限制,则较适合采用边界值分析。这里的关键是 **“独立”的“物理量”** 。例如,Date是3个变量(年、月、日)的函数,对其采用边界分析测试用例,就会发现测试用例是不充分的,例如,没强调2月和闰年。其存在问题是因为没有考虑月份、日期和年变量之间存在的依赖关系。由于边界值分析假设变量是完全独立的,因此边界值分析测试用例是对物理量的边界独立导出变量极值,不考虑函数的性质,也不考虑变量的语义含义。 边界值分析对布尔变量和逻辑变量没有多大意义。例如,布尔变量的极值是true和false,但是其余3个值不明确。 ### 3.4 决策表 @@ -835,7 +905,9 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | TC5 | E、符、% | 3 | 提示L | | TC6 | F、特、@ | G、殊、* | 提示L和M | #### 3.5.4 优点和缺点 -优点: + +优点: + 1. 考虑多个输入之间的相互组合、相互制约的关系 2. 指出需求规格说明书中存在的不完整性和二义性 3. 帮助测试人员按照一定的步骤高效的开发测试用例 @@ -867,20 +939,23 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | 7 | 插入合法的卡
输入正确的密码
ATM有现金
输入不合法的金额 | 提示错误,重新输入 | | 8 | 插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额不足 | 提示错误,重新输入 | | 9 | 插入合法的卡
输入正确的密码
ATM有现金
输入正确的金额
余额充足
ATM现金不足 | 提示错误,重新输入 | + #### 3.6.3 测试用例 -| 用例ID | 场景/条件 | 卡片 | 密码 | ATM内金额 | 账户余额 | 输入金额 | 预期结果 | -| :----: | ------------------------------- | ------ | ------ | --------: | -------: | -------: | ------------------------ | -| TC1 | 场景1:成功提款 | 合法卡 | 123456 | 2000.00 | 5000.00 | 100 | 成功提款,账户余额400.00 | -| TC2 | 场景2:非法的卡 | 非法卡 | n/a | 2000.00 | 5000.00 | n/a | 提示错误,退卡 | -| TC3 | 场景3:点取消 | 合法卡 | n/a | 2000.00 | 5000.00 | n/a | 退卡 | -| TC4 | 场景4:密码错误(还有机会) | 合法卡 | 654321 | 2000.00 | 5000.00 | n/a | 提示错误,重新输入 | -| TC5 | 场景5:密码错误(超过限制次数) | 合法卡 | 234516 | 2000.00 | 5000.00 | n/a | 提示错误,退卡/吞卡 | -| TC6 | 场景6:ATM无现金 | 合法卡 | 123456 | 0.00 | 5000.00 | n/a | 提款选项不可用,用例结束 | -| TC7 | 场景7:金额错误 | 合法卡 | 123456 | 2000.00 | 5000.00 | 20 | 提示错误,重新输入 | -| TC8 | 场景8:卡内余额不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 600 | 提示错误,重新输入 | -| TC9 | 场景9:ATM现金不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 2500 | 提示错误,重新输入 | + +| 用例ID | 场景/条件 | 卡片 | +| :----: | ------------------------------- | ------ | +| TC1 | 场景1:成功提款 | 合法卡 | +| TC2 | 场景2:非法的卡 | 非法卡 | +| TC3 | 场景3:点取消 | 合法卡 | +| TC4 | 场景4:密码错误(还有机会) | 合法卡 | +| TC5 | 场景5:密码错误(超过限制次数) | 合法卡 | +| TC6 | 场景6:ATM无现金 | 合法卡 | +| TC7 | 场景7:金额错误 | 合法卡 | +| TC8 | 场景8:卡内余额不足 | 合法卡 | +| TC9 | 场景9:ATM现金不足 | 合法卡 | ### 3.7 错误推测法 + #### 3.7.1 概念 错误推测法是利用经验和直觉推测出出错的可能类型,列举出程序中所有可能的错误和容易发生错误情况的清单,根据清单设计测试用例。所谓凭经验,是指人们对过去所作测试结果的分析,对所揭示缺陷的规律性直觉的推测来发现缺陷。 -- Gitee From 635bfdd9a6ab60535b2c08a04f898368dd39fe0a Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:15:38 +0800 Subject: [PATCH 11/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5merge=E9=AD=8F=E6=9D=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 38 +++++++++++++++++++------------------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/README.md b/README.md index 7e1c2f1..35f64ef 100644 --- a/README.md +++ b/README.md @@ -72,7 +72,7 @@ * 《软件支持手册》 #### 1.1.3 软件发展史 -1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 ≠ 程序) +1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序) 2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 4. 多层分布结构,面向服务架构 @@ -317,7 +317,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 | 用户界面 | 未按照原型设计,影响交互,如:显示格式,按钮位置 | | 文档 | 文档内容不完整或不正确,影响发布和维护 | | 软件包 | 由于软件配置库、变更管理或版本控制引发的错误 | - | 性能 | 执行时间长、处理速度慢、负载高等方面 | + | 性能 | 执行时间长、处理速度慢、负载高等方面 | | 接口 | 与其他模块参数不匹配 | #### 1.4.5 缺陷级别 @@ -326,13 +326,13 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 **优先级:** 表示修复缺陷的重要程度和紧迫程度。 ##### 严重性 -| 级别 | 名称 | 说明 | 示例 | -| :---: | :------: | :----------------------------------------: | ---- | -| S1 | 致命错误 | 严重阻碍开发或测试工作的进行,必须马上解决 | 安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件 | -| S2 | 严重缺陷 | 系统出现重大问题,影响提供的主要功能使用 | 内存泄露
数据无法保存 | -| S3 | 主要错误 | 主要功能实现有问题,易用性不够好 | 某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码 | +| 级别 | 名称 | 说明 | 示例 | +| :---: | :------: | :----------------------------------------: | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | +| S1 | 致命错误 | 严重阻碍开发或测试工作的进行,必须马上解决 | 安装包或App无法安装
网页不能访问
不能启动
死机
核心功能无法使用,比如QQ不能收发消息,邮箱不能收发邮件 | +| S2 | 严重缺陷 | 系统出现重大问题,影响提供的主要功能使用 | 内存泄露
数据无法保存 | +| S3 | 主要错误 | 主要功能实现有问题,易用性不够好 | 某个非核心功能全部或者部分未实现、实现后流程走不通、实现的功能与需求不同、文本框未校验或者校验不全、提示不全(异常提示不合理或者没提示)、手册相关内容缺失、兼容问题、安装界面乱码 | | S4 | 次要错误 | 次要功能实现有问题或者手册相关问题 | 个别不常用的属性不生效或实现有问题(前提:不影响主要功能使用)
次要功能实现与需求不符或实现有问题(如:日志不能轮转、预警策略不生效、搜索框不能用、快照生成格式有问题等)
错别字
手册描述不合理或样式格式有问题 | -| S5 | 轻微缺陷 | 建议,不属于缺陷 || +| S5 | 轻微缺陷 | 建议,不属于缺陷 | | ##### 优先级 @@ -942,17 +942,17 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 #### 3.6.3 测试用例 -| 用例ID | 场景/条件 | 卡片 | -| :----: | ------------------------------- | ------ | -| TC1 | 场景1:成功提款 | 合法卡 | -| TC2 | 场景2:非法的卡 | 非法卡 | -| TC3 | 场景3:点取消 | 合法卡 | -| TC4 | 场景4:密码错误(还有机会) | 合法卡 | -| TC5 | 场景5:密码错误(超过限制次数) | 合法卡 | -| TC6 | 场景6:ATM无现金 | 合法卡 | -| TC7 | 场景7:金额错误 | 合法卡 | -| TC8 | 场景8:卡内余额不足 | 合法卡 | -| TC9 | 场景9:ATM现金不足 | 合法卡 | +| 用例ID | 场景/条件 | 卡片 | 密码 | ATM内金额 | 账户余额 | 输入金额 | 预期结果 | +| :----: | ------------------------------- | ------ | ------ | --------: | -------: | -------: | ------------------------ | +| TC1 | 场景1:成功提款 | 合法卡 | 123456 | 2000.00 | 5000.00 | 100 | 成功提款,账户余额400.00 | +| TC2 | 场景2:非法的卡 | 非法卡 | n/a | 2000.00 | 5000.00 | n/a | 提示错误,退卡 | +| TC3 | 场景3:点取消 | 合法卡 | n/a | 2000.00 | 5000.00 | n/a | 退卡 | +| TC4 | 场景4:密码错误(还有机会) | 合法卡 | 654321 | 2000.00 | 5000.00 | n/a | 提示错误,重新输入 | +| TC5 | 场景5:密码错误(超过限制次数) | 合法卡 | 234516 | 2000.00 | 5000.00 | n/a | 提示错误,退卡/吞卡 | +| TC6 | 场景6:ATM无现金 | 合法卡 | 123456 | 0.00 | 5000.00 | n/a | 提款选项不可用,用例结束 | +| TC7 | 场景7:金额错误 | 合法卡 | 123456 | 2000.00 | 5000.00 | 20 | 提示错误,重新输入 | +| TC8 | 场景8:卡内余额不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 600 | 提示错误,重新输入 | +| TC9 | 场景9:ATM现金不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 2500 | 提示错误,重新输入 | ### 3.7 错误推测法 -- Gitee From 618f3fa7c9a9e6c2e3f5f27b461bddeade36df6d Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:23:17 +0800 Subject: [PATCH 12/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E5=8D=93=E5=AD=90=E6=B4=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 35f64ef..154f986 100644 --- a/README.md +++ b/README.md @@ -577,11 +577,11 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 **术语** 1. 测试编号:测试用例的编号 2. 测试项:测试的功能点说明 -3. 前置条件:该测试用例的前提条件,比如测试wangdachui/dachui12345(用户名/密码)账户是否能正确登录进去,那前提wangdachui/dachui12345已定是注册过的 +3. 前置条件:该测试用例的前提条件,比如测试wangdachui/dachui12345(用户名/密码)账户是否能正确登录进去,那前提wangdachui/dachui12345一定是注册过的 4. 测试步骤:就是测试的所有操作步骤,最好是每一个步骤应该对应一个期望结果,最少也得一个测试用例对应一个期望结果 5. 期望结果:就是希望得到的结果(正确的结果) 6. 测试结果:实际测试的结果,可选项有:通过、不通过、暂时挂起/锁定(就是暂时不测试); -7. 对应的bug:当期望结果与实际结果不符时测试不通过,此时需要上报bug(纪录缺陷),bug需要与测试用例对应 +7. 对应的bug:当期望结果与实际结果不符时测试不通过,此时需要上报bug(记录缺陷),bug需要与测试用例对应 8. 测试执行人:实际由谁来执行测试用例;也有任务分配人的选项,就是测试用例分配给哪个测试员来测试 9. 备注:做一些备注或者测试的说明 10. 合法用户:就是已经注册过的用户 -- Gitee From e4e3b0a6d8be8f9b631820b7609044347226c49e Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:30:33 +0800 Subject: [PATCH 13/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E7=8E=8B=E6=99=93=E6=B0=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index 154f986..cc26bc3 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ ## 写在最前面 ### 1 课程目标 * 掌握基础的软件测试理论、测试方法和策略 -* 掌握常用工具使用 +* 掌握常用工具的使用方法 * 根据需求和设计文档独立编写测试计划、测试方案、测试用例以及测试报告 ### 2 主要内容 * 软件测试概论 @@ -75,7 +75,7 @@ 1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序) 2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 -4. 多层分布结构,面向服务架构 +4. 多层分布结构,面向服务架构。 #### 1.1.4 软件项目 软件项目是一种特殊的项目,具有如下特点: @@ -174,7 +174,7 @@ The process of executing a program with the intent of finding errors. 5. 1988–至今-预防为主(Prevention Oriented) - 尽量早的介入并发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 + 尽量早地介入并发现这些明显的或隐藏的bug,发现得越早,修复起来的成本越低,产生的风险也越小。 #### 1.3.3 测试与开发的关系 **瀑布模型** @@ -277,7 +277,7 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 * 响应变化高于遵循计划 - 通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费 + 通过高效的协作,获取快速的反馈,从而尽早做出调整,减少浪费。 **缺点:** @@ -287,11 +287,11 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 ### 1.4 软件缺陷 #### 1.4.1 缺陷定义 -IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 +IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 符合下面4个条件之一就是缺陷: 1. 软件未达到规格说明书中规定的功能。 -2. 软件出现了产品说明数中指明的不会出现的错误。 +2. 软件出现了产品说明书中指明的不会出现的错误。 3. 软件功能超出了产品说明书中指明的范围。 4. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。 @@ -386,7 +386,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。 7. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。 -以上是上报bug、创建bug必须要做的,在后续我们还会对bug进行修复、复测等工作,那在为了记录后续工作,bug还应该包含: +以上是上报bug、创建bug必须要做的,在后续我们还会对bug进行修复、复测等工作,那么为了记录后续工作,bug还应该包含: 1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 2. bug修订人:bug修订人员。 @@ -406,7 +406,7 @@ IEEE729-1983 对缺陷有一个标准的定义:从产品内部看,缺陷是 我国软件测试行业起步较晚,发展较慢,直到21世纪初期,我国才逐步开始重视软件测试行业。但近年来,软件行业的快速发展为软件测试行业的发展提供了良好的基础,随着我国软件测试行业的发展,行业内企业向规模化发展将获得规模效应,可以有效降低企业的单位成本;而软件测试技术的不断发展,也将淘汰那些技术实力较弱的企业,促使行业内企业向专业化方向发展。 -在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量1。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。 +在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。 从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 -- Gitee From 93db300c0ce8d285942052c09e76446472f515fc Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:34:20 +0800 Subject: [PATCH 14/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E4=BD=95=E6=98=95=E6=98=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 50 +++++++++++++++++++++++++------------------------- 1 file changed, 25 insertions(+), 25 deletions(-) diff --git a/README.md b/README.md index cc26bc3..0d4a356 100644 --- a/README.md +++ b/README.md @@ -422,17 +422,17 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 9. 高校从师资储备到专业设置再到人才培养的机制薄弱。 国内外软件测试差距 -1. 测试的理解认识 -2. 测试过程的管理 -3. 测试工具的使用 -4. 测试人员的培养 +1. 测试的理解认识; +2. 测试过程的管理; +3. 测试工具的使用; +4. 测试人员的培养。 #### 1.5.2 未来趋势 -1. 以软件为代表的计算机行业正在以一种井喷式的趋势发展 -2. 人才缺口大 -3. 女性员工受到青睐 -4. 未来发展空间大 -5. 外包为主 +1. 以软件为代表的计算机行业正在以一种井喷式的趋势发展; +2. 人才缺口大; +3. 女性员工受到青睐; +4. 未来发展空间大; +5. 外包为主。 #### 1.5.3 软件测试职业发展 1. 技术方向 @@ -458,22 +458,22 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 6. 发散思维方式 ### 1.6 测试认识的误区 -1. 使用了测试工具,就是进行了有效的测试 -2. 存在太多无法测试的东西 -3. 软件开发完成后才进行测试 -4. 软件发布后发现质量问题,是测试人员的问题 -5. 软件测试很简单,就是点点点,是个人就能做 -6. 软件测试没有前途,只有程序员才是软件高手 -7. 软件测试是测试人员的事情和程序员无关 -8. 项目进度吃紧时少做测试,时间多时多做测试 -9. 测试要进行穷尽测试 -10. 采样是随机抽取过程 -11. 测试和开发是对头 -12. 测试少报bug开发就会高兴点,报告也会好看点 -13. 自动化测试终会取代手工测试 -14. 规范化软件测试是增加项目成本 -15. 越多测试越有效 -16. 软件测试工作只负责项目上线/产品发布之前的部分 +1. 使用了测试工具,就是进行了有效的测试; +2. 存在太多无法测试的东西; +3. 软件开发完成后才进行测试; +4. 软件发布后发现质量问题,是测试人员的问题; +5. 软件测试很简单,就是点点点,是个人就能做; +6. 软件测试没有前途,只有程序员才是软件高手; +7. 软件测试是测试人员的事情和程序员无关; +8. 项目进度吃紧时少做测试,时间多时多做测试; +9. 测试要进行穷尽测试; +10. 采样是随机抽取过程; +11. 测试和开发是对头; +12. 测试少报bug开发就会高兴点,报告也会好看点; +13. 自动化测试终会取代手工测试; +14. 规范化软件测试是增加项目成本; +15. 越多测试越有效; +16. 软件测试工作只负责项目上线/产品发布之前的部分。 ### 1.7 知识点总结 ## 第2章 软件测试基础知识 -- Gitee From 19303aef2e2611ebc1402c25749caeda8a0353e0 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:38:18 +0800 Subject: [PATCH 15/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E5=86=AF=E6=99=93=E7=BF=A0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 0d4a356..fa76ab8 100644 --- a/README.md +++ b/README.md @@ -81,7 +81,7 @@ 软件项目是一种特殊的项目,具有如下特点: 1. 知识密集型,技术含量高 2. 涉及多个专业领域,多种技术综合应用 -3. 项目范围和目标的灵活性 +3. 项目范围广和目标的灵活性高 4. 风险大,收益大 5. 客户化程度高 6. 过程管理重要 @@ -155,7 +155,7 @@ IEEE:使用人工或自动手段来运行或测定某个软件系统的过程, 2. 1957–1978-证明为主(Demonstration Oriented) - 与调试区分开,这是软件测试史上一个重要的里程碑,主要目是确认软件是满足需求的。 + 与调试区分开,这是软件测试史上一个重要的里程碑,主要目的是确认软件是满足需求的。 3. 1979–1982-破坏为主(Destruction Oriented) @@ -219,7 +219,7 @@ The process of executing a program with the intent of finding errors. ![W模型](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/w-model.png) -明确表示出了测试与开发的并行关系 +明确表示出了测试与开发的并行关系。 **优点:** @@ -396,9 +396,9 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 6. bug备注:备注,以便记录一些额外信息。 #### 1.4.8 缺陷预防 -**差错**:人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) -**错误**:软件内部问题,设计错误、编码错误。(内部原因) -**失效**:软件系统运行时偏离了用户需求。(外部表现) +**差错:**人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) +**错误:**软件内部问题,设计错误、编码错误。(内部原因) +**失效:**软件系统运行时偏离了用户需求。(外部表现) ### 1.5 软件测试行业 #### 1.5.1 行业现状 @@ -719,7 +719,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ![健壮性边界值分析](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/bianjiezhi2.jpg) #### 3.3.3 应用举例 -延伸上节的例子来说明:学生信息系统中有一个“考试成绩”的输入项,成绩的取值范围是0~100之间的整数,考试成绩及格的分数线是60,优秀的分数线是80。那么这个例子中的边界值数据是哪些呢: +延伸上节的例子来说明:学生信息系统中有一个“考试成绩”的输入项,成绩的取值范围是0~100之间的整数,考试成绩及格的分数线是60,优秀的分数线是80。那么这个例子中的边界值数据是哪些呢? > 选取的边界值数据应该包括: > @@ -740,7 +740,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 边界值分析对布尔变量和逻辑变量没有多大意义。例如,布尔变量的极值是true和false,但是其余3个值不明确。 ### 3.4 决策表 -等价类划分法和边界值分析法只是孤立地考虑各个输人数据的测试效果,没有考虑输入数据的组合及其相互制约关系,而决策表考虑了多种条件的组合情况。决策表又称为判定表,分析多种逻辑条件(if-else、switch-case等)与执行动之间的关系。 +等价类划分法和边界值分析法只是孤立地考虑各个输人数据的测试效果,没有考虑输入数据的组合及其相互制约关系,而决策表考虑了多种条件的组合情况。决策表又称为判定表,分析多种逻辑条件(if-else、switch-case等)与执行之间的关系。 决策表由4部分组成: 1. 条件桩:列出了问题的所有条件,通常认为列出的条件次序无关紧要。 @@ -906,13 +906,13 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 | TC6 | F、特、@ | G、殊、* | 提示L和M | #### 3.5.4 优点和缺点 -优点: +**优点:** 1. 考虑多个输入之间的相互组合、相互制约的关系 2. 指出需求规格说明书中存在的不完整性和二义性 3. 帮助测试人员按照一定的步骤高效的开发测试用例 -缺点: +**缺点:** 1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到 2. 此方法得到的用例数量规模大 ### 3.6 场景法 @@ -952,7 +952,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 | TC6 | 场景6:ATM无现金 | 合法卡 | 123456 | 0.00 | 5000.00 | n/a | 提款选项不可用,用例结束 | | TC7 | 场景7:金额错误 | 合法卡 | 123456 | 2000.00 | 5000.00 | 20 | 提示错误,重新输入 | | TC8 | 场景8:卡内余额不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 600 | 提示错误,重新输入 | -| TC9 | 场景9:ATM现金不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 2500 | 提示错误,重新输入 | +| TC9 | 场景9:ATM现金不足 | 合法卡 | 123456 | 2000.00 | 5000.00 | 2500 | 提示错误,重新输入 | ### 3.7 错误推测法 -- Gitee From d602d949ea31b773e7ed9421aee8b000ddaadfb2 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 12:45:21 +0800 Subject: [PATCH 16/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E9=82=B5=E9=9C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index fa76ab8..7edbc23 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ ### 1 课程目标 * 掌握基础的软件测试理论、测试方法和策略 * 掌握常用工具的使用方法 -* 根据需求和设计文档独立编写测试计划、测试方案、测试用例以及测试报告 +* 根据需求和设计文档,独立编写测试计划、测试方案、测试用例以及测试报告 ### 2 主要内容 * 软件测试概论 * 软件测试基础知识 @@ -95,24 +95,24 @@ #### 1.2.2 可行性分析 **描述:** 由项目组相关成员去研究需求是否可行,能不能做出来。 -**参与者:** 产品经理、架构师、项目经理、开发 +**参与者:** 产品经理、架构师、项目经理、开发人员 #### 1.2.3 需求分析 **描述:** 需求分析其实是在做需求细化,按照任务说明书中的任务内容和指标具体细化各个点,细化到每个输入框、每个按钮的样式,输入输出等各项值。 -**参与者:** 产品经理、架构师、项目经理、测试/质量管理员(很多公司把这个统称为QA)、开发 +**参与者:** 产品经理、架构师、项目经理、测试人员/质量管理员(很多公司把这个统称为QA)、开发人员 **输出:**《需求规格说明书》 #### 1.2.4 评审 **描述:** 评审就是做审查,对这个阶段的工作进行审查,看是否偏离或者有遗漏(比如:设计和工厂的各个环节都有相关的审查,审查材料是否合格、设计是否符合规定、按照工人/设计出的材料需求是否足够或者多余等等,这些审查都是评审);评审一般由相应工作人员来参与。 -**参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试、开发一起评审;系统设计一般是项目经理、开发评审;测试策略评审一般是测试组内部评审等等 +**参与者:** 每个阶段的评审一般都是各职能部门内部审核,也可以申请其他相关人员审核,比如需求评审,一般是产品经理、项目经理、测试人员、开发人员一起评审;系统设计一般是项目经理、开发人员评审;测试策略评审一般是测试组内部评审等等 #### 1.2.5 设计 **描述:** 架构师根据需求确定产品或者项目的场景、特点,选择合适的框架,技术使项目实现最优化。在此基础上将系统进行概要设计,包括系统总体数据结构、数据库结构、模块结构以及它们之间的关系等。开发人员根据概要设计对具体模块进行详细设计,包括接口、参数等。此处设计会形成概要设计文档和详细设计文档。 -**参与者:** 项目经理、架构师、开发、测试 +**参与者:** 项目经理、架构师、开发人员、测试人员 #### 1.2.6 编码 **描述:** 开发人员根据详细设计文档对系统进行模块化开发,在确定参数和接口的情况下,根据需求对模块内部进行方法级别的设计和编码以及自测,对产品功能进行一一实现。 @@ -122,7 +122,7 @@ #### 1.2.7 提测 **描述:** 开发人员完成一个小迭代/小功能,且完成自测(开发编码完成后,一般都会自己检测下),于是向测试部门发起提测,一般以邮件方式或者任务管理工具的任务流方式向测试部门通知xxx模块/功能可以测试。 -**参与者:** 任务责任人(开发)、测试 +**参与者:** 任务责任人(开发)、测试人员 #### 1.2.8 测试 - 测试需求 @@ -135,7 +135,7 @@ **描述:** 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 -**参与人:** 配置管理人员、测试 +**参与人:** 配置管理人员、测试人员 #### 1.2.10 支持维护 @@ -408,7 +408,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 在软件业较发达的国家,软件测试产业已形成规模,比较发达,软件测试不仅早已成为软件开发的一个重要组成部分,而且在整个软件开发的系统工程中占据着相当大的比重。在微软公司内部,软件测试人员与软件开发人员的比例一般为1.5∶1到2.5∶1左右,即一个开发人员背后,有至少两位测试人员在工作,以保证软件产品的质量。国外优秀的软件开发机构把40%的工作花在软件测试上,软件测试费用占软件开发总费用的30%至50%,对于一些要求高可靠性、高安全性的软件,测试费用甚至相当于整个软件项目开发所有费用的3至5倍。 -从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单的测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 +从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单地测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 当前国内软件测试行业主要存在以下问题: 1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题。 -- Gitee From 577979866d02d261e50f5a7ee90433d8b3844a19 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 23:16:29 +0800 Subject: [PATCH 17/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E7=A7=A6=E5=85=B6=E4=B9=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 7edbc23..9fc0102 100644 --- a/README.md +++ b/README.md @@ -343,7 +343,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 | P3 | 高 | 影响整个测试的继续进行,要马上修改 | | P4 | 急 | 系统无法继续执行下去,必须立即修改 | -严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为1这样的缺陷着手,而不是优先修复简单的,由简到难。 +严重性和优先级对于审查缺陷报告并决定哪些软件缺陷应该修复,以何种顺序修复的人员极为重要。如果一个程序员受命修复10个缺陷,他就应该先从严重性为1 、优先级为4这样的缺陷着手,而不是优先修复简单的,由简到难。 综合使用重要性等级和严重性双标准的优先顺序: -- Gitee From 9a1f3000849c90aa4610d865fa993f2e59938859 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 23:18:24 +0800 Subject: [PATCH 18/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E5=B4=94=E6=80=80=E5=8D=9A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 9fc0102..999c3d2 100644 --- a/README.md +++ b/README.md @@ -390,10 +390,10 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 2. bug修订人:bug修订人员。 -3. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。 -4. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。 -5. bug复测说明:由复测人员来写,说明复测过程,复测结果等。 -6. bug备注:备注,以便记录一些额外信息。 +3. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。 +4. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。 +5. bug复测说明:由复测人员来写,说明复测过程,复测结果等。 +6. bug备注:备注,以便记录一些额外信息。 #### 1.4.8 缺陷预防 **差错:**人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) -- Gitee From cd6b59f4d383946ca8d3caf96620cfe423654158 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Thu, 16 Sep 2021 23:24:17 +0800 Subject: [PATCH 19/30] =?UTF-8?q?=E6=9D=8E=E4=BD=B3=E9=BD=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 999c3d2..00e0f6a 100644 --- a/README.md +++ b/README.md @@ -480,7 +480,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 2.1 概述 1. 从软件测试的目的来理解 - 软件的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。 + 软件测试的目的是发现软件中的错误,是为了证明软件有错,而不是无错。是在软件投入运行前,对软件需求分析、设计和编码各个阶段产品的最终检查,是为了保证软件开发产品的正确性、完整性和一致性。 2. 从软件测试的性质来理解 -- Gitee From 9b5da89f1ba015dd1d671b881c49c950b27b681c Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Fri, 17 Sep 2021 11:39:32 +0800 Subject: [PATCH 20/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E6=9B=B9=E9=9D=99=E9=93=AB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/README.md b/README.md index 00e0f6a..a85254b 100644 --- a/README.md +++ b/README.md @@ -146,7 +146,7 @@ ### 1.3 软件测试概述 #### 1.3.1 软件测试定义 软件测试的经典定义是:在规定的条件下对程序进行操作,以发现程序错误,衡量软件质量,并对其是否能满足设计要求进行评估的过程。 -IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。 +IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。 #### 1.3.2 测试发展历程 1. 1957年之前-调试为主(Debugging Oriented) @@ -189,13 +189,13 @@ The process of executing a program with the intent of finding errors. 为了更早的发现问题,测试应延伸需求评审,设计审查活动中,软件生命周期的每个阶段都应包含测试。 -**优点:** +**优点:** 1. 各阶段划分清晰 2. 强调计划与需求分析 3. 适合需求稳定的产品开发 -**缺点:** +**缺点:** 1. 单一流程,不可逆 2. 风险显露得晚,纠正机会少 @@ -754,7 +754,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 所有条件都是逻辑结果(即真/假、是/否、0/1)的决策表称为有限条件决策表。如果条件有多个值,则对应的决策表叫做扩展条目决策表。决策表设计测试用例,条件解释为输入,动作解释为输出。 -决策表适合以下特征的应用程序: +决策表适合以下特征的应用程序: 1. if-then-else分支逻辑突出。 2. 输入变量之间存在逻辑关系。 3. 涉及输入变量子集的计算。 @@ -762,7 +762,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 5. 很高的圈复杂度。 #### 3.4.1 应用举例 -决策表(判定表)设计测试用例的具体步骤如下: +决策表(判定表)设计测试用例的具体步骤如下: 1. 确定规则的个数。假如有n个条件,每个条件有两个取值(0,1),故有2种规则。 2. 列出所有的条件桩和动作桩。 3. 填入条件项。 @@ -912,7 +912,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 2. 指出需求规格说明书中存在的不完整性和二义性 3. 帮助测试人员按照一定的步骤高效的开发测试用例 -**缺点:** +**缺点:** 1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到 2. 此方法得到的用例数量规模大 ### 3.6 场景法 @@ -961,7 +961,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 该方法强调的是对被测试软件的需求理解以及设计实现的细节把握,当然还有个人的能力。那么显而易见地,这个方法的缺点就是太过依赖个人能力,难以系统化。因此,这个方法一般是作为测试用例设计的补充,而不是单独用来设计测试用例。在回归测试中应用较多。 -错误推测法一般采用如下技术: +错误推测法一般采用如下技术: 1. 有关软件设计方法和实现技术。 2. 有关前期测试阶段结果的知识。 3. 测试类似或相关系统的经验,了解以前这些系统曾在哪些地方出现缺陷。 @@ -1000,14 +1000,14 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 - JavaScript字符转义 ### 3.8 综合策略 黑盒测试方法有等价类划分、边界值分析、决策表、因果图、场景法、错误推测法等,每种测试方法都有其各自的特点和适用场合。 -软件测试专家Myers给出了黑盒测试方法中各种测试方法的使用策略: +软件测试专家Myers给出了黑盒测试方法中各种测试方法的使用策略: 1. 在任何情况下都必须使用边界值分析方法。经验表明,用这种方法设计的测试用例发现程序错误的能力最强。 2. 必要时使用等价类划分方法补充一些测试用例。 3. 用错误推测法再追加一些测试用例。 4. 对照程序逻辑,检查已设计出的测试用例的逻辑覆盖程度,如果没有达到要求的覆盖标准,应当再补充足够的测试用例。 5. 如果程序的功能说明中含有输入条件的组合情况,则一开始就可选用因果图法。 -对于功能性测试技术,可以根据如下条件进行选择: +对于功能性测试技术,可以根据如下条件进行选择: 1. 如果变量是独立的,则可以用定义域测试和等价类测试。 2. 如果变量不是独立的,可采用决策表测试。 3. 如果为单缺陷假设,则可采用边界值分析和健壮性测试。 -- Gitee From 6fd0d156af2ad728e2f4bc6dca2b35f5de33c74b Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Fri, 17 Sep 2021 22:33:39 +0800 Subject: [PATCH 21/30] =?UTF-8?q?=E6=89=8B=E5=B7=A5=E5=90=88=E5=B9=B6?= =?UTF-8?q?=E5=88=98=E8=B6=85=E9=9C=9E?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index a85254b..8e34400 100644 --- a/README.md +++ b/README.md @@ -580,7 +580,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 3. 前置条件:该测试用例的前提条件,比如测试wangdachui/dachui12345(用户名/密码)账户是否能正确登录进去,那前提wangdachui/dachui12345一定是注册过的 4. 测试步骤:就是测试的所有操作步骤,最好是每一个步骤应该对应一个期望结果,最少也得一个测试用例对应一个期望结果 5. 期望结果:就是希望得到的结果(正确的结果) -6. 测试结果:实际测试的结果,可选项有:通过、不通过、暂时挂起/锁定(就是暂时不测试); +6. 测试结果:实际测试的结果,可选项有:通过、不通过、暂时挂起/锁定(就是暂时不测试) 7. 对应的bug:当期望结果与实际结果不符时测试不通过,此时需要上报bug(记录缺陷),bug需要与测试用例对应 8. 测试执行人:实际由谁来执行测试用例;也有任务分配人的选项,就是测试用例分配给哪个测试员来测试 9. 备注:做一些备注或者测试的说明 -- Gitee From 3a1d547e362868b59f8f81d450b6d899d1b63a11 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Fri, 17 Sep 2021 23:08:52 +0800 Subject: [PATCH 22/30] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E9=98=B6=E6=AE=B5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 51 insertions(+) diff --git a/README.md b/README.md index 8e34400..54421c9 100644 --- a/README.md +++ b/README.md @@ -1047,9 +1047,60 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 6.4 测试设计 ### 6.5 测试执行 #### 6.5.1 单元测试 +单元测试即为将整个软件分解为各个单元,随后对单元进行测试。此类测试策略的优点在于所需分析数据较少,且针对性较强,程序开发者于开发过程中可通过操作经验明确出现问题的大致区域,随后针对此类问题对相关单元展开分析,进行问题排查。但需注意的是,某些程序中无具体单元驱动程序,即单个单元无法有效驱动,易出现问题,若针对此类软件展开测试,需重点注意此类分解单元。 + +单元测试是对软件组成单元进行测试。其目的是检验软件基本组成单位的正确性。测试的对象是软件设计的最小单位:模块。 + +* 测试阶段:编码后 +* 测试对象:最小模块 +* 测试人员:白盒测试工程师或开发工程师 +* 测试依据:代码和注释+详细设计文档 +* 测试方法:白盒测试 +* 测试内容:模块接口测试、局部数据结构测试、路径测试、错误处理测试、边界测试 + +单元测试针对模块进行测试,主要有一下5个任务: +* 模块接口:全局量定义一致性,调用参数 +* 局部数据结构:数据的定义和使用 +* 边界条件:循环边界和输入边界 +* 执行路径:关键路径和重要路径 +* 错误处理:非合理输入和系统错误 + #### 6.5.2 集成测试 +集成测试与单元测试相反,原理为将部分需测试部分作为整体进行集成,随后针对此类集成部分进行测试。测试要求为此类被测试集成题应具有一定的结构,且属于非渐增方式集成。对于较大软件而言,集成测试方式较单元测试方式而言较为繁琐,多数大型软件的测试皆采取渐增方式进行测试。渐增测试方式为集成测试方式的衍生,其能够按照不同次序对软件进行测试,日常测试中,常将两类方式进行集成测试,随后按照次序展开选择。 + +集成测试也称联合测试、组装测试,将程序模块采用适当的集成策略组装起来,对系统的接口及集成后的功能进行正确性检测的测试工作。主要目的是检查软件单位之间的接口是否正确。 + +* 测试阶段:一般单元测试之后进行 +* 测试对象:模块间的接口 +* 测试人员:白盒测试工程师或开发工程师 +* 测试依据:单元测试的模块+概要设计文档 +* 测试方法:黑盒测试与白盒测试相结合 +* 测试内容:模块之间数据传输、模块之间功能冲突、模块组装功能正确性、全局数据结构、单模块缺陷对系统的影响 + #### 6.5.3 系统测试 +一般情况下,系统测试采用黑盒法来进行测试的,以此来检查该系统是否符合软件需求。本阶段的主要测试内容包括健壮性测试、性能测试、功能测试、安装或反安装测试、用户界面测试、压力测试、可靠性及安全性测试等。为了有效保证这一阶段测试的客观性,必须由独立的测试小组来进行相关的系统测试。另外,系统测试过程较为复杂,由于在系统测试阶段不断变更需求造成功能的删除或增加,从而使程序不断出现相应的更改,而程序在更改后可能会出现新的问题,或者原本没有问题的功能由于更改导致出现问题。所以,测试人员必须进行回归测试。 + +将软件系统看成是一个系统的测试。包括对功能、性能以及软件所运行的软硬件环境进行测试。时间大部分在系统测试执行阶段。 + +* 测试阶段:集成测试通过之后 +* 测试对象:整个系统(软、硬件) +* 测试人员:黑盒测试工程师 +* 测试依据:需求规格说明文档 +* 测试方法:黑盒测试 +* 测试内容:功能、界面、可靠性、易用性、性能、兼容性、安全性等 + #### 6.5.4 验收测试 +验收测试是最后一个阶段的测试操作,在软件产品投入正式运行前的所要进行的测试工作。和系统测试相比而言,验收测试与之的区别就只是测试人员不同,验收测试则是由用户来执行这一操作的。验收测试的主要目标是为向用户展示所开发出来的软件符合预定的要求和有关标准,并验证软件实际工作的有效性和可靠性,确保用户能用该软件顺利完成既定的任务和功能。通过了验收测试,该产品就可进行发布。但是,在实际交付给用户之后,开发人员是无法预测该软件用户在实际运用过程中是如何使用该程序的,所以从用户的角度出发,测试人员还应进行Alpha测试或Beta测试这两种情形的测试。Alpha测试是在软件开发环境下由用户进行的测试,或者模拟实际操作环境进而进行的测试。Alpha测试主要是对软件产品的功能、局域化、界面、可使用性以及性能等等方面进行评价。而Beta测试是在实际环境中由多个用户对其进行测试,并将在测试过程中发现的错误有效反馈给软件开发者。所以在测试过程中用户必须定期将所遇到的问题反馈给开发者。 + +验收测试是部署软件之前的最后一个测试操作。它是技术测试的最后一个阶段,也称为交付测试。阿旺总结验收测试的目的是确保软件准备就绪,按照项目合同、任务书、双方约定的验收依据文档,向软件购买都展示该软件系统满足原始需求。 + +* 测试阶段:系统测试通过之后 +* 测试对象:整个系统(包括软硬件)。 +* 测试人员:主要是最终用户或者需求方。 +* 测试依据:用户需求、验收标准 +* 测试方法:黑盒测试 +* 测试内容:同系统测试(功能...各类文档等) + #### 6.5.5 α测试 #### 6.5.6 β测试 ### 6.6 回归测试 -- Gitee From a5381ef2e63578ebce7053baf8e24ead71a2c1f1 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Fri, 17 Sep 2021 23:20:34 +0800 Subject: [PATCH 23/30] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E6=89=A7=E8=A1=8C?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 54421c9..fcb2bd8 100644 --- a/README.md +++ b/README.md @@ -1052,7 +1052,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 单元测试是对软件组成单元进行测试。其目的是检验软件基本组成单位的正确性。测试的对象是软件设计的最小单位:模块。 * 测试阶段:编码后 -* 测试对象:最小模块 +* 测试对象:最小模块(函数、类、模块) * 测试人员:白盒测试工程师或开发工程师 * 测试依据:代码和注释+详细设计文档 * 测试方法:白盒测试 -- Gitee From edfb6bbe49f7d189e0f64345bb2e37a236735f48 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Fri, 17 Sep 2021 23:57:44 +0800 Subject: [PATCH 24/30] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E8=AE=A4=E8=AF=86?= =?UTF-8?q?=E8=AF=AF=E5=8C=BA=E8=A1=A5=E5=85=85=E5=92=8C=E7=AB=A0=E8=8A=82?= =?UTF-8?q?=E5=B0=8F=E7=BB=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 63 ++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 56 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index fcb2bd8..893a888 100644 --- a/README.md +++ b/README.md @@ -459,22 +459,71 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 1.6 测试认识的误区 1. 使用了测试工具,就是进行了有效的测试; +>有效的测试首先是指该软件具有可测试性。可测试性反映了软件质量的内在属性,是一个强内聚、弱耦合、接口明确的软件,它不会因为使用了某种测试工具,就证明被测试的软件具有可测试性。 + 2. 存在太多无法测试的东西; +>在软件开发领域,确实存在一些看起来比另外一些东西难测试的东西,但是远非无法测试。在大多数情况下,发生这种情况还是由于被测试软件本身在设计时没有考虑到可测试性的问题。只不过这种不可测试性不是由于被测试软件内部的过紧耦合造成的,而是和外部某些很难测试的部分耦合过紧,从而表现出被测试软件本身很难测试的特征。这些很难测试的部分,比较常见的有图形界面、硬件、数据库等。 + 3. 软件开发完成后才进行测试; +>软件测试是一个系列过程活动,包括软件测试需求分析、测试计划设计、测试用例设计、执行测试,软件测试贯穿软件项目的整个生命过程,每一个阶段都要进行不同目的和内容的测试活动,以保证各个阶段的正确性。软件测试的对象不仅仅包括软件代码,还包括软件需求文档和设计等各类文档。软件开发与软件测试是交互进行的,例如,单元编码需要单元测试,模块组合阶段需要集成测试。如果等到软件编码结束后才进行测试,测试的时间将会很短,测试的覆盖面将很不全面,测试的效果也将很差。更严重的是,如果发现了软件需求阶段或概要设计阶段的错误,要修复该类错误,将会耗费大量的时间和人力。 + 4. 软件发布后发现质量问题,是测试人员的问题; +>这种错误的认识非常伤害软件测试人员的积极性。软件中的错误可能来自软件项目中的各个过程,软件测试只能确认软件存在错误,不能保证软件没有错误,因此从根本上讲,软件测试不可能发现全部错误。从软件开发的角度看,软件的高质量不是软件测试人员测出来的,是靠软件生命周期的各个过程中设计出来的。如果出现软件错误,不能简单地归结为某一个人的责任,有些错误可能是技术原因,也可能是混乱的管理所致。因此,应该分析软件项目的各个过程,从过程改进方面寻找产生错误的原因和改进的措施。 + 5. 软件测试很简单,就是点点点,是个人就能做; +>随着软件工程学的发展和软件项目管理经验的提高,软件测试已经形成了一个独立的技术学科,演变成一个具有巨大市场需求的行业。软件测试技术不断更新和完善,新工具、新流程、新方法都在不断出现,因此,软件测试需要学习很多测试知识,更需要不断的实践经验和学习精神。 + 6. 软件测试没有前途,只有程序员才是软件高手; +>随着市场对软件质量要求的不断提高,软件测试将变得越来越重要,对测试人员的要求也越来越高。测试人员不仅要懂得如何测试,还要懂得被测软件的业务知识和专业知识.而开发人员往往只需要对自己开发的模块了解比较深,对算法掌握的程度要求高一些,所以,软件测试和开发人员只是工作的侧重点不同,并不存在水平差异的问题。 + 7. 软件测试是测试人员的事情和程序员无关; +>开发和测试是相辅相成的过程,需要测试人员、程序员和系统分析师等保持密切的联系,需要交流和协调,以便提高测试效率。另外,对于单元测试,主要应该由程序员完成,必要时测试人员可以帮助设计测试样例。对于测试中发现的软件错误,很多都需要程序员通过修改编码才能修复。程序员通过有目的地分析软件错误的类型、数量,找出产生错误的位置和原因,以避免同样的错误发生,积累编程经验,提高软件开发能力。 + 8. 项目进度吃紧时少做测试,时间多时多做测试; -9. 测试要进行穷尽测试; +>这是在软件开发过程中不重视软件测试的常见表现,也是软件项目过程管理混乱的表现,必然会降低软件测试的质量。软件项目开发需要合理的项目进度计划,其中就包括测试计划,对项目实施过程中的任何问题,都要有风险分析和相应的对策,不要因为开发进度的延期而简单地缩短测试时间,压缩人力和资源。因为缩短测试时间使测试不完整,引入潜在风险,往往造成更大的软件缺陷。避免这种现象的最好办法是加强软件过程的计划和控制,包括软件测试计划、测试设计、测试执行、测试度量和测试控制。 + +9. 测试要进行穷尽测试; +>测试最多只是采样。 + 10. 采样是随机抽取过程; -11. 测试和开发是对头; -12. 测试少报bug开发就会高兴点,报告也会好看点; -13. 自动化测试终会取代手工测试; -14. 规范化软件测试是增加项目成本; -15. 越多测试越有效; -16. 软件测试工作只负责项目上线/产品发布之前的部分。 +>测试采样过程需要使用正确的测试用例设计方法来操作。 + +11. 测试和开发是对头; +>开发和测试是合作伙伴的关系,在日常生活中要注意沟通技巧和方式,如意见不一致且不能说服对方的问题,上报给负责人去决定。 + +12. 测试少报bug开发就会高兴点,报告也会好看点; +>遇到缺陷一定要上报,即使他不能稳定复现(当然测试要尽可能的再现缺陷,并且找出再现问题的具体步骤)。但是一定不要不负责任的乱报。 + +13. 自动化测试终会取代手工测试; +>我们在选择用哪种方法的测试的时候,坚持“效率最高化,利益最大化”的原则来选择用最适合的方法。我们工作的目的是为了利益,而不是显得高端。 +> +>自动化测试的初衷是将测试从繁重的、重复的回归工作中解放出来,从而提高测试效率的。并不是为了取代手工测试的,当然以目前的情况来看也取代不了手工测试。另外自动化测试需要在前期投入大量的人力资源和时间,且维护成本很高,故不能盲目推崇测试自动化。 + +||手工测试|自动化测试| +|----|----|----| +|概念|手工测试是由专门的测试人员从用户视角来验证软件是否满足设计要求的行为,更适合用于深度的测试和强调主观判断的测试。|自动化测试利用测试工具软件来控制测试的自动化执行以及对预期和结果进行检查。一般来说单元测试、接口测试和性能测试等就是利用自动化测试完成。| +|优点|易发现缺陷
容易实施
创造性、灵活性|高效率、速度快
高复用性
覆盖率容易度量
准确、可靠
不知疲劳| +|缺点|覆盖量化难
重复测试效率低
不一致性,可靠性低
人力资源依赖|机械、发现缺陷率低
一次性投入较大
对人员要求高| + +14. 规范化软件测试是增加项目成本; +>大家常说“磨刀不误砍柴工”,但是真正用时又拿“能省则省”的理论来操作,殊不知此时省了相当于埋了颗雷。不仅要规范化软件测试,更要规范化整个软件过程,规避个人水平、责任心、经验的差距。 + +15. 测出bug越多测试越有效; +>测试过程中bug的数量并不能说明测试的有效性,只能说明开发人员的技术水平高低。项目上线后/产品卖出后现场反馈回来的线上bug数量才能反应测试的有效性。 + +16. 软件测试工作只负责项目上线/产品发布之前的部分。 +>测试活动贯穿整个软件生命周期。 + ### 1.7 知识点总结 +1. 软件定义与发展 +2. 软件测试定义与发展 +3. 软件生命周期 +4. 软件测试模型 +5. 缺陷定义、来源、产生原因和记录方法 +6. 软件测试行业 +7. 软件测试职业发展 +8. 软件测试认识误区 + ## 第2章 软件测试基础知识 ### 2.1 概述 -- Gitee From e21a708021e6e1c95cd1167428459a4c471d1bd0 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Sat, 18 Sep 2021 00:05:08 +0800 Subject: [PATCH 25/30] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E7=AB=A0=E5=B0=8F?= =?UTF-8?q?=E7=BB=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README.md b/README.md index 893a888..26eefdc 100644 --- a/README.md +++ b/README.md @@ -683,6 +683,10 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 6. 在系统测试中发现的错误已经得到修改,各级缺陷修复率达到标准 ### 2.6 知识点总结 +1. 软件测试的目的和原则 +2. 软件测试的分类(测试阶段、执行状态、测试技术、执行主体) +3. 测试用例设计和维护 +4. 测试停止标准 ## 第3章 黑盒测试 ### 3.1 概述 -- Gitee From af2acaad7bbde6c58db3f72831add0b2a1ae512b Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Sat, 18 Sep 2021 00:07:26 +0800 Subject: [PATCH 26/30] =?UTF-8?q?=E7=AC=AC=E4=B8=89=E7=AB=A0=E5=B0=8F?= =?UTF-8?q?=E7=BB=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/README.md b/README.md index 26eefdc..8d9e664 100644 --- a/README.md +++ b/README.md @@ -1068,6 +1068,15 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 5. 如果程序包含大量例外处理,可采用健壮性测试和决策表测试。 6. 如果变量引用的是逻辑量,可采用等价类测试用例和决策表测试。 +### 3.9 知识点总结 +1. 等价类划分 +2. 边界值分析 +3. 决策表 +4. 因果图 +5. 场景法 +6. 错误推测法 +7. 综合策略 + ## 第4章 白盒测试 ### 4.1 概述 ### 4.2 静态测试 -- Gitee From ba1eb5f2b900708ba41208a38847979c0fbff8a2 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Sat, 18 Sep 2021 00:27:35 +0800 Subject: [PATCH 27/30] =?UTF-8?q?=E5=8A=A8=E6=80=81=E6=B5=8B=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 38 +++++++++++++++++++++++++++++++------- 1 file changed, 31 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 8d9e664..f0b77dc 100644 --- a/README.md +++ b/README.md @@ -1079,14 +1079,38 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ## 第4章 白盒测试 ### 4.1 概述 +白盒测试是把测试对象看做打开的盒子,允许测试人员利用程序内部的逻辑结构及有关信息设计或选择测试用例,通过在不同点检查程序状态确定实际状态是否与预期的状态一致。白盒测试测试软件产品的内部结构和处理过程,而不测试软件产品的功能,用于纠正软件系统在描述、表示和规格上的错误,是进一步测试的前提。 + +白盒测试分为静态测试和动态测试。 + +静态白盒测试是在不执行的条件下有条理地仔细审查软件设计、体系结构和代码,从而找出软件缺陷的过程,有时也称为结构分析。 + +动态白盒测试也称结构化测试,通过查看并使用代码的内部结构设计和执行测试。 ### 4.2 静态测试 -### 4.3 逻辑覆盖 -### 4.4 路径分析 -### 4.5 控制结构测试 -### 4.6 数据流测试 -### 4.7 程序插桩 -### 4.8 测试方法综述 -### 4.9 知识点总结 +静态方法是指不运行被测程序本身,仅通过分析或检查源程序的语法、结构、过程、接口等来检查程序的正确性。对需求规格说明书、软件设计说明书、源程序做结构分析、流程图分析、符号执行来找错。 + +此类过程中应用数据较少,主要过程为通过软件的静态性测试(即人工推断或计算机辅助测试)测试程序中运算方式、算法的正确性,进而完成测试过程,此类测试的优点在于能够消耗较短时间、较少资源完成对软件、软件代码的测试,能够较为明显地发现此类代码中出现的错误。静态测试方法适用范围较大,尤其适用于较大型的软件测试。 + +静态测试有代码检查、静态结构分析。 + +* 代码检查 +主要是检查代码的可读性、逻辑表达的正确性、结构的合理性等方面。一般在编译和动态测试之前执行,具有走查、审查或伙伴检查等方法 + +* 静态结构分析 +测试者通过使用测试工具,分析程序代码数据结构等控制逻辑,生成函数调用关系图等,用于检查函数之间的调用关系是否符合要求,是否存在递归调用,函数的调用是否过深,是否存在孤立的函数,用于检测系统是否存在结构缺陷。 + +### 4.3 动态测试 +动态测试方法是指通过运行被测程序,检查运行结果与预期结果的差异,并分析运行效率、正确性和健壮性等性能。主要目的为检测软件运行中出现的问题,较静态测试方式相比,其被称为动态的原因即为其测试方式主要依赖程序的运用,主要为检测软件中动态行为是否缺失、软件运行效果是否良好。 + +### 4.4 逻辑覆盖 +逻辑测试,又称为控制流覆盖,是一种按照程序内部逻辑结构和编码结构设计测试用例的测试方法。目的是要测试程序中的语句,判定(控制流能够分解为不同路径的程序点),条件(形成判定的原子谓词)等。根据覆盖的标准不同,分为语句覆盖、判定覆盖、条件覆盖、条件判定覆盖、修正条件判定覆盖、增强条件判定覆盖、条件组合覆盖和路径覆盖等标准。 + +### 4.5 路径分析 +### 4.6 控制结构测试 +### 4.7 数据流测试 +### 4.8 程序插桩 +### 4.9 测试方法综述 +### 4.10 知识点总结 ## 第5章 性能测试 ### 5.1 基本概念 -- Gitee From 839cc1e4b48df401bad560567f8111aee0e0116c Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Sun, 19 Sep 2021 12:20:18 +0800 Subject: [PATCH 28/30] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E6=A0=87=E7=82=B9?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 373 +++++++++++++++++++++++++++--------------------------- 1 file changed, 189 insertions(+), 184 deletions(-) diff --git a/README.md b/README.md index f0b77dc..7dd8ba4 100644 --- a/README.md +++ b/README.md @@ -51,10 +51,10 @@ ##### 管理文档 从管理的角度规定涉及软件生存的信息: -1. 职责定义 -2. 开发过程的每个阶段的进度和进度变更的记录 -3. 软件变更情况的记录 -4. 相对于开发的判定记录 +1. 职责定义; +2. 开发过程的每个阶段的进度和进度变更的记录; +3. 软件变更情况的记录; +4. 相对于开发的判定记录。 * 《工作报告》 * 《工作日志》 @@ -72,19 +72,19 @@ * 《软件支持手册》 #### 1.1.3 软件发展史 -1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序) -2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统。 -3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准。 +1. 程序设计阶段:个体化生产、专用软件、规模小、功能单一、开发者即使用者。(软件 = 程序); +2. 程序系统阶段:多用户人机交互,实时系统和数据库管理系统; +3. 软件工程阶段:以软件的产品化、系列化、工程化和标准化为特征的软件产业发展起来,软件开发有了可以遵循的软件工程化的设计准则、方法和标准; 4. 多层分布结构,面向服务架构。 #### 1.1.4 软件项目 软件项目是一种特殊的项目,具有如下特点: -1. 知识密集型,技术含量高 -2. 涉及多个专业领域,多种技术综合应用 -3. 项目范围广和目标的灵活性高 -4. 风险大,收益大 -5. 客户化程度高 -6. 过程管理重要 +1. 知识密集型,技术含量高; +2. 涉及多个专业领域,多种技术综合应用; +3. 项目范围广和目标的灵活性高; +4. 风险大,收益大; +5. 客户化程度高; +6. 过程管理重要。 ### 1.2 软件生命周期 #### 1.2.1 需求定义 @@ -131,7 +131,7 @@ - 测试执行 - 回归测试 - 测试评估 -#### 1.2.9 部署/发版 +#### 1.2.9 部署/发版 **描述:** 经过前面的各个阶段,产品已经可以出售或者面向大众了。配置管理人员进行封版、版本制作(针对产品来说)/部署上线(针对项目应用来说)。 @@ -146,7 +146,7 @@ ### 1.3 软件测试概述 #### 1.3.1 软件测试定义 软件测试的经典定义是:在规定的条件下对程序进行操作,以发现程序错误,衡量软件质量,并对其是否能满足设计要求进行评估的过程。 -IEEE:使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。 +IEEE(电气与电子工程师协会):使用人工或自动手段来运行或测定某个软件系统的过程,其目的在于检测他是否满足规定的需求或弄清预期结果和实际结果的差别。 #### 1.3.2 测试发展历程 1. 1957年之前-调试为主(Debugging Oriented) @@ -191,15 +191,15 @@ The process of executing a program with the intent of finding errors. **优点:** -1. 各阶段划分清晰 -2. 强调计划与需求分析 -3. 适合需求稳定的产品开发 +1. 各阶段划分清晰; +2. 强调计划与需求分析; +3. 适合需求稳定的产品开发。 **缺点:** -1. 单一流程,不可逆 -2. 风险显露得晚,纠正机会少 -3. 测试只是其中一个阶段,缺乏全过程测试思想 +1. 单一流程,不可逆; +2. 风险显露得晚,纠正机会少; +3. 测试只是其中一个阶段,缺乏全过程测试思想。 **V模型** @@ -246,17 +246,17 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 在敏捷开发中,软件项目在构建初期被切分成多个子项目,各个子项目的成果都经过测试,具备可视、可集成和可运行使用的特征。换言之,就是把一个大项目分为多个相互联系,但也可独立运行的小项目,并分别完成,在此过程中软件一直处于可使用状态。 **《联盟敏捷宣言》** -1. 最重要的是通过尽早和不断交付有价值的软件满足客户需要。 -2. 我们欢迎需求的变化,即使在开发后期。敏捷过程能够驾驭变化,保持客户的竞争优势。 -3. 经常交付可以工作的软件,从几星期到几个月,时间尺度越短越好。 -4. 业务人员和开发者应该在整个项目过程中始终朝夕在一起工作。 -5. 围绕斗志高昂的人进行软件开发,给开发者提供适宜的环境,满足他们的需要,并相信他们能够完成任务。 -6. 在开发小组中最有效率也最有效果的信息传达方式是面对面的交谈。 -7. 可以工作的软件是进度的主要度量标准。 -8. 敏捷过程提倡可持续开发。出资人、开发人员和用户应该总是维持不变的节奏。 -9. 对卓越技术与良好设计的不断追求将有助于提高敏捷性。 -10. 简单——尽可能减少工作量的艺术至关重要。 -11. 最好的架构、需求和设计都源自自我组织的团队。 +1. 最重要的是通过尽早和不断交付有价值的软件满足客户需要; +2. 我们欢迎需求的变化,即使在开发后期;敏捷过程能够驾驭变化,保持客户的竞争优势; +3. 经常交付可以工作的软件,从几星期到几个月,时间尺度越短越好; +4. 业务人员和开发者应该在整个项目过程中始终朝夕在一起工作; +5. 围绕斗志高昂的人进行软件开发,给开发者提供适宜的环境,满足他们的需要,并相信他们能够完成任务; +6. 在开发小组中最有效率也最有效果的信息传达方式是面对面的交谈; +7. 可以工作的软件是进度的主要度量标准; +8. 敏捷过程提倡可持续开发;出资人、开发人员和用户应该总是维持不变的节奏; +9. 对卓越技术与良好设计的不断追求将有助于提高敏捷性; +10. 简单——尽可能减少工作量的艺术至关重要; +11. 最好的架构、需求和设计都源自自我组织的团队; 12. 每隔一定时间,团队都要总结如何更有效率,然后相应地调整自己的行为。 **解读:** @@ -290,15 +290,15 @@ W 模型是顺序性的、不可逆的,需求的变更和调整,依旧不方 IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准的定义:从产品内部看,缺陷是软件产品开发或维护过程中存在的错误、毛病等各种问题;从产品外部看,缺陷是系统所需要实现的某种功能的失效或违背。 符合下面4个条件之一就是缺陷: -1. 软件未达到规格说明书中规定的功能。 -2. 软件出现了产品说明书中指明的不会出现的错误。 -3. 软件功能超出了产品说明书中指明的范围。 +1. 软件未达到规格说明书中规定的功能; +2. 软件出现了产品说明书中指明的不会出现的错误; +3. 软件功能超出了产品说明书中指明的范围; 4. 软件难于理解,不易使用,运行速度慢,或者最终用户认为软件使用效果不好。 #### 1.4.2 产生原因 -1. 软件本身复杂性,产生大量不确定因素。 -2. 成本、时间限制,导致流程不够完善,文档缺失,缺乏严谨的评审。 -3. 人员本身技能水平、责任心、交流沟通不顺畅。 +1. 软件本身复杂性,产生大量不确定因素; +2. 成本、时间限制,导致流程不够完善,文档缺失,缺乏严谨的评审; +3. 人员本身技能水平、责任心、交流沟通不顺畅; 4. 不全面或者没有复审。 #### 1.4.3 缺陷来源 @@ -356,11 +356,11 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 #### 1.4.6 跟踪流程 最优化、最简单的生命周期是:(理想情况) -1. 测试员发现缺陷并记录缺陷报告。 -2. 缺陷报告交给程序员,此时缺陷状态是打开。(open state) -3. 程序员修改缺陷,此时缺陷状态是解决。(resolved state) -4. 缺陷报告交还测试员。 -5. 测试员确认已修复。 +1. 测试员发现缺陷并记录缺陷报告; +2. 缺陷报告交给程序员,此时缺陷状态是打开;(open state) +3. 程序员修改缺陷,此时缺陷状态是解决;(resolved state) +4. 缺陷报告交还测试员; +5. 测试员确认已修复; 6. 测试员关闭缺陷报告,此时缺陷状态是关闭。(closed state) 一个缺陷很可能会被反复打开→关闭。在日常工作过程中,由于开发修订其他缺陷影响、需求变更等因素缺陷可能会被反复打开→关闭。 @@ -378,26 +378,26 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 | 不能重现 | 开发不能复现这个缺陷,需要测试人员检查缺陷发现步骤 | #### 1.4.7 缺陷记录内容 -1. bug编号:bug的唯一id,以方便尽快找到此bug。 -2. bug标题:bug摘要,阐述bug大体内容。 -3. bug严重级别,优先级:作为缺陷是否修复以及缺陷修复优先级的决定性因素。 -4. bug产生的模块:记录bug所属模块,方便开发定位问题。 -5. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题。 -6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果。 +1. bug编号:bug的唯一id,以方便尽快找到此bug; +2. bug标题:bug摘要,阐述bug大体内容; +3. bug严重级别,优先级:作为缺陷是否修复以及缺陷修复优先级的决定性因素; +4. bug产生的模块:记录bug所属模块,方便开发定位问题; +5. bug对应的版本:bug对应的软件版本,方便后续的统计归档以及开发定位问题; +6. bug描述:bug的产生环境、详细步骤、期望结果、实际结果; 7. 附件:包括但不仅限于截图、日志、录像、所用到的示例文件以及应用;同样是方便复现解决缺陷的。 以上是上报bug、创建bug必须要做的,在后续我们还会对bug进行修复、复测等工作,那么为了记录后续工作,bug还应该包含: -1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到。 -2. bug修订人:bug修订人员。 -3. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人。 -4. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等。 -5. bug复测说明:由复测人员来写,说明复测过程,复测结果等。 +1. bug状态:开始、修复中、修复完成、提测、测试中、测试通过/失败、关闭等,后续bug周期中会讲到; +2. bug修订人:bug修订人员; +3. bug复测人:通常是谁报的bug最后返回给谁测试,但是在某些情况下比如bug报告人任务积累太多/不在的情况下也会分给其他人,所以通常会记录bug复测责任人; +4. bug修订说明:由bug修订人来写,说明bug产生原因,修改思路等; +5. bug复测说明:由复测人员来写,说明复测过程,复测结果等; 6. bug备注:备注,以便记录一些额外信息。 #### 1.4.8 缺陷预防 -**差错:**人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误。(产生根源) -**错误:**软件内部问题,设计错误、编码错误。(内部原因) +**差错:**人在理解和解决问题的思维和行为过程中出现的问题,沟通不当,理解错误;(产生根源) +**错误:**软件内部问题,设计错误、编码错误;(内部原因) **失效:**软件系统运行时偏离了用户需求。(外部表现) ### 1.5 软件测试行业 @@ -411,14 +411,14 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 从国内软件公司软件测试部门的独立性来看,多数软件企业没有专门的测试技术部门,软件测试程序也不太规范,多数企业也不懂测试,对测试的投入资金过少。大多数是在经过简单地测试之后,就认为是没有问题了,就交于用户了,让用户去“测试”。于是,软件产品在没有经过严格测试的情况下就发布了。对国内消费类软件而言,经常出现一些已经推向市场的产品由于被发现有严重缺陷而导致大量退货的现象。定制的行业软件,常出现一再返工、无限期的修改和维护的现象。 当前国内软件测试行业主要存在以下问题: -1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题。 -2. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步。 -3. 对于分布式系统整体性能还难以进行很好的测试。 -4. 对于实时系统缺乏有效的测试手段。 -5. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题。 -6. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合。 -7. 缺乏软件测试意识、对其重视不够。 -8. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准。 +1. 软件规模越来越大,功能越来越复杂,如何进行充分而有效的测试成为难题; +2. 面向对象的开发技术越来越普及,但是面向对象的测试技术却刚刚起步; +3. 对于分布式系统整体性能还难以进行很好的测试; +4. 对于实时系统缺乏有效的测试手段; +5. 随着安全问题的日益突出,信息系统的安全性如何进行有效的测试与评估,成为世界性的难题; +6. 测试的自动化程度不高,手工测试过多,自动化测试工具和手工测试人员也缺乏较好的结合; +7. 缺乏软件测试意识、对其重视不够; +8. 在软件开发基本完成后才进行测试,也缺乏软件测试的统一标准; 9. 高校从师资储备到专业设置再到人才培养的机制薄弱。 国内外软件测试差距 @@ -549,19 +549,19 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 2.2 测试的目的和原则 #### 2.2.1 测试的目的 -1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进。 -2. 检测产品是否符合用户要求。 -3. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法。 +1. 测试不仅仅是找出错误。通过分析错误产生的原因和错误的发展趋势,可以帮助项目管理者发现当前软件开发过程中的缺陷,以便即时改进; +2. 检测产品是否符合用户要求; +3. 没有发现错误的测试也是有价值的,完整的测试是评定软件质量的一种方法; 4. 提升用户体验。 #### 2.2.2 测试的原则 -1. 软件测试是证伪而非证实。 -2. 尽早地、不断地进行测试。 -3. 重视无效数据和非预期的测试。 -4. 应当对每一个测试结果做全面的检查。 -5. 测试现场保护和资料归档。 -6. 程序员应避免检查自己的程序。 -7. 充分注意测试中的集群现象。 +1. 软件测试是证伪而非证实; +2. 尽早地、不断地进行测试; +3. 重视无效数据和非预期的测试; +4. 应当对每一个测试结果做全面的检查; +5. 测试现场保护和资料归档; +6. 程序员应避免检查自己的程序; +7. 充分注意测试中的集群现象; 8. 用例要定期评审,适时补充修改用例。 ### 2.3 测试分类 @@ -610,10 +610,10 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 选择测试用例是软件测试员最重要的一项任务,不正确的选择可能导致测试量过大或者过小,甚至测试目标不对。准确评估风险,把无穷尽的可能性减少到可以控制的范围是软件测试成功的诀窍。 #### 2.4.2 测试用例的作用 -1. 指导测试的实施 -2. 评估测试结果的度量基准 -3. 保证软件的可维护性和可复用性 -4. 分析缺陷的标准 +1. 指导测试的实施; +2. 评估测试结果的度量基准; +3. 保证软件的可维护性和可复用性; +4. 分析缺陷的标准。 #### 2.4.3 测试用例设计准则 1. 有效性 @@ -637,50 +637,50 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 11. 非法用户:没有注册过;注册过但是用户名/密码不匹配的;本文特指未注册过的用户 测试用例维护一般分为以下几种情况: -1. 产品特性没变:漏测或者环境变更,这个时候版本没变,测试用例增加和修改均可 -2. 原有特性变化:功能变化,只能新增,不能修改,还要兼容老版本 -3. 原有功能取消:测试用例在新版本上置为“空”标志或者“无效状态”,对于先前版本有效 -4. 新增功能:新增用例,对应新版本标志 +1. 产品特性没变:漏测或者环境变更,这个时候版本没变,测试用例增加和修改均可; +2. 原有特性变化:功能变化,只能新增,不能修改,还要兼容老版本; +3. 原有功能取消:测试用例在新版本上置为“空”标志或者“无效状态”,对于先前版本有效; +4. 新增功能:新增用例,对应新版本标志。 #### 2.4.5 测试用例设计误区 -1. 测试用例设计等同于测试输入数据设计 -2. 测试用例设计越详细越好 -3. 追求测试用例设计“一步到位” -4. 将多个测试条件混在一个用例中 +1. 测试用例设计等同于测试输入数据设计; +2. 测试用例设计越详细越好; +3. 追求测试用例设计“一步到位”; +4. 将多个测试条件混在一个用例中。 ### 2.5 测试停止标准 #### 2.5.1 软件测试停止总体标准 -1. 测试超过了预定时间 -2. 执行了所有的测试用例,并没有发现故障 -3. 使用特定的测试用例设计方法作为判断测试停止的基础 -4. 给出测试停止的要求 -5. 根据经单位时间内查出故障的数量决定是否停止测试 -6. 软件系统经过了单元、集成、系统测试,分别达到停止标准。通过验收测试,得出验收测试结论。 -7. 软件项目暂停以进行调整,测试应随之暂停,并备份暂停点数据。或者软件项目开发生命周期内出现重大估算、进度偏差,需暂停或终止时,测试应随之暂停或终止,并备份数据 +1. 测试超过了预定时间; +2. 执行了所有的测试用例,并没有发现故障; +3. 使用特定的测试用例设计方法作为判断测试停止的基础; +4. 给出测试停止的要求; +5. 根据经单位时间内查出故障的数量决定是否停止测试; +6. 软件系统经过了单元、集成、系统测试,分别达到停止标准。通过验收测试,得出验收测试结论; +7. 软件项目暂停以进行调整,测试应随之暂停,并备份暂停点数据。或者软件项目开发生命周期内出现重大估算、进度偏差,需暂停或终止时,测试应随之暂停或终止,并备份数据。ß #### 2.5.2 软件测试各阶段停止标准 ##### 单元测试停止标准 -1. 单元测试用例已经通过评审 -2. 按照单元测试计划完成了所有规定单元测试 -3. 达到了测试计划中关于单元测试所规定的覆盖率要求 -4. 被测试的单元每千行代码必须发现至少3个错误 -5. 软件单元功能与设计一致 -6. 单元测试中发现的错误已经得到修改,各级缺陷修复率达到标准 +1. 单元测试用例已经通过评审; +2. 按照单元测试计划完成了所有规定单元测试; +3. 达到了测试计划中关于单元测试所规定的覆盖率要求; +4. 被测试的单元每千行代码必须发现至少3个错误; +5. 软件单元功能与设计一致; +6. 单元测试中发现的错误已经得到修改,各级缺陷修复率达到标准。 ##### 集成测试停止标准 -1. 集成测试用例已经通过评审 -2. 按照集成测试计划和增量集成策略完成了整个系统的集成测试 -3. 达到了测试计划中关于集成测试所规定的覆盖率要求 -4. 被测试的集成工作版本每千行代码必须发现至少2个错误 -5. 集成工作版本满足设计定义的各项功能、性能要求 -6. 在集成测试中发现的错误已经得到修改,各级缺陷修复率达到标准 +1. 集成测试用例已经通过评审; +2. 按照集成测试计划和增量集成策略完成了整个系统的集成测试; +3. 达到了测试计划中关于集成测试所规定的覆盖率要求; +4. 被测试的集成工作版本每千行代码必须发现至少2个错误; +5. 集成工作版本满足设计定义的各项功能、性能要求; +6. 在集成测试中发现的错误已经得到修改,各级缺陷修复率达到标准。 ##### 系统测试停止标准 -1. 系统测试用例已经通过评审 -2. 按照系统测试计划完成了系统测试 -3. 达到了测试计划中关于系统测试所规定的覆盖率要求 -4. 被测试的系统每千行代码必须发现至少1个错误 -5. 系统测试满足设计需求规格说明书要求 -6. 在系统测试中发现的错误已经得到修改,各级缺陷修复率达到标准 +1. 系统测试用例已经通过评审; +2. 按照系统测试计划完成了系统测试; +3. 达到了测试计划中关于系统测试所规定的覆盖率要求; +4. 被测试的系统每千行代码必须发现至少1个错误; +5. 系统测试满足设计需求规格说明书要求; +6. 在系统测试中发现的错误已经得到修改,各级缺陷修复率达到标准。 ### 2.6 知识点总结 1. 软件测试的目的和原则 @@ -697,11 +697,11 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 黑盒测试从用户的角度出发,以输入数据与输出数据的对应关系进行测试,数据驱动。 黑盒测试注重测试软件的功能需求,主要视图发现下列几类错误 -1. 功能不正确或遗漏 -2. 界面错误 -3. 数据库访问错误 -4. 性能错误 -5. 初始化和终值错误 +1. 功能不正确或遗漏; +2. 界面错误; +3. 数据库访问错误; +4. 性能错误; +5. 初始化和终值错误。 ### 3.2 等价类划分 等价类是指某个输入域的子集合。在该子集合中,测试某等价类的代表值就等于对这类其他值的测试,对于揭露程序的错误是等效的。 @@ -713,17 +713,17 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 无效等价类:和有效等价类相反,是指对程序的规格说明无意义、不合理的输入数据构成的集合。 #### 3.2.1 划分原则 -1. 在输入条件规定了取值范围的情况下,可以确立一个有效等价类(在取值范围之内)和两个无效等价类(小于取值范围和大于取值范围)。 -2. 在输入条件规定了取回个数的情况下,可以确立一个有效等价类(在取值个数范围之内)和两个无效等价类(小于取值个数和大于取值个数)。 -3. 在输入条件规定了输入值的集合的情况下,可以确立一个有效等价类和一个无效等价类。 -4. 在输入条件规定了“必须如何”条件的情况下,可以确立一个有效等价类和一个无效等价类。 -5. 在输入条件是一个布尔值的情况下,可以确立一个有效等价类和一个无效等价类。 -6. 在规定了输入数据的一组值(假定n个),并且程序要对每一个输入值分别处理的将情况下,可以确立n个有效等价类和一个无效等价类。 -7. 在规定了输入数据必须遵守规则的情况下,可以确立一个有效等价类(符合规则)和若干个无效等价类(从不同角度违反规则)。 +1. 在输入条件规定了取值范围的情况下,可以确立一个有效等价类(在取值范围之内)和两个无效等价类(小于取值范围和大于取值范围); +2. 在输入条件规定了取回个数的情况下,可以确立一个有效等价类(在取值个数范围之内)和两个无效等价类(小于取值个数和大于取值个数); +3. 在输入条件规定了输入值的集合的情况下,可以确立一个有效等价类和一个无效等价类; +4. 在输入条件规定了“必须如何”条件的情况下,可以确立一个有效等价类和一个无效等价类; +5. 在输入条件是一个布尔值的情况下,可以确立一个有效等价类和一个无效等价类; +6. 在规定了输入数据的一组值(假定n个),并且程序要对每一个输入值分别处理的将情况下,可以确立n个有效等价类和一个无效等价类; +7. 在规定了输入数据必须遵守规则的情况下,可以确立一个有效等价类(符合规则)和若干个无效等价类(从不同角度违反规则); 8. 在确知已划分的等价类中各元素在程序处理中的方式不同的情况下,则应再将改等价类进一步划分为更小的等价类。 #### 3.2.2 设计测试用例步骤 -1. 形成等价类表,每一等价类规定一个唯一编号 -2. 设计测试用例,使其尽可能多的覆盖尚未覆盖的有效等价类 +1. 形成等价类表,每一等价类规定一个唯一编号; +2. 设计测试用例,使其尽可能多的覆盖尚未覆盖的有效等价类; 3. 设计一个新的测试用例,使其只覆盖一个无效等价类,重复这一步直到所有无效等价类均被覆盖。 #### 3.2.3 等价类举例 我们要测试学习成绩这一输入框(假设总成绩都是100),那么我们就可以如下图划分,有效的成绩是>=0且<=100的,无效的是<0和>100这两部分。 @@ -737,7 +737,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 2. 无效等价类1:小于0的负数,比如:-1; 3. 无效等价类2:大于100的数,比如:121; 4. 无效等价类3:其他任意非数字字符,比如:a、你、\; -5. 无效等价类4:空字符 +5. 无效等价类4:空字符。 **等价类最终必须是分割到最小单位,只有这样才能保障测试覆盖全面。** @@ -751,16 +751,16 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 边界值分析法是等价类划分法的补充。顾名思义,边界值分析法是对输入的边界值进行测试。从实践中我们可以发现,人们无论是在生活中还是在工作中往往会忽略边界值的条件,所以在输入或者输出的边界上会发生大量的错误。因此,在测试用例设计中,需要对输入的条件进行分析并且提取其中的边界值条件,通过对这些边界值的测试来查出更多的错误。 常见的边界值: -1. 文本框接受字符个数,比如用户名长度、密码长度等。 -2. 报表的第1行和最后1行。 -3. 数组元素的第1个和最后1个。 +1. 文本框接受字符个数,比如用户名长度、密码长度等; +2. 报表的第1行和最后1行; +3. 数组元素的第1个和最后1个; 4. 循环的第1次、第2次和倒数第1次、最后1次。 #### 3.3.1 设计原则 -1. 如果输入条件规定了值的范围,则应取刚达到这个范围边界的值,以及刚刚超越这个范围边界的值作为测试输入数据。 -2. 如果输入条件规定了值的个数,则用最大个数、最小个数、比最小个数少1、比最大个数多1的数作为测试数据。 -3. 如果规格说明书给出的输入域或输出域是有序集合,则应选取集合的第1个元素和最后1个元素作为测试用例。 -4. 如果程序中使用了内部数据结构,则应选择内部数据结构边界上的值作为测试用例。 +1. 如果输入条件规定了值的范围,则应取刚达到这个范围边界的值,以及刚刚超越这个范围边界的值作为测试输入数据; +2. 如果输入条件规定了值的个数,则用最大个数、最小个数、比最小个数少1、比最大个数多1的数作为测试数据; +3. 如果规格说明书给出的输入域或输出域是有序集合,则应选取集合的第1个元素和最后1个元素作为测试用例; +4. 如果程序中使用了内部数据结构,则应选择内部数据结构边界上的值作为测试用例; 5. 分析规格说明,找出其他可能的边界条件。 #### 3.3.2 两类方法 1. 一般边界值分析 @@ -776,7 +776,7 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 > 选取的边界值数据应该包括: > -> -1,0,1,59,60,61,79,80,81,99,100,101 +> -1、0、1、59、60、61、79、80、81、99、100、101 通常情况下,软件测试所包含的边界检验有以下几种类型:数字、字符、位置、质量、大小、速度、方位、尺寸、空间等,而相应地,这些类型的边界值应该在最大/最小,首位/末尾,上/下,最快/最慢,最高/最低,最短/最长,空/满等情况下。 @@ -796,9 +796,9 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 等价类划分法和边界值分析法只是孤立地考虑各个输人数据的测试效果,没有考虑输入数据的组合及其相互制约关系,而决策表考虑了多种条件的组合情况。决策表又称为判定表,分析多种逻辑条件(if-else、switch-case等)与执行之间的关系。 决策表由4部分组成: -1. 条件桩:列出了问题的所有条件,通常认为列出的条件次序无关紧要。 -2. 动作桩:列出了问题规定可能采取的操作,这些操作的排列顺序没有约束。 -3. 条件项:列出针对条件桩的取值,在所有可能情况下的真假值。 +1. 条件桩:列出了问题的所有条件,通常认为列出的条件次序无关紧要; +2. 动作桩:列出了问题规定可能采取的操作,这些操作的排列顺序没有约束; +3. 条件项:列出针对条件桩的取值,在所有可能情况下的真假值; 4. 动作项:列出在条件项的各种取值情况下应该采取的动作。 规则:任何条件组合的特定取值及其相应要执行的操作。在决策表中贯穿条件项和动作项的列就是规则。显然,决策表中列出多少条件取值,也就有多少规则,条件项和动作项就有多少列。 @@ -808,26 +808,26 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 所有条件都是逻辑结果(即真/假、是/否、0/1)的决策表称为有限条件决策表。如果条件有多个值,则对应的决策表叫做扩展条目决策表。决策表设计测试用例,条件解释为输入,动作解释为输出。 决策表适合以下特征的应用程序: -1. if-then-else分支逻辑突出。 -2. 输入变量之间存在逻辑关系。 -3. 涉及输入变量子集的计算。 -4. 输入和输出之间存在因果关系。 +1. if-then-else分支逻辑突出; +2. 输入变量之间存在逻辑关系; +3. 涉及输入变量子集的计算; +4. 输入和输出之间存在因果关系; 5. 很高的圈复杂度。 #### 3.4.1 应用举例 决策表(判定表)设计测试用例的具体步骤如下: -1. 确定规则的个数。假如有n个条件,每个条件有两个取值(0,1),故有2种规则。 -2. 列出所有的条件桩和动作桩。 -3. 填入条件项。 -4. 填入动作项,得到初始判定表。 -5. 简化,合并相似规则(相同动作)。 +1. 确定规则的个数。假如有n个条件,每个条件有两个取值(0,1),故有2种规则; +2. 列出所有的条件桩和动作桩; +3. 填入条件项; +4. 填入动作项,得到初始判定表; +5. 简化,合并相似规则(相同动作); 简化就是合并多条具有相同的动作的规则,并且其条件项之间存在极为相似的关系。 ![简化规则](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/juecebiao2.jpg) 需求:输入三边值,判定是哪种三角形:非三角形、不等边三角形、等腰三角形、等边三角形 -1. 绘制初始三角形判定决策表 -2. 优化1的产出 -3. 设计测试用例 +1. 绘制初始三角形判定决策表; +2. 优化1的产出; +3. 设计测试用例。 条件桩: * abc能构成三角形 @@ -874,10 +874,10 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 决策表把复杂问题的各种可能情况一一列出,易于理解。但是,决策表不能表达重复执行动作的缺点。 使用判定表设计测试用例的条件如下: -1. 规格说明以判定表形式给出,或很容易转换成判定表。 -2. 条件的排列顺序不会也不影响执行哪些操作。 -3. 规则的排列顺序不会也不影响执行哪些操作。 -4. 每当某一规则的条件已经满足,并确定要执行的操作后,不必检验别的规则。 +1. 规格说明以判定表形式给出,或很容易转换成判定表; +2. 条件的排列顺序不会也不影响执行哪些操作; +3. 规则的排列顺序不会也不影响执行哪些操作; +4. 每当某一规则的条件已经满足,并确定要执行的操作后,不必检验别的规则; 5. 如果某一规则得到满足要执行多个操作,这些操作的执行顺序无关紧要。 @@ -909,16 +909,16 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ![约束图](https://gitee.com/XiaFuXiangFei/software-testing/raw/main/images/yueshutu.png) -* E(互斥):原因不会同时成立,最多1个成立,可以都不成立 -* I(包含):原因中至少一个成立,不能同时为0 -* O(唯一):原因中有且只有一个成立 -* R(要求):原因中a出现,b必须出现,a=1则b=1,a=0的话,b随便。QQ登录的例子a为自动登录,b是记住密码 -* M(屏蔽):a为1时,b必须是0,a=1,则b=0,如果a=0,b随便 +* E(互斥):原因不会同时成立,最多1个成立,可以都不成立。 +* I(包含):原因中至少一个成立,不能同时为0。 +* O(唯一):原因中有且只有一个成立。 +* R(要求):原因中a出现,b必须出现,a=1则b=1,a=0的话,b随便。QQ登录的例子a为自动登录,b是记住密码。 +* M(屏蔽):a为1时,b必须是0,a=1,则b=0,如果a=0,b随便。 #### 3.5.2 设计因果图测试用例步骤 -1. 分析软件规格说明,哪些是原因(即输入条件或输入条件的等价类),哪些是结果(即输出条件),给每个原因和结果赋予标识符。 -2. 分析原因与结果之间、原因与原因之间对应的逻辑关系,用因果图表示。 -3. 由于语法或环境限制,有些原因与原因之间、原因与结果之间的组合情况不可能出现,在因果图上用一些记号表明这些特殊情况的约束或限制条件,把因果图转换为判定表。 +1. 分析软件规格说明,哪些是原因(即输入条件或输入条件的等价类),哪些是结果(即输出条件),给每个原因和结果赋予标识符; +2. 分析原因与结果之间、原因与原因之间对应的逻辑关系,用因果图表示; +3. 由于语法或环境限制,有些原因与原因之间、原因与结果之间的组合情况不可能出现,在因果图上用一些记号表明这些特殊情况的约束或限制条件,把因果图转换为判定表; 4. 从判定表的每一列产生出测试用例。 对于逻辑结构复杂软件,先用因果图进行图形分析,再用判定表进行统计,最后设计测试用例。当然,对于比较简单的测试对象,可以忽略因果图,直接使用决策表。 @@ -961,13 +961,13 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 **优点:** -1. 考虑多个输入之间的相互组合、相互制约的关系 -2. 指出需求规格说明书中存在的不完整性和二义性 -3. 帮助测试人员按照一定的步骤高效的开发测试用例 +1. 考虑多个输入之间的相互组合、相互制约的关系; +2. 指出需求规格说明书中存在的不完整性和二义性; +3. 帮助测试人员按照一定的步骤高效的开发测试用例。 **缺点:** -1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到 -2. 此方法得到的用例数量规模大 +1. 作为输入条件的原因和输出结果之间的因果关系,很难从规格说明书得到; +2. 此方法得到的用例数量规模大。 ### 3.6 场景法 通过尝尽该描述的业务流程(业务逻辑),设计用例来遍历场景(路径),验证系统功能的正确性。 场景法重点是测试流程,因此每个流程用一个用例验证即可,流程测试没问题不代表系统功能没问题,还需要单步进行测试,结合前面的方法。 @@ -1015,21 +1015,21 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 该方法强调的是对被测试软件的需求理解以及设计实现的细节把握,当然还有个人的能力。那么显而易见地,这个方法的缺点就是太过依赖个人能力,难以系统化。因此,这个方法一般是作为测试用例设计的补充,而不是单独用来设计测试用例。在回归测试中应用较多。 错误推测法一般采用如下技术: -1. 有关软件设计方法和实现技术。 -2. 有关前期测试阶段结果的知识。 -3. 测试类似或相关系统的经验,了解以前这些系统曾在哪些地方出现缺陷。 +1. 有关软件设计方法和实现技术; +2. 有关前期测试阶段结果的知识; +3. 测试类似或相关系统的经验,了解以前这些系统曾在哪些地方出现缺陷; 4. 典型的产生错误的知识,如被零除错误。 #### 3.7.2 优点和缺点 **优点:** -1. 不用设计等价类的测试用例,将多个等价类的测试合成一个随机测试,可以以较少代码实现测试代码的编写。 -2. 当等价类设计不确切或不完全时,测试会产生遗漏,而使用错误推测法则是按照概率进行等价类覆盖。不论存在多少个等价类,只要随机数据个数足够,就能保证各个等价类被覆盖的概率足够高,能够有效弥补等价类分法设计不充分的缺陷。 +1. 不用设计等价类的测试用例,将多个等价类的测试合成一个随机测试,可以以较少代码实现测试代码的编写; +2. 当等价类设计不确切或不完全时,测试会产生遗漏,而使用错误推测法则是按照概率进行等价类覆盖。不论存在多少个等价类,只要随机数据个数足够,就能保证各个等价类被覆盖的概率足够高,能够有效弥补等价类分法设计不充分的缺陷; 3. 采用错误推测法进行测试,每次执行测试时,测试的样本数据可能都不相同,执行次数愈多,错误暴露的概率愈大。 **缺点:** -1. 错误推测法中的随机数据很难覆盖到边界值,无法保证测试的充分性。 -2. 错误推测法进行自动化测试的难度较大。有些程序很难用程序来自动验证,这使得程序结果的验证工作难度变大。 -3. 当等价类的范围较小,这些范围较小的等价类被覆盖的概率也是很小的,错误推测法难以测试到。 +1. 错误推测法中的随机数据很难覆盖到边界值,无法保证测试的充分性; +2. 错误推测法进行自动化测试的难度较大。有些程序很难用程序来自动验证,这使得程序结果的验证工作难度变大; +3. 当等价类的范围较小,这些范围较小的等价类被覆盖的概率也是很小的,错误推测法难以测试到; 4. 随机测试不可以代替常规的功能或非功能测试,因为其随意性大,没有一套完整严格的方法且并非有章可循的测试技术。 #### 3.7.3 常见错误 @@ -1054,18 +1054,18 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 3.8 综合策略 黑盒测试方法有等价类划分、边界值分析、决策表、因果图、场景法、错误推测法等,每种测试方法都有其各自的特点和适用场合。 软件测试专家Myers给出了黑盒测试方法中各种测试方法的使用策略: -1. 在任何情况下都必须使用边界值分析方法。经验表明,用这种方法设计的测试用例发现程序错误的能力最强。 -2. 必要时使用等价类划分方法补充一些测试用例。 -3. 用错误推测法再追加一些测试用例。 -4. 对照程序逻辑,检查已设计出的测试用例的逻辑覆盖程度,如果没有达到要求的覆盖标准,应当再补充足够的测试用例。 +1. 在任何情况下都必须使用边界值分析方法。经验表明,用这种方法设计的测试用例发现程序错误的能力最强; +2. 必要时使用等价类划分方法补充一些测试用例; +3. 用错误推测法再追加一些测试用例; +4. 对照程序逻辑,检查已设计出的测试用例的逻辑覆盖程度,如果没有达到要求的覆盖标准,应当再补充足够的测试用例; 5. 如果程序的功能说明中含有输入条件的组合情况,则一开始就可选用因果图法。 对于功能性测试技术,可以根据如下条件进行选择: -1. 如果变量是独立的,则可以用定义域测试和等价类测试。 -2. 如果变量不是独立的,可采用决策表测试。 -3. 如果为单缺陷假设,则可采用边界值分析和健壮性测试。 -4. 如果为多缺陷假设,可采用最坏情况测试、健壮最坏情况测试和决策表测试。 -5. 如果程序包含大量例外处理,可采用健壮性测试和决策表测试。 +1. 如果变量是独立的,则可以用定义域测试和等价类测试; +2. 如果变量不是独立的,可采用决策表测试; +3. 如果为单缺陷假设,则可采用边界值分析和健壮性测试; +4. 如果为多缺陷假设,可采用最坏情况测试、健壮最坏情况测试和决策表测试; +5. 如果程序包含大量例外处理,可采用健壮性测试和决策表测试; 6. 如果变量引用的是逻辑量,可采用等价类测试用例和决策表测试。 ### 3.9 知识点总结 @@ -1104,7 +1104,12 @@ IEEE729-1983 (电气和电子工程师协会标准IEEE) 对缺陷有一个标准 ### 4.4 逻辑覆盖 逻辑测试,又称为控制流覆盖,是一种按照程序内部逻辑结构和编码结构设计测试用例的测试方法。目的是要测试程序中的语句,判定(控制流能够分解为不同路径的程序点),条件(形成判定的原子谓词)等。根据覆盖的标准不同,分为语句覆盖、判定覆盖、条件覆盖、条件判定覆盖、修正条件判定覆盖、增强条件判定覆盖、条件组合覆盖和路径覆盖等标准。 - +#### 4.4.1 语句覆盖 +#### 4.4.2 判定覆盖 +#### 4.4.3 条件覆盖 +#### 4.4.4 条件判定覆盖 +#### 4.4.5 +#### 4.4.6 ### 4.5 路径分析 ### 4.6 控制结构测试 ### 4.7 数据流测试 -- Gitee From 0f949572c7ab2076e2dbc691c6c12ddbb6951fb2 Mon Sep 17 00:00:00 2001 From: xiafuxiangfei Date: Sun, 19 Sep 2021 23:34:51 +0800 Subject: [PATCH 29/30] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E6=8A=A5=E5=91=8A?= =?UTF-8?q?=E6=A8=A1=E6=9D=BF=E5=88=9D=E7=A8=BF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .DS_Store | Bin 6148 -> 6148 bytes ...5\345\221\212\346\250\241\346\235\277.doc" | Bin 0 -> 92672 bytes 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 "\346\265\213\350\257\225\347\233\270\345\205\263\346\226\207\346\241\243\346\250\241\346\235\277/\346\265\213\350\257\225\346\212\245\345\221\212\346\250\241\346\235\277.doc" diff --git a/.DS_Store b/.DS_Store index f164f471049cc4843ce648fc54f74f0a1c69533f..e357c7811c6aacb9bef18bc859ae65db276f6bab 100644 GIT binary patch delta 190 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 Date: Mon, 20 Sep 2021 00:14:34 +0800 Subject: [PATCH 30/30] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E6=8A=A5=E5=91=8A?= =?UTF-8?q?=CE=B1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...5\345\221\212\346\250\241\346\235\277.doc" | Bin 0 -> 162 bytes ...5\345\221\212\346\250\241\346\235\277.doc" | Bin 92672 -> 239616 bytes 2 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 "\346\265\213\350\257\225\347\233\270\345\205\263\346\226\207\346\241\243\346\250\241\346\235\277/~$\346\265\213\350\257\225\346\212\245\345\221\212\346\250\241\346\235\277.doc" diff --git "a/\346\265\213\350\257\225\347\233\270\345\205\263\346\226\207\346\241\243\346\250\241\346\235\277/~$\346\265\213\350\257\225\346\212\245\345\221\212\346\250\241\346\235\277.doc" "b/\346\265\213\350\257\225\347\233\270\345\205\263\346\226\207\346\241\243\346\250\241\346\235\277/~$\346\265\213\350\257\225\346\212\245\345\221\212\346\250\241\346\235\277.doc" new file mode 100644 index 0000000000000000000000000000000000000000..3e47a945653c04a02ddd13bd4d8b5cefe4be4a72 GIT binary patch literal 162 zcmd;%%1^CSaL!0A%}Zw>8gMg2G2}C(GE_1sFgP=009mCBc?=)}QW=UEiW&47s-W`v z4CO#p5kodm%!t7Nhz)^yUgVYMDlp{tfAjOsz1pqM5DZk4#!v!On+Q~!$`As?#Xx>0 G&{O~tycA>VxMiD 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

lKn7uo|4Q_%Apd@Gm%?AVnxV&QS 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

_qx9-pXFaF{$!jw>});B#e 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 z℘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 delta 18389 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 CPSc?P -- Gitee