Wednesday, January 6, 2010

Unit testing reference

The parts of unit testing I'm trying to commit to memory but keep referring back to are as follows:
  • Good unit test properties
    • automated and repeatable
    • easy to implement
    • once written, should remain for future use
    • anyone should be able to run it
    • should run at the push of a button
    • should run quickly
  • Is it a good unit test?
    • Can I run and get results from a unit test written weeks,months, years ago?
    • Can any member of the team run and get results from unit tests written weeks,months, years ago?
    • Can I run all the unit tests I've written in no more than a few minutes?
    • Can I run all the unit tests at the push of a button?
    • Can I write a basic unit test in no more than a few minutes?
  • TDD overview:
    • Write a failing test to prove code or functionality is missing
    • Make the test pass by writing production code that meets the expectations of the test
    • Refactor your code
    • [blogger's note: I would run the tests again after the refactoring]
  • Definitions
    • Integration test
      • testing two or more dependent software modules as a group
      • If the method you are testing has external dependencies (filesystem, sql server, OS, etc..) that you are not able to provide fakes for then it is an integration test
    • Unit test
      • a piece of code (usually a method) that runs another piece of code (usually a single method/function in isolation) and checks the correctness of some assumptions afterward. If the assumptions are wrong, the unit test is failed.
    • SUT - system under test (sometimes CUT - class under test)
      • when we test something, we refer to the thing we are testing as the SUT.
    • Regression
      • a feature that used to work and now doesn't
    • Naming conventions
      • Project
        • [ProjectUnderTest].Tests
      • Classes
        • For each class, create at least one class with the name [ClassName]Tests
      • Method
        • For each method, create at least one test method with the following name:
          • [MethodName]_[StateUnderTest]_[ExpectedBehavior]
            • StateUnderTest
              • The conditions used to produce the behavior
            • ExpectedBehavior
              • What you expect the tested method to do under the specified conditions
          • example: IsValidFileName_validFile_ReturnsTrue
    • Typical test method body
      • Arrange objects, creating and setting them up as necessary
      • Act on an object
      • Assert the expected results
    • Types of unit tests
      • State based testing/state verification
        • you act on something, assert the state after acting on that something or its collaborators(dependencies)
      • Interaction testing
        • tests how an object sends input to or recieves input from other objects
        • how that object interacts with other objects
    • Stub
      • a controllable replacement for an existing dependency(or collaborator) in the system.
      • By using a stub, you can test your code without dealing with the dependency directly.
      • Can not fail a test - not asserted against
    • Mock
      • a fake object in the system that decides whether the unit test has passed or failed. It does so by verifying whether the object under test interacted as expected with the fake object. There's usually no more than one mock per test.
      • Asserted against
    • Fake
      • generic term for mock or stub
  • Things to look out for
    • Why are we doing multiple asserts in a single test? How hard would it be to separate them into separate tests
    • Complicated hand-written stubs or mocks should be overcome with a Isolation (Mock) framework

2 comments:

  1. Great list.

    [quote]
    - Refactor your code
    - [blogger's note: I would run the tests again after the refactoring]
    [/quote]

    An absolute must to run the test again after refactoring. Allowing for safe refactoring is one of the reason to write the tests in the first place.

    ReplyDelete
  2. Thanks Tim, this is based on my notes from a unit testing book, they didn't emphasize it, and I think it should have been =)

    ReplyDelete