内外BDD(带Specflow)

Ser*_*kiy 41 c# bdd cucumber specflow

我是BDD的新手,但我发现它非常有趣,并希望使用BDD开发我的下一个项目.在谷歌搜索和观看截屏后,我仍然有很多关于BDD在现实生活中的问题.

1.陈述性或势在必行的场景?

我看到的大多数给定的时间场景都是用UI(命令式)编写的.

Scenario: Login
     Given I am on the Login-page
     When I enter 'AUser' in the textbox 'UserName'
       And I enter 'APassword' in the textbox 'Password'
       And I click the 'Login' button
     Then I should see the following text 'You are logged in'
Run Code Online (Sandbox Code Playgroud)

我发现这些测试非常脆弱,并且它们没有说明点击按钮的商业价值.我认为这是维持的噩梦.为什么大多数示例都使用命令性场景?

Scenario: Login (declarative)
     Given I am not logged in
     When I log in using valid credentials
     Then I should be logged in
Run Code Online (Sandbox Code Playgroud)

如果您更喜欢声明式样式,那么如何描述"主页"或"产品页面"等内容?

2.运动UI与否?

我看到的大多数步骤实现都使用WatiN,White或类似的东西从用户的角度来实现场景.启动浏览器,单击按钮.我认为它极其缓慢而脆弱.好吧,我可以使用类似Page对象的东西来减少测试.但那是另一项工作.特别适用于具有复杂UI的桌面应用.

您如何在现实项目中实施场景 - 行使UI,或通过测试控制器/演示者?

3.真实数据库与否?

当给定部分场景时,通常需要一些数据存在于系统中(例如,一些用于商店应用的产品).您如何实现该部分 - 将数据添加到真实数据库(完整的端到端测试),或者向控制器提供存储库存根?

等待有经验的答案!

更新:在问题上添加了有用的链接.

And*_*ndy 12

  1. IMO是一种正确的方式.如果你在谈论.aspx文件名页面,你做错了.故事的目的是促进开发人员和非开发人员之间的沟通.非开发人员不关心products.aspx,他们关心产品列表.您的系统会执行非开发人员认为有价值的内容.这就是您要捕获的内容.

  2. 这些故事讲述了您需要实现的高级功能.它是你的系统必须做的.真正告诉你是否已经这样做的唯一方法是实际上运用UI.对我来说,BDD SpecFlow故事并没有取代单元测试,而是它们是集成测试.如果你打破这个局面,你就会破坏企业从软件中获得的价值.单元测试是用户不关心的实现细节,他们只是单独测试每个部分.这无法告诉你A和B是否一直在一起工作(理论上它应该在实践中有趣的[读取:意外]事情发生时你实际上有两个部分互相玩耍).自动端到端测试也有助于您的QA.如果功能区域中断,您就会知道它,并且当您确定破坏集成测试的内容时,他们可以将时间花在应用程序的其他区域.

  3. 这是一个棘手的问题.我们做了一个混合方法.我们确实使用数据库(在测试系统作为一件事情而不是单个组件之后集成测试),而不是在我们需要时使用Deleporter用Moq替换我们的存储库时重置配置.似乎工作正常,但无论哪种方式肯定有利有弊.我想我们仍然在很大程度上自己解决这个问题.


Mer*_*ham 7

编辑:我发现这篇文章刚刚描述了限制自己只讨论特定域以避免脆弱场景的概念.

他的主要观点是,您可以谈论的最小域数是问题域和解决方案域.如果你在谈论这两个领域之外的任何事情,那么你涉及太多的利益相关者,你引入了太多的噪音,并且你使你的场景变得脆弱.

他还提到一个绝对的"陈述性"或"命令式"模型是一个神话.他谈到了一个名为"分块"的认知模型,他说在你的抽象的任何层面上,你都可以"大块"或"大块化".这意味着您可以更明确地(如何?)或更多元(什么或为什么?).通过询问"我们在做什么?",你从命令式模型中掏腰包?你说"我们将如何做到这一点?" 所以我想我不会在声明与命令方面挂得太多 - 就这个问题而言,它不会让你到处都是.

什么会得到你的地方是搞清楚哪些域每学期所属,可能是通过确定哪些利益相关者对这个词在所属领域的专家.一旦你确定所有的域,您都可以选择相关的术语说在一个场景最突出的域名,或完全删除不合适的语句.如果这还不够,您可以拆分,进一步指定或移动方案,以便它可以满足这些要求.

顺便说一下,他还使用了登录UI的场景,所以你得到了具体的指导:)

在编辑之前 :(其中一些仍然适用."DB或无数据库"和"UI或无UI"问题无关)

1 - 声明性或势在必行的场景?

虽然命令式具有一定的价值(在项目生命周期的某些点上),但可以尽可能地声明.

对于不熟悉信息理论和设计的测试人员和业务分析师来说,这是一种更容易思考的方法.在确定问题域和工作流程之前,在项目早期考虑也更容易.它对探索性思维很有用.

声明随着时间的推移不太可能发生变化.由于GUI是应用程序的一部分,因此非常有用,因此非常有价值.一旦确定了问题域和工作流,就会更容易思考,并且更关注关系概念.它是一种更稳定,更普遍适用的模型.

如果使用通用和声明性模型编写测试用例,则可以使用完整应用程序GUI自动化,集成测试或单元测试的任意组合来实现它们.

你如何描述像'主页'或'产品页'这样的东西?

我不确定我会在基本级别的功能和要求.您可以创建描述实现细节的子功能和子需求,例如特定的UI工作流.如果您正在描述UI的一部分,那么您应该定义UI功能/要求.

2 - 运动UI与否?

都.

我认为它极其缓慢而脆弱

是的.使用UI和完整数据库集成执行每个高级场景/需求,但不要使用端到端UI自动化执行每个代码路径,当然也不要使用边缘情况.如果你这样做,你将花费更多的时间让它们工作,并且实际测试你的应用程序的时间要少得多.

您可以构建应用程序,以便进行低成本集成测试,包括基于单件UI的测试.单元测试也很有价值.

但是,您进行的集成测试越少,您就会错过更多的前额错误.编写单元测试可能更容易,而且它们肯定不那么脆弱,但根据定义,您将测试较少的应用程序.

3 - 真实数据库与否?

都.

必须在整个系统到位的情况下完成高级端到端集成测试.这包括一个真正的数据库,在不同服务器上运行每个系统的测试等.

你得到的级别越低,我提倡的模拟对象就越多.

  • 单元测试应该只测试单个类
  • 中级集成测试应该避免昂贵,脆弱和有影响力的依赖,例如文件系统,数据库,网络等.尝试仅使用单元测试和端到端测试来测试那些脆弱且有影响的依赖项的实现.