精华内容
下载资源
问答
  • 随着软件测试的发展,自动化测试技术也得到了很大提高。 本文首先介绍了自动化测试的概念、分类和现状,并分别不同端上的自动化测试实现原理进行了详细地分析和阐述,通过目前主流的一些自动化测试框架和工具的...

    前言:

    软件测试作为软件生命周期中不可缺少的组成部分,对提高软件质量起着重要作用。随着软件测试的发展,自动化测试技术也得到了很大提高。

    本文首先介绍了自动化测试的概念、分类和现状,并分别对不同端上的自动化测试实现原理进行了详细地分析和阐述,通过对目前主流的一些自动化测试框架和工具的比较,指出了当前不同端上实施自动化测试的痛点和困难。

    最后通过由数据驱动的自动化测试向关键词驱动的自动化测试的探索,进而由传统模式下的自动化测试转向基于AI的自动化测试的摸索,对自动化测试的未来进行了展望。

    一、自动化测试的概念

    自动化测试是把以人为驱动的测试行为转化为机器执行的一种过程。

    二、适用自动化测试的项目特征

    三、软件测试的分类

    1、按项目流程:单元测试、集成测试、系统测试、回归测试、验收测试

    2、按技术:黑盒测试、白盒测试、灰盒测试

    3、按功能:逻辑功能测试、界面测试、易用性测试、安装测试、兼容性测试

    4、按性能:时间性能测试、空间性能测试

    5、按自动化:功能自动化、性能自动化

    项目流程 + 自动化 → 分层测试:unit测试(单元测试)、service测试(接口测试)、UI测试

    四、自动化测试的现状

    1、单元测试(极限编程-测试驱动开发),占比70%
    (1)对软件中最小可测试单元进行检查和验证
    (2)由开发人员编写,检验测试单元的语义是否正确
    (3)一般在构建阶段执行自动化测试脚本
    (4)代表工具:XUnit等

    2、接口测试,占比20%
    (1)测试系统组件间接口的测试
    (2)主要是保证接口的正确和稳定
    (3)代表工具:Jmeter、Postman等

    3、UI测试,占比10%
    (1)验证布局是否合理、风格是否一致等等
    (2)确保UI功能内部的对象符合预期
    (3)代表工具:selenium、robot framework等

    4、小结
    (1)单元测试借助对应语言的测试框架,可以做到在构建时执行测试脚本,难度较小
    (2)接口测试通过定义好每个用例的输入和输出,借助接口测试工具,也可以实现自动化,难度不大
    (3)UI测试更多是与界面渲染相关的,包括元素的位置、大小是否正确,元素内容是否正确等等,主要是对界面渲染后的结果进行测试

    五、不同端上的UI自动化测试

    要判断渲染界面是否满足预期,首先就需要具备操控终端界面的能力,通过定位元素获取元素的信息与预期结果比较。

    注意:这仅仅属于功能性测试的范畴,如果包括多媒体内容的话,还需要借助其他手段进行比较。

    而操控终端界面的能力也随终端的不同而不同,这里主要是PC端和移动端的区别。

    1、PC端:

    每个浏览器厂商都会提供相应的driver,它们都实现了Selenium定义的WebDriver's wire protocol,通过这个协议可以操控浏览器做任何事情!

    这个driver会启动基于这个协议的web服务,实际上就是在一个端口上监听http请求,根据不同的请求执行不同的操作。

    代表框架:

    以Selinium为例,实现原理如下:

    2、移动端:

    与PC端上原理类似,但又有Android与IOS的区别

    Android:主要基于UIAutomator和UIAutomator2,更早的可以追溯到instrumentation框架。
    (1)instrumentation可以把测试包和目标测试app加载到同一个进程中运行,以此实现对app的控制。

    之后封装形成Selendroid架构

    (2)UIAutomator是谷歌在Android4.1版本发布时推出的基于Java编写的UI测试框架,与Bootstrap配合使用。
    其特点是可以跨进程操作,可以获取屏幕上任意一个app的任意一个控件属性并对其操作。
    但不足的是只能用Java编写,且测试脚本必须上传到设备上运行。

    (3)UIAutomator2修复了原有版本的bug,还增加了很多新功能

    1.设备和开发机可以脱离数据线,通过WiFi互联(基于atx-agent)

    2.集成了openstf/minicap达到实时屏幕投频,以及实时截图

    3.集成了openstf/minitouch达到精确实时控制设备

    4.修复了xiaocong/uiautomator经常性退出的问题

    5.代码进行了重构和精简,方便维护

    6.实现了一个设备管理平台(也支持iOS) atxserver2

    IOS:主要基于UIAutomation,Xcode 7之后引入UITesting

    (1)通过UIAutomation操作app时,UIAutomation会给app发送WM_GETOBJECT的消息

    如果app处理WM_GETOBJECT消息,实现了UIAutomation Provider,并调用了下面的函数,则该app支持UiaReturnRawElementProvider(HWND hwnd, WPARAM wparam, LPARAM lparam, IRawElementProviderSimple *el)IRawElementProviderSimple就是UIAutomation Provider,包含了控件的各种信息,如Name,ClassName,坐标等。

    因此,app想要支持自动化,就必须实现UIAutomation Provider,详情请参看《UI Automation Client Programmer's Guide

    (2)UITesting是苹果公司推出,在Xcode 7引入的UI自动化测试框架,其原理利用了IOS的Accessibility

    1.Xcode 自带,不需要搭建环境

    2.支持 OC、Swift,学习成本低

    3.支持 WebView 测试

    4.稳定性好

    六、常用的移动端自动化测试框架

    下图列举了一部分测试框架在一些指标上的表现,除了这些,还有Robot framework、阿里的macaca框架等也可以考虑。

    七、移动端自动化测试的具体实现

    一千个嘴把式,不如lai个手把式!

    下面这一段自动化测试脚本代码基于Appium实现了在app里截屏的功能:

    当然,除了写好测试脚本以外,还有很多工作需要准备

    1. usb要连接好设备,设备需要打开开发者模式

    2. 安装好目标测试app的debug包

    3. 检查chromeDriver的驱动版本是否与设备匹配

    4. 可能遇到其他未知问题......

    下面是基于Robot framework的自动化测试脚本片段

    八、移动端自动化测试的探索

    1、基于数据驱动的自动化测试 →  基于关键字驱动的自动化测试。

    从以上具体实现中可以看出,要针对一个测试用例编写出对应的测试脚本,这需要的代码量不算少,并且还需要对每个方法的定义和输入输出十分熟悉。

    因此,要实现UI层面的自动化测试,成本很高,甚至超过了收益。

    所以,如果可以让测试脚本的编写变的简单,那么将大大改善现状。

    2、探索

    仔细观察上述具体实现,可以发现,一个测试脚本是可以由多个测试用例组成,而每一个测试用例又可以是由多条语义清晰的指令构成的。

    于是这就可以考虑对其进行抽象,这也是策略模式的一种具体应用,主要包括三个方面:

    1.界面元素名与测试内部对象名的分离。

    将界面上的所有元素映射成相对应的一个逻辑对象,测试针对这些逻辑对象进行,界面元素的改变只会影响映射表,而不会影响测试。

    2.测试描述与具体实现细节的分离,把测试描述和测试的具体实现细节分离开来。

    测试描述只说明软件测试要做什么以及期待什么样的结果,而不管怎样执行测试或怎样证实结果。

    这样做是因为测试的实现细节通常与特定的平台以及特定的测试执行工具有着密切的联系。

    这种分离使得测试描述对于应用实现细节是不敏感的,而且有利于测试在工具和平台间的移植。

    3.脚本与数据的分离。

    把测试执行过程中所需的测试数据从脚本中提取出来,在运行时测试脚本再从数据存放处读取预先定制好的数据,这样脚本和数据可以独立维护,如果对软件测试、接口测试、自动化测试、面试经验交流。感兴趣可以加测试交流群:829792258,还会有同行一起技术交流。

    九、移动端UI自动化测试的展望

    一个完整的移动端UI自动化流程应该是包括功能和视觉两部分内容的。

    在功能方面,尽管利用一些主流框架可以实现自动化,但编写脚本的成本依然很大并且很复杂。

    在视觉方面,更是需要依赖图像识别、图像相似度匹配、音频匹配等等技术手段。

    所以,目前针对移动端UI的自动化测试还是困难重重,并没有一个成熟的解决方案。

    展开全文
  • 谈谈对软件开发的理解

    千次阅读 2018-03-15 20:38:10
    我当时笔试时自己只写了软件开发流程软件开发流程:1.需求分析2.系统总体设计3.系统详细设计4.编码5.测试6.软件交付7.验收8.维护

    我当时笔试时自己只写了软件开发的流程

    软件开发流程:

    1.需求分析

    2.系统的总体设计

    3.系统的详细设计

    4.编码

    5.测试

    6.软件交付

    7.验收

    8.维护

    展开全文
  • 谈谈软件测试的氛围

    2013-02-22 21:49:04
    软件测试项目是否成功很大程度取决于整个团队中质量控制的理解,以及测试气氛的形成。一个合适的测试氛围帮组整个团队朝着解决问题的方向前进。不合适的软件测试氛围,会导致很多问题,例如过多的纠缠于指标(代码...

    http://blogs.msdn.com/b/cheno/archive/2009/10/01/9901654.aspx

     

    软件测试项目是否成功很大程度取决于整个团队中对质量控制的理解,以及测试气氛的形成。一个合适的测试氛围帮组整个团队朝着解决问题的方向前进。不合适的软件测试氛围,会导致很多问题,例如过多的纠缠于指标(代码覆盖率,自动化率等),相互推托责任等。很多因素影响整个项目组的测试气氛。以下就是几个我觉得非常重要的。

    1)测试组的组织结构
    不同的公司、项目都有不同的测试组织结构,有的扁平一些,有的不严格区分开发与测试人员。这些差异性对项目的测试都是有直接的影响。举例来说,微软比较典型的测试组织为SDET->Test Lead->Test Mgr->Test Director,然后PM/Dev/Test组织再统一汇报到一个大老板。(详见 HWTSaM)这种组织结构优点是,测试组织独立性较好,测试经验容易得到分享。另外也有一些组织,Test Lead/Dev Lead/PM Lead 直接汇报给Group Manager。这种结构的灵活性强,适合快节奏的项目,以及Agile的开发模式。

    2)测试人员的不同背景(Diversity)
    测试不仅仅需要很多创新和新鲜的想法,同时也往往需要丰富的经验去开展有效的测试活动。所以,一个好的测试团队,我理解应该是多元化的背景。举例来说,当测试一个应用软件时,一个有美工背景的测试人员必定会关注软件的界面的美观和合理性。一个有安全背景的人,必定会更多考虑软件的可靠和安全。这些不同的背景的人,在一起才能更多程度提高测试的覆盖率。这些不同背景的测试人员可以相互学习,共同促进。

    3) 管理人员的领导力和风格
    一个测试组的氛围,很大程度受到测试管理人员的影响。管理层处理质量问题的方式,也直接影响执行层的工作。质量管理大师朱兰曾经总结一个80/20规律,他认为80%的质量问题是由于管理人员管理不当造成的,而真正由于基础执行导致的质量问题只有20%。管理人员对软件质量的理解,以及传递给执行层的信息,都直接关系到测试的氛围。这里,我想强调的是,管理人员不仅仅包括测试的管理人员,还包括开发的管理人员以及项目经理等。Adam Goucher在他的博客中也提到了对质量影响最大的是项目经理,而非测试或则开发人员。

    4) 对于共同目标的认可
    在实际当中,很多测试人员将质量作为唯一的目标,开发人员将完成功能/解决Bug作为唯一目标,项目经理将产品的新功能作为唯一目标。但是从另外一个角度来看,其实满足客户的需求才是三个领域(开发,测试,项目经理)共同的目标,因此三个领域如何快速合作、如何以共同目标为重也对测试的气氛也有很大影响。有时候,这个共同目标会和各个领域的目标有所冲突,因此如何快速有效解决这些冲突是非常需要智力的过程,同时也依赖很多经验。

    其实,软件测试的氛围也受很多其他的因素影响,例如测试人员和开发人员的比例,沟通等等。这里列出的只是我直接想到的几点而已。希望大家都能享受一个好的测试气氛。

     

    展开全文
  • 测试驱动开发:英文全称Test-Driven Development,简称TDD,是一种不同于传统软件开发流程新型开发方法。它要求在编写某个功能代码之前先编写测试代码,然后只编写使测试通过功能代码,通过测试来推动整个...

    介绍

    测试驱动开发:英文全称Test-Driven Development,简称TDD,是一种不同于传统软件开发流程的新型的开发方法。它要求在编写某个功能的代码之前先编写测试代码,然后只编写使测试通过的功能代码,通过测试来推动整个开发的进行。这有助于编写简洁可用和高质量的代码,并加速开发过程。 (from 百度百科),请自行 google、baidu

    这篇文章主要是谈个人的感想,有理解错误的请指教,欢迎评论交流

    (p.s. 我是一个 Dev,这个感想更多是从开发角度来看的)

    主要包含如下内容:

    • 我心中的 TDD
    • 如何做 Tasking
    • 举个例子 - Tasking 纵向拆分
    • 如何写 Test
    • 一个 class 可以有多个测试文件么?
    • 一个 Tasking 可以有多个测试么?
    • 业务规模 - 代码规模 - TDD 规模越来越大,如何维护?
    • TDD 的测试覆盖率能表示什么?
    • TDD 是测试方法么,是 Unit Test 么?
    • 使用 TDD 对开发时间的影响
    • 敏捷与 TDD, 不是敏捷项目可以 TDD 么?
    • 其他的 TDD 经验 / 疑问
    • 理想与现实

    。。

    我心中的 TDD

    TDD 的英文和中文意思都很好:测试驱动开发,Test-Driven Development。从小的教育就是一句话中的动词是很重要的,对于 TDD 我也是认为最重要的是“驱动”。而驱动的是什么呢?是“开发”,通过什么驱动呢?通过“测试”,于是我心中的优先级是:

    1. 驱动
    2. 开发
    3. 测试

    其实除了 TDD 以外还有很多 DD,比如 BDD - 行为驱动开发(Behavior Driven Development),再比如 ATDD - 验收测试驱动开发(Acceptance Test Driven Development),这些方法论都是从不同方面给开发提供驱动力,。

    驱动开发实际上是为了给开发以一定辅助手段,让开发的正确率、效率、业务表述贴合度提高,无论是测试、行为、验收测试都只是为开发提供的一种工具,一种方法论,一种外界的驱动力

    当然还有一种驱动力是自驱力,我相信自驱力,但我也不信自驱力,尤其是在复杂的业务关系、业务逻辑、软件架构、代码设计、技术栈以及组织架构混合下,单纯以自驱力就能够对开发驾驭自如,我们需要优先把这种混合的大泥球拆解开。

    再会到 TDD,我想它主要的目的是让开发人员尽可能在 coding 时,准确来说是在开发业务代码时,可以心无旁骛,沉浸于技术实现。那么想要以 TDD 的方式进入“开发阶段”:

    • 一定要现有一系列的驱动力“测试的红、绿”
    • 而想要有这一些列的测试就需要先对业务有足够全面的理解,并写出当前 story 的 tasking。

    到此为止,按照上面所说的两个大步,我在使用 TDD 的时候,无论是明确的感知到每一步的进行还是潜意识帮我做了很多,实际上在做 TDD 时,我都会间接地完成下面四步,

    • 理解业务
    • 细分业务
    • 编写符合业务流程的测试
    • 完成测试(开发业务代码)

    回想自己写个人项目的经历,埋头苦干,边写、边思考业务,脑子里在并行性工作,产品愿景分析,开发目标是什么,业务分析,功能到底要怎么样,UI 怎么做更好,架构是否够优秀,是否现在要重构,增加这个还是下一个业务时重写一下之前可能有 bug 的功能,这端代码写完了是否正确,好像这一段写出来的好熟悉是不是重复了,我记着曾经看过某人写的博客这里可以引入和框架一行搞定,是不是这个功能和某产品类似了看起来是不是用处不大……稀里糊涂写完了代码,然后启动程序试一试------

    怎么就不对了,我感觉写的对着呢!
    稍等我找找原因,没看出来什么地方有问题呀 20min ……
    这么多代码,在等我断点调试一下。
    你看这一步数据是对的,下一步就错了,所以进入这个 method 看看
    你看这一步数据是对的,下一步就错了,所以进入这个 method 看看(心理在喷,这不是我写的呀,或者是我很早以前写的了?这代码到底啥意思)
    你看这一步数据是对的,下一步就错了,所以进入这个 method 看看
    哦对,身份证号不能为空,一个人怎么能没有身份证号呢,怎么这里返回的对象里是 null,我再看看它从哪来的
    ……
    我在这忘记判断身份证号了,这里忘了,抱歉抱歉,真不好意思,现在就改:身份证号为 null 就是脏数据扔掉

    重新编译,再启动,这个问题解决了,来咱们继续验收
    刚才看过的就算了,咱们看看没看的功能
    不对不对,这里刚才不是对着呢?还好又看了一眼
    哦对了,我想起来当时写代码为什么身份证没有判断 null 了,因为身份证号可以为 null,有可能是护照等其他证件号
    ……

    其实无论是 TDD 或者其他的任何驱动方式,首要目的都是为了给开发提供一个工具 / 方法,使其能够在开发时只需要沉浸于技术,而不是业务流程+业务边界+代码实现+设计……人并非精密的机器,百密终有一疏。

    除此以外,TDD 在执行过程中还是期待能够进行合理的 Tasking 拆分,以供持续集成,更进一步的是持续部署(CI / CD)。

    如何做 Tasking

    为什么要先写如何做 Tasking,因为做 Tasking 是应该在真正做某个测试、某个实现、某个重构之前的。换句话说,Tasking 是最优先的,应该相将 Tasking 完成,再根据 Tasking 的输出去做写进行红-绿-重构的步骤,一定不是想到一个 task -> 写一个测试 ->实现 -> 重构。

    看到很多博客教程的大纲是这样的(我不认为这是合理的):

    • 介绍 TDD
    • 介绍教程的 Story
    • 第一个测试
    • 第一个实现
    • 重构
    • 第二个测试
    • 第二个实现
    • 重构

    上面这种大纲我并不认可,这样去写可能在这个简单的 demo 上看不出来什么,但是这样将会导致两个问题:

    • 仍然没有将业务理解和开发分离,仅仅只是先写了个测试
    • 如果开发复杂一些(相对比较大的 Story),写到后面就会对之前的测试、实现、最初对业务的理解有所遗忘,很可能导致整个 Story 的每一部分实现是基于随时间变化的不同的业务理解。

    我认为最合适的 TDD Tasking 应该是如下的过程:

    • 了解 Story,(如果是敏捷可以在开卡过程,甚至在开卡并了解了当前代码后,还可以继续再详细的根据当前业务实现现状询问 BA)
    • 根据 Story,识别整体价值,从价值角度初步拆分成交付步骤(这里可能还不是 Task,只是 Story 的几大步,这里是为了应对持续部署、持续交付,可以随时交付价值,而不是只有完整的 Story 完成才可交付价值,同时也是为了下面 Task 拆分时有足够的依据)
    • 根据每个交付步骤完成主业务流程的 Task,写到一个文档里(一定要整理下来,只有整理并且有产出才好让自己进行业务与实现的分离,当然如果这个过程已经熟练掌握那可以不进行持久化,不进行持久化的前提是确保自己的记忆力可以保证对业务理解在整个 Story 过程不会朦胧、突变)
    • 找到各种边界,将边界写成 Task,边界可以特例化的写,不需要遍历相同边界的所有可能,是为了驱动开发,而不是自动化校验所有可能。

    总结一下,我认为从需求到实现的过程应该是:自顶向下,逐层剖析,纵向拆分

    自顶向下指:从需求出发,以树的形式不断地分析出各个分支,最后到达实现代码。

    逐层剖析:分析的过程应该是有层次的,而不是抓住一点一口气钻到底(需求-一个 task-一个test-红-绿-再研究出一个 task……),应该脚踏实地一步一个脚印的分析,通过逐层分析让我们解耦需求、设计、实现。

    纵向拆分:就像上面的过程所说的从价值角度拆分,纵向就是

    举个例子 - Tasking 纵向拆分

    下面每个标题是按照流程写的,当然这个流程可能更像是个人开发者在和非技术人员沟通的过程,通过技术实现他人的 idea,如果项目明确的 BA or 业务负责人,可能技术拿到的第一份需求已经包含了一系列的 AC。

    开发,没有正确的,只有最适合的,下面的也只是个范例,我只是期待能够通过这个详细的过程描述,来让更多的开发能够在实践 TDD 时合理的拆分 Task,并提高持续部署、持续交付的意识,当然这个思考方式不止局限于 TDD,也不局限于敏捷。

    Story 背景

    A:您好,我这有个软件需要开发,主要是管理停车场的……我们商场的停车场比较麻烦,首先我们地下一层有 100 个停车位,地下二层也有 90 个停车位,除此以外我们楼顶还有一个停车区域有 50 个停车位,我们希望能够更好地管理这些位置,现在我们都是人工管理,希望能够数字化,不需要很复杂的管理,三个停车区域没有价格差异,只是希望有位置就能让车停入,没有剩余位置就给出提示就可以了。

    B:您好,近年来车辆越来越多,我感觉停车场是个很好的商机,我希望能够开发一个停车场管理系统,能够实现存车取车服务,现阶段希望能管理一个停车场就行了,以后可能会不断扩充,甚至可能需要合理的调度。

    为什么要说背景?我不认为没有背景的 Story 是可以分析出价值的,甚至于会影响侧重点。这两个背景可以看出 A 用户是已经有了成熟的管理区域,希望数字化转型,B 用户是只有 idea,没有人,甚至可能也没有场地,是个探索性的商业产品开发。

    当然为了简化(或者说我想要偷懒),这里只说 B 用户

    Story – 粗略版

    我希望我的客户能够在停车场存取车,客户存车以后可以得到一个存车卡,可以用卡取车。

    Story – 清晰版

    这一步可能是 BA 或者是 PM 也可能是自己根据交流得出来并持久化的 AC 内容。

    AC 如下

    1. 用户如果来存车,他可以得到一个存车小票。
    2. 用户如果用这张小票来取车,那么他可以取到自己存进去的车。

    Story – 扩充

    现在让我们从 AC 还有了解到的现实情况来分析,并和通过不断和需求提供方问答,我们可能会得到一些边界信息,来扩充 AC

    1. 用户如果过来存车,但是没有开着车,这样用户也会得到存车小票。
    2. 用户如果用一个无效的小票(用过的,或者自己创造的假的),或者随便拿其他东西来,都无法取到东西。
    3. 用户不会出现把一辆车存两次的情况,现实中会避免这种情况出现,不需要考虑

    Task 过程

    下面的 Task 可能会同时包含 Task 的实现,因为发现了很多人 Task 写的很好,但实现远远超出了 Task 内容

    先来个 Task:
    given 一辆车
    when 存车
    then 得到小票
    
    given 小票
    when 取车
    then 得到小票对应的车
    
    ……
    

    实现的过程(JAVA):

    void x1() { // poor naming
      ParkingLot parkingLot = new ParkingLot();
      Vehicle myCar = new vehicle("京AAAA");
      Ticket myTicket = parkingLot.park(myCar);
      assertNotNull(myTicket);
    }
    void x2() { // poor naming
      ParkingLot parkingLot = new ParkingLot();
      String vehiclePlateNumber = "京AAAA";
      Vehicle myVehicle = new vehicle(vehiclePlateNumber);
      Ticket myTicket = parkingLot.park(myVehicle);
      
      Vehicle pickedUpVehicle = parkingLot.pickUp(myTicket);
      assertEquals(vehiclePlateNumber, pickedUpVehicle.getVehiclePlateNumber());
    }
    

    这里,很多人写的 Task 并不是 “车牌号为 京A 12345” 的车,可能只是写了提供一个车,但是实现的过程用到了车牌号或者其他的号。

    这里有两个问题:

    首先:用车牌照号是一种对某个 vehicle object 的唯一识别方式,但是这个行为等于是对需求进行了脑补,上面写到的各种 AC 包括详细问答后扩充的 AC 都没有提到“车牌号”这个概念,若这个时候引入了车牌号,尤其是这个 Story 可以看出来比较简单,很可能只是第一个 Story,这样的行为很大概率会导致后续所有 Story 都被注入了全新的概念,最终结果这就是对整个业务注入了全新的概念,如果真的出现这个情况应该考虑先谈更改 AC,否则直接 new 一个无参、无私有成员的对象就足够了,每个对象都是唯一的。

    如果使用 new 一个对象的方式,最后断言在 Java 注意使用 assertSame,其他语言可找类似方案,要明确识别是对象完全一样(就是一个东西),还是对象的内容一样。

    其次,是 Task 划分的建议:

    在全新功能划分时,根据工作量以及业务价值进行划分,当前业务足够简单,那么存取车完全是一个必须组合到一起的功能,那么可以考虑把 Task 这么划分:

    given 一辆车
    when 存车
    Then 得到小票
    when 用小票取车
    then 取出来这辆车  -- 一辆车存取可以完成
    
    given A B 两辆车
    when 存 A 车
    then 得到小票
    when 用小票取车
    then 取出来 A 车
    when 存 B 车
    then 得到小票
    when 用小票取车
    then 取出来 B 车   --- 一辆车存取可以重复完成
    
    given A B 两辆车
    when 存 A 车
    then 得到 A 车小票
    when 存 B 车
    then 得到 B 小票
    when 用 A 小票取车
    then 取出来 A 车
    when 用 B 小票取车
    then 取出来 B 车   --- 多车可以顺序存顺序取
    
    given A B 两辆车
    when 存 A 车
    then 得到 A 车小票
    when 存 B 车
    then 得到 B 小票
    when 用 B 小票取车
    then 取出来 B 车
    when 用 A 小票取车
    then 取出来 A 车   --- 多车可以顺序存 逆序取(这里不是乱序,若要乱序最少三辆车)
    
    ……
    

    这里可以看到第一步的跨度可能有点大,但这样的 Task 更符合价值,最少在这时候我能保证存车、取车,虽然只是一辆车,但这时候已经可以做一定的 showcase。

    当然我这里并没有严格的遵守 given-when-then 的流程,可能在一个测试里有很多的行为(这可能会被喷吧),上面的这些流程是可以只在最后断言的,能保证的就是断言唯一,让整体读起来的感觉还是一个完整的意义。我认为这样是可以的,因为可以在阅读 task 的同时理解到各种业务场景。

    有人可能说:这样就没有单独测试 存车 接口的测试了,并不是的,具体可以看后面的章节“一个 Tasking 可以有多个 测试么?”

    还见到的其他的 Task
    • 小票给脑补出了 number,或者 实现上用到了 number,这时候更神奇的是要考虑 number 怎么生成?甚至要引入 UUID?如果非敏捷项目确实有明确的设计可以这么做,减少未来的大改动,但这个只是简单地 demo,明确了没有复杂内容
    • 实现上,把车存到了小票里,ParkingLot 仅仅只是从小票里拿出来了车,这个实现最后功能完全正确,但是对于后续项目转手给他人后会很难让人理解
    • 为了测试而实现,给 ParkingLot 提供了一个当前存车数量的 public method,提前公开了停车场这个属性,实际上并没有这个诉求,但是公开的 API 就会被四处使用,这就需要对这个接口进行维护。比如未来如果需要预留空位呢?那么这个时候返回的停车场存车数量应该包含预留么?难道要分成 3 个 API 分别针对历史的调用者(无预留空位时期的)、对于新的非预留车辆的、对于新的预留车辆的。(当然可以通过三个枚举、一个 API 维护这个内容,但无论怎样都会因为从未有过的诉求导致维护成本)
    • 如果存车时没有给车,那么能拿到存车票,这里要如何实现呢?返回 null?返回一个空的包装对象?当前的 Story 并没有看出来什么,怎么写都可以

    最后,很抱歉,这个 demo 可能并不适合讲解在价值上的纵向拆分,因为这个 Task 无论怎么变动,开发时间都很短,可能无论哪种方案,最后完成的总时间都是几分钟,无法感受到差异,只能期望读者能够体会到我所描述的本意了(唉,也可以说我懒吧)。如果有合适的 demo 欢迎留言。

    如何写的 Test

    无论是单元测试的 3A 模板:

    1. 组织数据(Arrange)
    2. 执行需要被测的函数(Action)
    3. 验证结果(Assertion)

    还是上面写的 Tasking 的 Given-when-then,我们最后都是要在“一个可控的环境下期待某种行为会产生理想的结果”

    这里面很重要的两个问题就是:

    • 一个测试如何构建“一个可控的环境”?
    • 什么是“产生理想的结果”

    下面我以多个小节分别分析两个内容,当然本文重点在个人的理解,讲述的流程、方法而不是具体的代码

    注意,这章讲的是如何写 Test,不是如何写 TDD 的测试。这是我从 TDD 实践过程以及一定的测试经历总结的,并非专业测试人员的角度,可能并不正确。

    一个可控的环境 - 测试工具的 BeforeAll / BeforeEach

    无论什么测试工具,都会有对整个 Class 测试前的前置处理方法,以及对 Class 每个 method 运行前会执行的方法,这两个工具并不建议使用。

    也有一些语言或者框架并没有 class 的概念,但是会有整个文件的概念,在文件里任何一个测试用例之前执行的方法,也算是 BeforeAll,下文都以 class 描述。

    可以使用 BeforeAll 对整个 class 需要 mock 的对象进行创建(注意只是对象创建,不是对象里的数据创建),可以指定整个测试类运行时是用什么对象进行执行。如果这样进行,也请务必保证,整个测试类里的每个测试用例都是要且都是会使用这个或者这些 mock 的,或者说这里面的所有测试用例一定都需要 mock 的,千万不要把 mock 的测试用例和正常运行的测试用例放在一个 class 里面。只要保证了上面说的,那么我们可以认为 BeforeAll 仅仅只是构建了一个 mock 的环境,并不会在 BeforeAll 中定义具体 mock 成了什么,调用 mock 的方法会返回什么等内容。

    对于 BeforeEach 完全不建议使用,如果 BeforeAll 已经对 mock 大环境做出了定义,那么不需要针对每个 method 单独进行定义了,如果需要改变大环境,那么请再建立一个 文件 / class

    除此以外,如果是面向对象的语言,有可能会出现测试 class 继承自某个自定义的 class,那么请让父类保持 BeforeAll 的要求,只对整个测试类的大环境做处理,比如每次启动前启动一个虚拟的数据库环境,每次整个 class / method 运行后清理数据库,不要进行具体的数据操作。

    为什么上面各种不建议呢?

    通过上面的描述可以看到,一系列的禁止后,我们可以保证一个 class 的 每个 method 的数据不会受到 BeforeAll、BeforeEach,我们可以认为我们看到的 class name 已经能够给我们足够的类信息,我们所写的 method 就是在这个信息下的,不会有意想不到的内容。

    那么如果整个测试每个 method 都需要在开始之前创建一个固定的数据呢?比如都要创建一个停车场,有 10 个停车位,其中位置 5 个存了车,这时候请建立一个 privat method,然后在每个测试用例第一行先调用这个私有方法。

    这么做有什么好处呢?

    请回想一下,现在有一个功能改动,你要在现有的功能下进行修改要如何操作?首先有了 story、无论是否做 tasking 吧,找到对应的实现代码,找到实现代码需要的测试类,创建一个 method(也有可能是复制上面的 method),然后写测试,然后运行一下,实现一下,测试过了,ok 了。(不要说拿到一个要修改的功能就直接改了,从不写测试)

    再回想一下,如果让阅读一个遗留代码,看了 story 不太懂,发现竟然有测试(好悲伤,我这里用到了竟然),然后是怎么读测试的?是不是根据方法命名,快速找到自己需要的功能,然后阅读

    上面的描述适合于多少人呢?

    上面两个过程都是:我们很少、极少会去有意识的、主动的、优先的看 BeforeAll 和 BeforeEach 方法。既然如此为什么要写这两个方法?如果在一个测试用例里明确的调用某个 method,我们可以很清楚的去查阅,如果用这一类便捷的方法那就是理想与现实的对立……

    为什么用"有意识的、主动的、优先的"三个词呢?意识决定了如果出现错误我们是否会考虑到是因为这两类方法的锅、主动决定了是否找到并考虑到此问题避免测试撰写错误、优先是不要等着测试挂了或者写完了测试才想到这个问题。

    其实 BeforeAll 和 BeforeEach 还有其他的可能问题,比如

    • 数据库我存进去两个数据,我的测试用例需要获取他们两个并经过一系列过滤后还能留下他们两个,然后我的测试过了,线上挂了,是什么原因呢?
    • 比如我的另一个测试需要 mock 一个方法传入“1”返回 null,但是 BeforeEach 里同样作了 mock 传入任何值都返回 null,然后我的执行行为写错了传入的是“2”,我成功得到了 null
    • ……

    最最最重要的:每一个测试用例应具有完整的语义。

    每一个测试用例单独抽离出来也应该是可用的。对于测试的 class 其实是一组测试用例的聚合,它可以归并一些用例的共同性,但往往我们归并的只是“是否属于这个类的测试”,那么这种归并就不应该提取出会影响到我们执行行为的数据内容。有共同需求的测试用例第一行写一行调用就好,对自己、对他人、对未来的自己、对未来的他人都是友好的。

    一个可控的环境 - 涉及到数据库如何构建数据

    请尽量严格遵守前面所说的根据价值纵向拆分: 数据库的数据不会凭空而来,所以我们的 tasking 一定是有数据输入的。

    如果是集成测试。比如说个“查看用户订单详情”Story 吧,如果可能了话,我们尽可能的去“规矩的创建订单”,而不是通过 Repository 直接插入数据

    集成测试最复杂的就是启动各个环境,我们费劲的启动了内存数据库,然后我们调过了所有创建订单的过程,直接插入了个订单,然后进行查看订单的行为及结果断言。这有用么?有用!这断言证明了“在我这种插入数据的方式下插入的数据可以被查看订单接口查阅”。

    为什么说纵向拆分呢,这里如果不纵向拆分,那么很可能 get 的 task 在 save 之前,那就完全无法合理的测试了,如果是纵向切分呢?save 一定是在之前的,或者 save 和 get 一起在第一个 task 里,这时候我们就有 save API,那么请调用 save 构造数据,这样可以保证无论 save 的行为如何改变,我们这个测试都是有价值的,我们测得不是能够查看数据库里固定样子(脑补、理想)的订单数据能够查看,我们测得是用户创建的订单能否查看

    这个是看到了很多很多人写的 API 测试,每次运行都要很久很久启动环境,然后 数据库插入、API 读取。。。。那为什么不直接 mock Repository 直接返回我们存进去的内容呢?和 mock 有什么区别,难道主流的框架自己没有测试而且基础的数据库读写会错?再进一步何必集成测试?无论是 JAVA 的 Spring 还是其他语言的其他框架,我想只要成为了主流,那么规矩的使用就不需要测试框架是否能调用了,框架不会把规矩的使用者路由错误的,如果真的怕有问题,那么可以专门写一个框架 API 调用行为的正确性

    我可以的接受 调用 HTTP save API 存数据,数据库查询:

    1. 有些业务需要只需要存储不需要查阅
    2. 存储可以做技术上的测试,确定存储行为是正确的
    3. 还有一种可能是:业务后来才需要查阅功能,但旧的测试仍然符合业务,计划删除但暂时未删,且新的测试完整测了存储与读取。

    对于第三点,写的很严谨,新的测试用例是完整的,且与旧的是包含关系,且是暂时未删除计划会删除。

    但是删掉一个测试用例真的这么难么?或者说留着旧的只是为了找个人一起背锅?难道版本管理系统的历史并不靠谱?

    我这里强调的是意识,一定要有对重复测试进行处理的意识,而不是无所谓的态度。

    如果要把这种类型的测试转成第二条说的技术上的测试,那么请把 HTTP API 调用这一步改成直接调用对应的服务 method,并 mock Repository 判断要存储的内容是否正确即可,这样这个测试的开销会很小也完成了测试需要,以后要修改也会相对容易处理

    当然真的要这么复杂的修改么?如果是 TDD 的测试,TDD 是为了驱动开发,当然可以不改,又没有冲突,如果没有时间,只要开发好就行。

    一个可控的环境 - 涉及到第三方服务如何构建数据

    mock,但是 mock 的返回内容请写到自己的测试用例中,不要写到 BeforeAll 和 BeforeEach 中,每个用例期待的第三方返回内容可能不同。

    然后?然后!我们 mock 了第三方调用,那么怎么保证这在链路中的数据真的是想要的格式呢?契约测试,可以使用相应的库、工具进行测试构建,对于微服务之间的契约测试我测试是考虑,具体开发实践过程就不细谈了。

    产生理想的结果 - 正确断言

    我们到底期待的是什么?那么请断言什么,千万避免下面这种断言方式:

    • 扩大断言范围:若停车场以车牌号作为唯一依据,判断取出来的车就是我存进去的车,那么请直接用车牌号判断,千万不要判断:assertEquals(pickedUpVehicle, myVehicle)。如果做完整的判断那么对于功能改动就需需改所有这样判断的测试,实际上大家的目的都不同,总不能说给一个 class 增加一个字段然后就要改几十个测试吧?
    • 断言混乱:并不是说一个测试只能有一个断言,可以一系列断言,但这些断言应该具有相同的目的,所以一般来说这些断言应该是连续的针对一个对象内容的断言。
    • 断言漏洞:如果返回值是个 list,里面应该有 A 和 B,且 AB 无顺序要求,那么如何断言?直接判断包含关系并不正确,还需要再补充一个数量的断言,只有数量确定,且分别为 A 和 B 才能证明是正确的,否则返回了 2 个 A ,1 个 B 也会通过。
    • ……

    不要过度的判断非测试内容的信息,因为测试最重要的是通过,无论是测试失败,还是测试运行失败都不是通过。如果中间内容很重要需要判断,那么可以做其他的测试,不要柔和到一起。

    一个 class 可以有多个测试文件么?

    这不需要长篇大论了:可以。

    一个 class 最少可以分成:需要 mock 进行的测试,可以直接调用进行的测试。测试不一定只有 test 这个目录,可以根据测试的类型进行分类

    一个 class 维护了很重要的一个数据内容,他的增删改查有独有的逻辑且很重要,需要完善各种边界的测试,每一个 method 可能都有几十个测试,那么可以分别放在不同的文件,一遍快速查找理解。这时候放在一个文件里可能难以通过 method name 快速理解,需要更多地 name 辅助理解。(一般来说边界的出现一定有对应的逻辑,如果真的有这么多的复杂边界,那么这个类的逻辑是有多复杂?是否能够拆分成其他类?比如 XxxxSaveAssistant、XxxxDeleteAssistant)

    一个 Tasking 可以有多个测试么?

    根据 Task 划分的粒度,为什么不能?如果按照我上面的停车场例子,given-when-then-when-then-when-then 这么多如果为了放心,完全可以写个单独的存车是否正确的技术验证。

    再比如停车场再复杂一些:

    我们有个停车场管理者,他管理了多个停车场,存取车只需要找管理者,他会帮忙放好,车主不需要知道车放到了哪里,给管理者就行。

    这时候我们对业务的测试可能和前面的一个停车场的完全一样,那怎么验证到底是否存到了停车场还是存到了管理者自己身上?具体存到了哪个停车场?这时候可以进行技术实现的测试,mock 多个停车场对象,判断存车时是否调用了期待的那个停车场就行了。

    这样我们对于这个新的停车场管理者的测试就会有业务流程测试、技术实现测试等等多个。当然也可能有的为了降低复杂性进行将复杂逻辑沉入到一系列单元测试,在集成测试测常规主流程。

    对于 TDD 来说为了驱动开发,一切都很灵活。

    业务规模 - 代码规模 - TDD 规模越来越大,如何维护?

    见“TDD 是测试方法么,是 Unit Test 么??”

    TDD 的测试测试覆盖率能表示什么?

    见“TDD 是测试方法么,是 Unit Test 么?”

    TDD 是测试方法么,是 Unit Test 么?

    这里先共同回答三个问题:

    • 业务规模 - 代码规模 - TDD 规模越来越大,如何维护?
    • TDD 的测试覆盖率能表示什么?
    • TDD 是测试方法么,是 Unit Test 么?

    TDD 的测试不会出现“ 规模越来越大”这种问题的,感觉太多了删了就好,他们是为了驱动你的开发么?没有,可能只有你现在写的测试时为了驱动你的开发,为什么要为其他人的驱动力发愁?我们可能真正需要考虑的是“测试的规模越来越大”。

    同样的对于 “TDD 的测试测试覆盖率” 我感觉可能接近于 0 吧!

    为什么要这么说?因为我不认为 TDD 是测试!TDD 是一种方法论,它以让开发人员先根据业务写出一定的测试再利用这些测试对开发过程进行保护的方法、开发流程。但这些测试的撰写的目的都是为了开发,只是个开发工具,并不是测试。

    注意,我前面几章的内容,他们都没有针对 TDD 去写:

    • 如何写 Test
    • 一个 class 可以有多个测试文件么?
    • 一个 Tasking 可以有多个测试么?

    这样一看 TDD 的产出物包含三种:Tasking 持久化后的文档、一系列的测试、开发出的内容。这些的直接价值只有“开发出的内容”。

    对于前两者,可以转化成测试,但它们在“转化”之前并不是测试。我为什么要提转化这个词,因为我们在交付之前应该对这些测试进行“专业化”,可以找 QA 聊聊,或者自己抛弃开发的想法,从测试角度来考虑,认真的看待这一系列的测试,他们是否要修改,这时候请转变身份,请认真的审视这些测试代码,不要逃避瑕疵,断言不合理?测试流程不正确?业务覆盖不全面?请用心修改,让他们成为真正的测试。

    在 TDD 开发过程写的测试是为了开发,属于 TDD 的中间产出物(可以删掉的),审查、转化后才是真正的测试。

    这样就解释了另外两个问题,若有需要请参考测试的管理、测试覆盖率的价值。

    对于测试覆盖率我想说。。。这个名字应该严谨的说“测试代码的代码覆盖率”,他只能表示代码,若代码都没有覆盖那一定是没有涉及到的,若代码覆盖了并不能保证一定覆盖了这个逻辑。所以测试覆盖率是用来挑错的,不能用它证明任何正确性

    使用 TDD 对开发时间的影响

    根据我观察到的情况,TDD 对于使用者来说可能要分为几个阶段:迷茫、了解、掌握……再往后我还差得远

    迷茫:可能在前期使用时会很迷茫,但是往往更多的是 follew,更多地是学习一套测试框架怎么用,如果项目有遗留代码,那么直接 copy 改动改动可能就完成了“使用”,根据业务复杂性会有一定的时间,但是并不多(除非项目对于 TDD 要求很严格,迫使此类人员不得不认真撰写才能过验收),否则可能更多的人会选择写的差不多就行了。当然,更可怕的是,有些人根本不知道自己写的根本覆盖不全业务,或者干脆没写测试(因为测试覆盖率过了)。这时候可能会对开发时间没有任何影响,也有可能会导致开发时间翻倍,这是很不稳定的时期。

    了解:知道如何去做,为什么去做,但是对于测试工具,尤其是 mock 工具的使用可能不太熟练或者不知道如何使用,这需要一个学习的过程,或者因为“不知道”而导致的设计错误(不知道能够 mock,为了测试给实现提供了多个接口),如果业务不太复杂,对于喜欢钻研的人员开发时间可能略微提高,对于无意识的人员开发时间没有影响,但是可能会导致长远的影响或者在 code review 时被要求修改。如果业务很复杂,天呀,可能会一团糟,此时就是 TDD(Test-Destroyed Development),测试写不好、实现不对、理解不断完整,实现改来改去,测试跟着一起变,最后测试也许还被删了。

    掌握:可以很好的根据业务要求进行 tasking,并严格的进行测试撰写及开发,对于复杂业务来说总体时间并不会提高很多,因为测试极大的降低了各种容易忽略的细节错误了,并保证长远来说的稳定性;对于很简单的业务可能会有所影响,甚至需要时间翻倍,因为容易很可能就一行代码搞定,那需要些最少一个测试,甚至一堆测试做各种边界校验。

    敏捷与 TDD, 不是敏捷项目可以 TDD 么?

    当然可以,如果项目整体都没有测试,并且无法推动出测试,那也可以写,写完删了就好都不需要转化成单元测试。。。。这只是一种开发过程,根据个人习惯就好。

    其他的 TDD 经验 / 疑问

    TDD 的驱动与红-绿-重构

    TDD 无论是否合理的进行 tasking,但只要真的想做(自驱力),那怎么也会有测试代码出现,一定会出现红色,为了能提交代码,那一定会出现绿色。

    但是重构呢?重构由谁来驱动?

    code review 确实会驱动重构,但这并非是 TDD 理想的重构效果,TDD 的红-绿-重构自身就是一个 circle,又有多少人破坏了 最后关键的一步,直接提交了绿色代码?

    红到绿是驱动的产物,就像我之前说的,我相信自驱力,但又不信自驱力,在个人项目做 tasking 写测试时完全依靠自驱,在团队项目有团队整体的风格可以参考,或者说有团队软件工程实践的规则限制,一定会写测试。

    有自驱的人是主动,无自驱的人是被要求的,总之一定会有测试的出现,红到绿的过程一定会被驱动出来,无论出来的质量如何。但是重构这一步没有驱动!

    这就带来了另一个问题:在敏捷的团队中,有多少人在喷着以前的代码设计的多么奇葩……

    我现在想到的途径只有在 code review 时的不断赋能,一对一的 feedback,但仍然没有红到绿这一步的强验收方式。

    TDD 在修 Bug 时的应用

    这里是最可怕的事情了。

    有多少人在 TDD 的实践过程中,修 bug 的时候完全没有 TDD,这里可怕之处不是第一个开发者无意识的挖了坑,而是修 bug 时没有补充测试用例就修改,这算有意识的改动了坑,这就成功造就一个埋了雷的坑。

    更可怕的是,这个修 bug 的人没有添加新的测试,还在修 bug 以后跑测试发现有挂的,再改了这些挂了的测试……

    既然是个 bug,修改之前请先根据当前的操作流程和期待的正确结果写出一个测试,通过测试复现出这个 bug,然后修好它,最后把这个产出物转化单元测试,这个测试很大概率本身就属于以前某个 story 的 task,只不过并未考虑到。为这才是填坑的过程。

    理想与现实

    上面说的是否太理想态了?现实中可能也就做个 demo、TDD 培训会注意这个,甚至培训都不会注意讲师也不会这么要求,只是单纯的告诉我们开发前先根据 story 写 tasking 进一步写 test 最后写出通过 test 的实现。

    理想态与现实差距很大!是不是我们可以顺其自然?我并不这么认为。

    虽然环境恶劣,但总要有量变的过程,只有越来越多的人有这个认知,才能有更多的人在开发过程中有这个意识,才能逐渐有人去践行这些方法论,才会有一个个经过方法论产出的产品,才能够产生反馈效应,给更多的人一种此方法已被校验,给更多只是有认知、有意识的人继续走下去、坚持下去的信心和赋能他人的有力支撑。

    最后

    上述所有内容仅供参考,非标准定义,仅为个人经验、理解,可以参考但请根据实际开发项目情况合理调整。我不认为 TDD 需要有条条框框,本身就是一个为开发提供外部驱动力的一种方法,如何合理的调整方法论的践行方式及流程?

    唯一的校验就是驱动的力量是否足够大,可以看产出速度,可以看主业务流程 bug 出现数量及业务边界操作出错的概率,可以看业务变动时连带的改动成本,可以看与 QA 交流及交接过程是否通畅,可以看与 BA 讨论过程是否能够在流程上边界上更容易达到理解一致,可以看项目转手后的开发理解速度……

    欢迎评论交流

    | 版权声明: 本站文章采用 CC 4.0 BY-SA 协议 进行许可,转载请附上原文出处链接和本声明。
    | 本文链接: Cologic Blog - 谈谈个人对 TDD (测试驱动开发) 的理解 - https://www.coologic.cn/2020/01/1738/

    展开全文
  • 作者:郑文强 时间:2019年7月15日 软件测试是评估软件产品质量和降低软件在运行过程中出现失效风险的一种手段。根据ISTQB软件测试专业术语对照表中对“测试”的...我将从下面几个方面谈谈对软件测试的理解: 1...
  • 谈谈软件测试面试问题

    千次阅读 2008-01-02 16:12:00
    (1) 你对SQA的职责和工作活动(如软件度量)的理解:SQA就是独立于软件开发的项目组,通过对软件开发过程的监控,来保证软件的开发流程按照指定的CMM规程(如果有相应的CMM规程),对于不符合项及时提出建议和改进方案...
  • 经常看到有些人把QA、QC、QM的概念搞混,认为他们是同一个概念的不同描述,由于这三者都是舶来品,并且翻译者在翻译的过程中概念的理解不一致,导致翻译质量良莠不一。 查阅了大量资料,认为他们之间的区别如下:...
  • 根据一学期的学习,谈谈对软件工程学科的认识。 这一题每个人都有不同的理解,而对于我目前了解到的就是: 所谓软件工程就是和建造房子一样的图纸,为开发软件提供一种策略,方法,可以设计出更加实用的软件,通过...
  • (4) 说说主流的软件工程思想(如CMM,CMMI,RUP,XP,PSP,TSP等)的大致情况以及你它们的理解: CMM:SW Capability Maturity Model 软件能力成熟度模型,其作用是用于软件过程的改进、评估及软件能力的评鉴 CMMI:...
  • 火龙果软件工程技术中心 本文仅就单元测试而论,虽然是说的测试,但目的是驱动开发,不过也不是谈测试驱动开发,更象是对测试驱动开发时TESTFIRST这个过程中如何保证测试代码的正确性的理解和想法,当然有一些,我...
  • 谈谈对测试的理解 你觉得软件测试中最重要的是什么 软件测试枯燥,你为什么选择这个职业 有没有做过什么实际项目,谈谈你做了些什么 会用什么测试工具,会不会搭建测试环境 会不会Linux 对于一个web测试,...
  • 1.什么是Bug,谈谈的理解 Bug在英文上是小虫子、窃听器的意思,第一次bug的出现,正是一个小虫子落在巨型计算机的导致晶体管短路,从而使得计算机出现问题。 我理解的bug是在编译程序时以及后续运行时出现的...
  • 那好,作为一名一线的测试人员,我想谈谈开发测试比的一个理解。首先,我要问,为什么要有测试呢?测试的目的是什么?记得有一本书里曾经说,有一个硬件人员转去做软件,他写的代码从来都没有bug...
  • 小议软件测试

    2009-07-23 10:45:12
    今天专门谈谈软件测试以及我对软件测试的一些理解,也希望这些理解对做软件测试的人有所帮助。 首先对于软件测试和软件开发的关系问题,首先要说明的是测试需要懂一些软件开发方面的知识,而这些软件开发知识里面...
  • 软件测试之我看

    2015-09-17 15:02:00
    软件测试,谈谈对软件测试的看法,从来没有想过对这么大一个话题来说出自己的一个想法或者说对软件测试的理解,我就觉得自己能不能把自己对软件测试的了解说说,或者说汇总汇总下这三四年来自己从事的行业,也算是...
  • 大公国际软件测试工程师面试题时间:2014-12-04 10:53分享到:一、软件工程试题:(1)谈谈对软件工程的理解。(2)您在以往的测试工作中都曾经具体从事过哪些工作?其中最擅长哪部分工作?(3)比较一下黑盒测试、白盒...
  • 软件测试复习题目.doc

    2020-11-24 13:46:49
    质量保证部分: 软件规模的度量指标有哪些?(LOC&FP,McCabe’s Cyclomatic Complexity Metric) ...请从度量(或者BUG管理或者测试)的角度谈谈CMM五个成熟度级别的理解 ISO9000和CMM的异同点?
  • 初识银行软件测试

    万次阅读 多人点赞 2014-12-30 21:57:39
    从一家工作了五年的软件公司的测试管理者跳槽到**银行做软件测试,短短两个月,对银行测试有了初步认识,...所以银行对软件的质量要求非常高,这也是银行软件测试的一大特点。接下来从多个角度来谈谈银行的软件测试。
  • 当时铁了心以软件工程班级第一开发水平选择做软件测试。不顾同学和老师们理解。毅然做了测试,这一晃就是五年多。这期间作为面试官,曾经在公司被hr专业训练过,如何做好一名合格面试官,需要从节奏/交接/...
  • 浅谈软件测试

    2006-01-08 15:48:15
    口出狂言浅谈软件测试,用这样的标题实在是感觉羞愧,虽然我用的题目是浅谈软件测试,我只不过是谈谈我在开发过程中...[@more@]我们的项目基本开发完毕了, 软件测试是必须的过程,我对软件测试的理解是:测试软件的...
  • 下面我就结合我在java项目当中的开发谈谈对软件测试的理解以及软件测试工具使用的过程。 软件测试工具:Jmeter 一. 软件测试的必要性 测试活动需要花费大量的时间和成本,如果用手工测试,测试的效率非常低;而...
  • 软件测试工程师主要工作职责是,理解产品功能要求,并其进行测试,检查软件有没有错误,决定软件是否具有稳定性,写出相应测试规范和测试案例。简而言之,软件测试工程师在一家软件企业中担当是“质量管理...
  • 1.谈谈“测试”的理解软件测试是软件开发过程中必不可少的一部分,它为软件提供质量保证。测试人员不仅要负责软件的需求一致性(软件功能与需求说明书等文档的符合程度),还要关注软件的可靠性、可移植性...
  • 随着客户对软件产品的质量要求...本文将从软件测试目的、软件测试类型和什么是好的测试几个方面谈谈对软件测试的一点理解。 1)软件测试目的 针对软件产品开展测试活动之前,首先需要明确本轮测试的主要目的...
  • 谈谈对B/S、C/S、APP的理解及区别以及测试关注点 问题解析:要回答这个问题首先要搞明白这几个架构的区别,把架构搞明白了,就应该知道怎么测试或者侧重点了。 1、WEB是所有业务功能就集中在后台服务器这块,借助...
  • 软件测试经典面试题 (超实用)

    热门讨论 2012-02-16 13:48:08
    14、TestDirector有些什么功能,如何对软件测试过程进行管理? 7 15、你所熟悉软件测试类型都有哪些?请试着分别比较这些不同测试类型区别与联系(如功能测试、性能测试……)? 7 16、条软件缺陷(或者叫Bug...
  • 1、先谈谈对软件测试的理解。 可简述软件测试的概念和目的。最后我加了一句,无论是软件开发人员,还是软件测试人员,我们大家的目标都是一致的,都是为了提高产品质量,开发出让用户满意的产品。 2、软件测试分为...

空空如也

空空如也

1 2 3 4
收藏数 64
精华内容 25
关键字:

谈谈对软件测试的理解