在同一测试用例或单独的测试用例中测试默认值和设置器

发布于 2024-11-14 05:26:11 字数 557 浏览 4 评论 0原文

您是否建议在 @Test 方法中对测试用例进行任何分组,或者每个测试场景使用一个 @Test 方法?例如,假设有不同的方法可以在应用程序中设置上下文。

下面的想法可以接受吗?

@Test
public void testContextSetting() {
    // Test default setting
    assert(...)

    // Test setting a context variable
    assert(...)

    ...
}

或者,您是否愿意建议像这样,使每个方法尽可能原子:

@Test
public void textDefaultSetting() {
    // Test default setting
    assert(...)
}

@Test
public void testSettingContextVar() {
    // Test setting a context variable
    assert(...)

    ...
}

任何反馈将不胜感激。

Would you recommend doing any grouping of test cases within @Test methods, or have one @Test method per test scenario? For example, let's suppose that there are different ways to set the context in an application.

Is the following idea acceptable?

@Test
public void testContextSetting() {
    // Test default setting
    assert(...)

    // Test setting a context variable
    assert(...)

    ...
}

Or, would you rather suggest having it like this, having each method as atomic as possible:

@Test
public void textDefaultSetting() {
    // Test default setting
    assert(...)
}

@Test
public void testSettingContextVar() {
    // Test setting a context variable
    assert(...)

    ...
}

Any feedback would be appreciated.

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

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

发布评论

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

评论(5

等风来 2024-11-21 05:26:11

我更喜欢每种方法有一个测试用例。

首先,如果将它们分成方法,而不是寻找嵌入在代码中的注释,则更容易看到正在测试的案例。大多数 IDE 都会为您提供方法摘要,因此不要说“我测试了 Edgecase XYZ 吗?”然后寻找注释,或者寻找设置该边缘情况的代码,您只需寻找名为 setupContextEdgeCaseXYZ() 的方法。

第二个原因是,如果您有多个案例在一起,其中一个可能会失败,然后其他案例永远不会执行。

 testDefaultCase()
 testInvalidInput()
 testEdgeCase1()
 testEdgeCase2()

使用这种结构,可以更容易地确定输入检查不良以及边缘情况 2 处理不当,但其他情况都正常(并且您可能会发现两个失败情况是相关的,并且可以更快地诊断问题)。

第三个原因是您可能会意外地留下前一个测试集中的值,从而以不明显的方式使后一个测试无效。一个简单的例子:

@Test
public void testMyMethod() {
  //test default
  String test = Foo.bar(null);
  assertEquals("foo", test);

  //test case 1
  Foo.bar(aValue);
  //Oops forgot to set value above, this passes regardless of 
  //what the above call does
  assertEquals("foo", test);
}

通过将大小写分开,您可以避免上述错误,因为这会变成编译错误或警告。

I prefer having one test case per method.

First it is easier to see what cases are being tested if they are split into methods as opposed to looking for comments embedded in the code. Most IDEs will give you a summary of methods, so instead of saying "did I test edgecase XYZ?" and then hunting for a comment, or looking for the code that sets up that edgecase, you just look for the method named setupContextEdgeCaseXYZ().

A second reason is if you have multiple cases together one may fail and then the others never execute.

 testDefaultCase()
 testInvalidInput()
 testEdgeCase1()
 testEdgeCase2()

With this structure it would be easier to determine that the input checking is bad and edge case 2 is handled improperly, but the others are OK (and you may find out that two failing cases are related and the problem is diagnosed faster).

A third reason is you may accidentally leave values from a previous test set that invalidates a latter test in a inconspicuous way. A simple example:

@Test
public void testMyMethod() {
  //test default
  String test = Foo.bar(null);
  assertEquals("foo", test);

  //test case 1
  Foo.bar(aValue);
  //Oops forgot to set value above, this passes regardless of 
  //what the above call does
  assertEquals("foo", test);
}

By breaking cases apart you can avoid mistakes as above as that would turn into a compile error or warning.

初见你 2024-11-21 05:26:11

最佳实践是每种方法都有一个测试用例。方法名称描述了您正在执行的测试。当测试失败时,如果只有一个断言,调试会更容易。

Best Practice is to have one test case per method. The method name describes the test that you are performing. It is easier to debug when your test fails when it is just one assert.

千紇 2024-11-21 05:26:11

Divide et impera :) 所以分成多个小案例......在出现错误时更容易修复。

Divide et impera :) so split in multiple small cases ...easier to fix in case of errors.

多孤肩上扛 2024-11-21 05:26:11

您将测试断言混淆了。具有多个 assert 的测试方法可以测试多项内容:默认设置设置上下文变量。但是测试一件事的测试方法也可以有多个断言。

一个好的模式是每个测试用例都有四个阶段:

  1. 设置:创建执行测试所需的对象,并在必要时更改这些对象以将它们放入所需的初始状态中。州。
  2. 练习:您执行正在测试的操作的位置。这将是一个方法调用,或构造函数调用。
  3. 验证:检查被测对象是否处于正确的状态,并检查您在练习阶段调用的方法返回的值,如果返回了一个值。这是您放置断言的位置。如果您使用此模式,则在验证阶段放置多个断言不会有任何问题。
  4. 拆卸:销毁或关闭用于执行测试的对象。

这是 Gerard Meszaros 所著的《xUnit 测试模式:重构测试代码》一书中推荐的方法。

将该模式与第一个示例中的模式进行对比,在第一个示例中,您似乎会执行以下操作:

  1. 初始设置
  2. 练习构造函数
  3. 验证默认
  4. 设置上下文变量的练习
  5. 验证上下文变量的设置
  6. 拆卸

You are confusing a test with an assertion. Your test method with multiple asserts tests multiple things: default setting and setting a context variable. But a test method that tests one thing can also have multiple asserts.

A good pattern to use is for each test-case to have four phases:

  1. Setup: where you create the objects you need to perform the test, and if necessary alter those objects to put them in the required initial states.
  2. Exercise: where you perform the operation that you are testing. This will be one method call, or a constructor call.
  3. Verify: where you check that the objects under test are in the correct state(s), and check the value returned by the method you called in the exercise phase, if it returned a value. This is where you place your asserts. If you use this pattern, there is nothing wrong with placing multiple asserts in the verify phase.
  4. Teardown: where you destroy or close the objects you used to perform the test.

That is the approach recommended in the book xUnit Test Patterns: Refactoring Test Code by Gerard Meszaros.

Contrast that pattern with what you have in your first example, in which it seems you would do this:

  1. Initial setup
  2. Exercise constructor
  3. Verify default
  4. Exercise to set a context variable
  5. Verify setting of context variable
  6. Teardown
愁杀 2024-11-21 05:26:11

Eclipse 为每个方法生成单元测试,这似乎是一种合理的方法。
如果测试的方法太复杂而无法使用一种测试方法进行测试,那么您可以考虑重构它。

但更好的方法是使用 TDD 并预先编写测试,这将驱动其余的设计和实现。

就个人而言,我更喜欢对每种方法进行一次测试以及 Eclipse 的 Java 代码覆盖率 http://www.eclemma.org

该工具会告诉您实际测试的内容。

Eclipse generates unit test per method which seems to be a reasonable approach.
If the tested method is too complex to test it using one test method then You may consider re factoring it.

But a much more better approach is to use TDD and write the tests upfront which will drive the rest of the design and implementation.

Personally I prefer to have one test per method along with the Java Code Coverage for Eclipse http://www.eclemma.org.

The tool will tell You what You're actually testing.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文