将 TDD 用于库/API 代码并使用 BDD 作为集成测试有意义吗?

发布于 2024-10-01 03:28:06 字数 363 浏览 0 评论 0原文

我是 BDD 的新手,我想了解它在开发周期中发挥什么作用。在 TDD 方法中,我们通常会为库或 API 编写单元测试,我们会模拟对象,这很棒,因为它甚至可以驱动我们的设计。这些测试将在实际代码之前编写,这很好。

我知道 BDD 更多的是关于规范/场景测试,并且我可以看到它非常适合根据实际代码测试业务需求。但是编写这些测试的最佳实践是什么?我们是否仍然继续编写单独的测试(如 TDD)来模拟依赖关系并为每一个可能出错的事情编写单元测试?然后编写我们的 bdd 测试?我们首先编写 bdd 测试吗?即使针对单个组件,我们是否也只编写 bdd 测试?

我使用 .NET,通常编写 asp.net mvc 应用程序,但这更多的是一个理论问题,与底层编程语言无关。

多谢。

I am a complete newbie to BDD and I would like to understand where does it come into play in a development cycle. In TDD approaches, we would write unit-tests commonly for libraries or apis, we would mock objects and that was great because it could even drive our design. These tests would be written before the actual code which is nice.

I understand that BDD is more about spec/scenario testing and I can see that it is a perfect fit to test a business requirement against the actual code. But what is the best practice for writing these tests? Do we still keep writing individual tests (as in TDD) mocking out dependencies and writing unit-tests for every single thing that could go wrong? Then write our bdd tests? Do we write the bdd tests first? Do we write only bdd tests even against individual components?

I use .NET and usually write asp.net mvc apps but this is more of a theory question and independent of the underlying programming language.

Thanks a lot.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

绻影浮沉 2024-10-08 03:28:06

不知道正确的方法,但这是我的经验。在分析了规范文档之后,我尝试提取尽可能多的不同“故事”并使用 BDD 故事文件来描述它们。正如您所知,每个句子都应以 given、whenthen 三个关键字之一开头。

将整个规范转换为 BDD 测试故事后,我编写了一个类来实现步骤,即执行故事中使用的每个句子。

下一步是开始编写一个实现,该实现将由通过设置初始状态(给定)、状态转换(何时)和检查应用程序的目标状态(然后)来执行脚本句子的方法调用。

每当我需要实现实际的类方法时,我都会使用 TDD 来进行彻底的隔离测试。

当然,为了运行测试,尚未实现的部分代码可能会被暂时模拟。

Don't know about the right way but this is my experience. After analyzing the specification document I try to extract as many different 'stories' and describe them using BDD stories files. As you already know every sentence should start with either one of three keywords given, when and then.

After translating the whole specification to BDD test stories I write a class that implement steps i.e. execute each one of sentences used in stories.

Next step is starting writing an implementation which will be called by methods that execute script sentences by setting initial state (given), state transitions (when) and checking the destination state of the app (then).

Whenever I need to implement an actual class method I use TDD to do a thorough testing in isolation.

Of course, in order to run the test part of the code that is not yet implemented may be temporarily mocked.

烂柯人 2024-10-08 03:28:06

BDD 是一组围绕描述和构建系统行为模型(以及更高级别的项目愿景)的模式,它可以帮助我们针对不同粒度级别就该行为进行对话。

我们使用诸如“给定上下文,当这个事件发生时,那么这个结果应该发生”之类的对话模式,并鼓励诸如“应该吗?总是?我们是否遗漏了任何其他上下文?”之类的问题。

我们可以在单元级别、场景级别甚至分析空间中做到这一点。

我倾向于从最高层开始向内工作。 这是我写的一篇文章,它描述了从项目愿景到项目愿景的整个过程。单元测试。

我编写的第一段代码将是场景。 以下是一些没有任何内容的场景 BDD 框架,只是普通的旧 NUnit,展示了如何使用领域语言等使这些框架成为英语可读的。

然后我从用户界面开始。这可以是 GUI、网页或供其他系统使用我的系统的界面。完成后,我可以获得有关我的用户是否喜欢它的反馈。我经常对数据等进行硬编码,以便获得反馈。

一旦我大致知道我的 GUI 是什么样子,我就可以开始创建它背后的行为。我通常从控制器的行为开始。我将编写类级示例来描述类的行为和职责。我使用模拟来代替我尚未编写的协作类。这相当于 TDD,但我不是编写测试来固定代码以便没有人破坏它,而是编写如何使用我的代码的示例,这些示例显示了它的行为方式以及为什么它很有价值,以便您可以更改安全地进行。我还使用给定/何时/那么为此!但我倾向于使用更多技术性语言,并且不担心它的英文可读性。通常我的给定/何时/那么只是在评论中。 以下是同一类的行为示例代码库作为场景,所以你可以看到有什么区别。

希望这对您有所帮助,祝 BDD 好运!

BDD is a set of patterns around describing and building models of the behaviour of a system (and, at a higher level, a project vision) which can help us to have conversations about that behaviour, for various levels of granularity.

We use conversational patterns like "Given a context, when this event happens then this outcome should occur", and encourage questions like, "Should it? Always? Are there any other contexts we're missing?"

We can do that at a unit level, a scenario level or even into the analysis space.

I tend to work from the highest level inwards. Here's an article I wrote which describes what that looks like, right the way from project vision to unit tests.

The first bit of code I write will be the scenarios. Here are some scenarios written without any BDD frameworks, just plain old NUnit, showing how you can make these English-readable with domain language, etc.

Then I start with the User Interface. This could be a GUI, web-page, or an interface for another system to use my system. When this is done I can get feedback on whether my users like it. I frequently hard-code data, etc., just so that I can get that feedback.

Once I know roughly what my GUI will look like, I can start creating the behaviour behind it. I usually start with the behaviour of the controller. I will write class-level examples which describe the class's behaviour and responsibilities. I use mocks in place of collaborating classes I haven't written yet. This is the equivalent of TDD, but rather than writing tests which pin the code down so that nobody breaks it, I'm writing examples of how you can use my code, which show how it behaves and why it's valuable so that you can change it safely. I also use Given / When / Then for this! But I tend to use more technical language and don't worry about it being English-readable. Frequently my Given / When / Then are just in comments. Here's an example of class behaviour from the same codebase as the scenarios, so you can see what the difference is.

Hope this helps, and good luck with the BDD!

夏日落 2024-10-08 03:28:06

您可以像 TDD、单元测试或其他方式一样使用它。区别在于测试“业务行为”。规范流程和功能是一种选择,单元测试语法看起来像这样

[Given(@"a user exists with username ""(.*)"" and password ""(.*)""")]
public void GivenAUserExistsWithUsernameAdminAndPasswordPassword(string userName, string password) {

}

[Then(@"that user should be able to login using ""(.*)"" and ""(.*)""")]
public void ThenThatUserShouldBeAbleToLoginUsingAdminAndPassword(string userName, string password) {
        Assert.IsTrue(_authService.IsValidLogin(userName, password));
    }

You can use it similarly as TDD, unit testing or otherwise. The difference is gonna come from testing "Business Behavior". Spec Flow and Features is one option, unit testing syntax would look something like this

[Given(@"a user exists with username ""(.*)"" and password ""(.*)""")]
public void GivenAUserExistsWithUsernameAdminAndPasswordPassword(string userName, string password) {

}

[Then(@"that user should be able to login using ""(.*)"" and ""(.*)""")]
public void ThenThatUserShouldBeAbleToLoginUsingAdminAndPassword(string userName, string password) {
        Assert.IsTrue(_authService.IsValidLogin(userName, password));
    }
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文