外部BDD(Specflow)

我是BDD的新手,但是我发现它非常有趣,想用BDD开发我的下一个项目。 谷歌search和屏幕截图之后,我仍然在现实生活中遇到很多有关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' 

我发现这些testing非常脆弱,他们没有提到点击button的商业价值。 我认为它的噩梦来维持。 为什么大多数例子使用命令式场景?

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

如果你喜欢声明式的风格,你怎么描述这样的东西,如“主页”或“产品页面”?

  • 编写好规格的技巧

2.锻炼UI还是不行?

我看到的大多数步骤实现使用WatiN,White或类似的东西从用户的angular度来实现场景。 启动浏览器,点击button。 我觉得它非常缓慢而脆弱。 那么,我可以使用类似于Page对象的东西来减lesstesting的脆弱性。 但那是另一个工作量。 特别适用于复杂UI的桌面应用程序。

您如何在实际项目中实施场景 – 锻炼UI还是通过testing控制器/演示者?

  • 最好的方法来应用BDD

真正的数据库还是不?

当给定部分场景实施时,往往需要一些数据在系统中(例如某些商店应用的产品)。 你如何实现这一部分 – 将数据添加到真正的数据库(完整的端到端testing),或提供存储库存根控制器?

等待有经验的答案!

更新:添加有用的问题链接。

  1. IMO是正确的。 如果你是在谈论page .aspx文件名,那么你做错了。 故事的目的是促进开发者和非开发者之间的沟通。 非开发人员不关心products.aspx,他们关心产品列表。 你的系统做了一些非开发人员发现的价值。这就是你想要捕捉的东西。

  2. 那么,这些故事告诉你需要实现的高级function。 它的系统必须做什么 真正知道你是否已经完成这个工作的唯一方法就是实际操作UI。 BDD SpecFlow的故事对我来说并不代替unit testing,而是他们是集成testing。 如果你打破这个,你已经打破了企业从你的软件获得的价值。 unit testing是用户不关心的实现细节,他们只是单独地testing每一块。 那不能告诉你A和B是否真的一直在一起工作(理论上说,实际上当两个部分彼此玩耍的时候,事情就会发生在有趣的事情上)。 自动化的端到端testing也可以帮助您进行质量检查。 如果某个function区域出现故障,您就会知道这个function区域,并且可以在应用程序的其他区域花费时间,同时确定是否打破了集成testing。

  3. 这是一个棘手的问题。 我们已经做了一个混合的方法。 我们使用数据库(整合testing毕竟testing系统的function,而不是单个组件),而不是重新configuration所有的时候,我们使用Deleporter来取代我们的存储库,当我们需要的时候。 似乎工作正常,但肯定有利弊两种方式之一。 我认为我们仍然主要是自己想出来的。

编辑 :我刚才发现这篇文章描述了限制自己只谈论特定领域的概念,以避免脆弱的情况 。

他的主要观点是,你可以谈论的领域的最小数量是问题领域和解决scheme领域。 如果你在这两个领域之外讨论什么,那么你涉及太多的利益相关者,你会引入太多的噪音,并且让你的scheme变得脆弱。

他还提到一个绝对的“陈述式”或“势在必行”的模式是一个神话。 他谈到一个称为“组块”的认知模型,他说,在任何抽象层面上,你都可以“大块”或“块化”。 这意味着你可以得到更明确的(如何?)或更多元(什么或为什么?)。 你从一个命令性的模型中大胆地问:“我们在做什么?” 你大声说:“我们该怎么做?” 所以我想我不会太过于坚持陈述式和必要式的 – 在这个问题上,它不会让你有任何的问题。

什么会让你在某个地方找出每个术语所属的领域,可能通过确定哪个利益相关者是这个术语所属领域的专家。一旦你确定了所有的领域,你可以select一个相关的术语场景最重要的领域,或完全删除非适合的陈述。 如果这还不够,可以拆分,进一步指定或移动场景以满足这些要求。

顺便说一句,他还使用了在UI上login的场景,所以你有具体的指导:)

在编辑之前 :(其中一些仍然适用。“DB或没有DB”和“UI或没有UI”的问题是无关的)

1 – 声明还是必要的情况?

尽可能声明,尽pipe势在必行(在项目生命周期的某些阶段)。

对于那些不熟悉信息理论和devise的testing人员和业务分析师来说,强制性是一种更简单的方法。 在确定问题领域和工作stream程之前,先在项目中思考一下也比较容易。 它可以用于探索性思考。

声明性不会随时间而改变。 由于graphics用户界面(GUI)是应用程序中最容易出错的应用程序的一部分,这是非常有价值的。 一旦你确定了你的问题领域和工作stream程,并且更关注于关系概念,那么考虑一下会更容易。 这是一个更稳定,更普遍适用的模式。

如果您使用generics和声明模型编写testing用例,则可以使用完整应用程序GUI自动化,集成testing或unit testing的任意组合来实现它们。

你如何描述这样的东西,如“主页”或“产品页面”?

我不确定我会在function和要求的基础级别。 您可以制作描述实现细节的子function和子需求,如特定的UI工作stream程。 如果你正在描述一个UI,那么你应该定义一个UI特性/需求。

2 – 锻炼UI还是不行?

都。

我觉得它非常缓慢而脆弱

是的。 通过UI和完整的数据库集成来执行每个高级场景/需求,但是不要使用端到端的UI自动化来执行每一条代码path,当然也不是边缘案例。 如果你这样做,你会花更多的时间让他们工作,而实际上testing应用程序的时间却less了很多。

您可以构build您的应用程序,以便您可以进行更低成本的集成testing,包括基于单个UI的testing。 unit testing也是有价值的。

但是你做的整合testing越less,你会错过更多的额头sla bu声。 编写unit testing可能会更容易,而且它们肯定不会太脆弱,但根据定义,您将会less量testing应用程序。

3 – 真正的数据库与否?

都。

高水平的端到端集成testing必须在完整的系统上完成。 这包括一个真实的DB,在不同的服务器上运行每个系统的testing等等。

你得到的层次越低,我越是主张模拟对象。

  • unit testing应该只testing单个类
  • 中级集成testing应该避免昂贵,脆弱和影响很大的依赖性,例如文件系统,数据库,networking等。尝试仅使用unit testing和端到端testing来testing那些脆弱和有影响的依赖性的实现。

不要按名称来提及页面,请描述它代表的内容,例如

 Scenario: Customers logs in successfully When I log in Then I should see an overview of ACME's top selling products 

您可以直接对底层的API或模型进行testing,但是您做得越多,您承担的风险就越大,不会遇到集成问题。 一种方法是用less量的全堆栈testing来进行平衡,另一种方法是只在两层之间进行testing。