STAssertTrue(thisThi
ng.state ==
NSONState, @”Is this
thing on?”);
   An iOS developer’s guide to unit testing
Software engineering:
       goals
Software engineering:
        goals
• Make money (sometimes)
Software engineering:
        goals
• Make money (sometimes)
• …by making software that the customer
  wants
Software engineering:
        goals
• Make money (sometimes)
• …by making software that the customer
  wants
 • Satisfies t...
Software engineering:
        goals
• Make money (sometimes)
• …by making software that the customer
  wants
 • Satisfies t...
Testing: goals
                         Cost                        Time Detected
• validate code
    behaviour           ...
Testing: goals
                             Cost                        Time Detected
• validate code
    behaviour       ...
The testing landscape
                                                        System Test Beta/Acceptance Testing
Black Bo...
The testing landscape
                                                        System Test Beta/Acceptance Testing
Black Bo...
TDD - what it achieves
TDD - what it achieves
• Imposes black-box thinking for the
  developer
TDD - what it achieves
• Imposes black-box thinking for the
  developer
• Guides design and implementation
TDD - what it achieves
• Imposes black-box thinking for the
  developer
• Guides design and implementation
• YAGNI
TDD - what it achieves
• Imposes black-box thinking for the
  developer
• Guides design and implementation
• YAGNI
• Provi...
TDD - what it achieves
• Imposes black-box thinking for the
  developer
• Guides design and implementation
• YAGNI
• Provi...
Find bugs before…
© 2009 Microsoft




…your customers do
TDD != [bullet
 silverColor]
TDD != [bullet
       silverColor]
• Can’t ensure the developer understood
  requirements
TDD != [bullet
        silverColor]
• Can’t ensure the developer understood
  requirements
• Or that the requirements rema...
TDD != [bullet
        silverColor]
• Can’t ensure the developer understood
  requirements
• Or that the requirements rema...
TDD != [bullet
        silverColor]
• Can’t ensure the developer understood
  requirements
• Or that the requirements rema...
TDD != [bullet
        silverColor]
• Can’t ensure the developer understood
  requirements
• Or that the requirements rema...
How TDD Works
How TDD Works
     RED
How TDD Works
     RED
    GREEN
How TDD Works
     RED
    GREEN
   REFACTOR
What do I test?
What do I test?
• Anything, within reason
 • Mustn’t take too long to run the tests
 • Shouldn’t depend on the environment...
What do I test?
• Anything, within reason
 • Mustn’t take too long to run the tests
 • Shouldn’t depend on the environment...
When do I test?


• Whenever you make a change
• Whenever you want to build
Test Design
#import <SenTestingKit/SenTestingKit.h>

@interface DateComparisonTests : SenTestCase {             One (or mo...
Test Design

must be repeatable
 Source: http://xkcd.com/221/
Testable code
Testable code

• Small, focussed classes, that contain…
Testable code

• Small, focussed classes, that contain…
• Short methods, each with obvious effect
Testable code

• Small, focussed classes, that contain…
• Short methods, each with obvious effect
• Any side-effects are f...
Testable code

• Small, focussed classes, that contain…
• Short methods, each with obvious effect
• Any side-effects are f...
Testable code

• Small, focussed classes, that contain…
• Short methods, each with obvious effect
• Any side-effects are f...
Testable code

• Small, focussed classes, that contain…
• Short methods, each with obvious effect
• Any side-effects are f...
OCUnit and Xcode 3
OCUnit and Xcode 4
OCUnit and Xcode 4
                Yay!




                Boo.
The competition…
The competition…
OCUnit and the Device




Source: http://developer.apple.com/iphone/library/documentation/Xcode/Conceptual/
 iphone_develo...
Enter GHUnit




http://github.com/gabriel/gh-unit
Enter GHUnit




http://github.com/gabriel/gh-unit
Fakes and Mocks

- (IBAction)removeTune: (id)sender
{
   [self.tunesArrayController remove: sender];
   [self destroyAttac...
Fakes and Mocks
            Fake sender

- (IBAction)removeTune: (id)sender
{
   [self.tunesArrayController remove: sender...
Fakes and Mocks
            Fake sender

- (IBAction)removeTune: (id)sender
{
   [self.tunesArrayController remove: sender...
Bibble…Biblob…List of
       books
Bibble…Biblob…List of
       books
Bibble…Biblob…List of
       books
Bibble…Biblob…List of
       books
Bibble…Biblob…List of
       books
Bibble…Biblob…List of
       books
iamleeg
iamleeg
Upcoming SlideShare
Loading in …5
×

Unit testing for Cocoa developers

3,741 views

Published on

An introduction to the motivation and theory behind test-driven development, suitable for people with experience in Mac or iOS development using Objective-C.

Published in: Technology
  • Be the first to comment

Unit testing for Cocoa developers

  1. 1. STAssertTrue(thisThi ng.state == NSONState, @”Is this thing on?”); An iOS developer’s guide to unit testing
  2. 2. Software engineering: goals
  3. 3. Software engineering: goals • Make money (sometimes)
  4. 4. Software engineering: goals • Make money (sometimes) • …by making software that the customer wants
  5. 5. Software engineering: goals • Make money (sometimes) • …by making software that the customer wants • Satisfies the customer’s requirements
  6. 6. Software engineering: goals • Make money (sometimes) • …by making software that the customer wants • Satisfies the customer’s requirements • Without costing too much to make
  7. 7. Testing: goals Cost Time Detected • validate code behaviour Time Requirements Architecture Construction System After introduced Test Release • discover defects Requirements 1 3 5-10 10 10-100 • verify fixes Architecture - 1 10 15 25-100 • detect regressions Construction - - 1 10 10-25
  8. 8. Testing: goals Cost Time Detected • validate code behaviour Time Requirements Architecture Construction System After introduced Test Release • discover defects Requirements 1 3 5-10 10 10-100 • verify fixes Architecture - 1 10 15 25-100 • detect regressions Construction - - 1 10 10-25 Unit Testing
  9. 9. The testing landscape System Test Beta/Acceptance Testing Black Box Pen/fuzz Testing Integration Testing GUI Testing Grey Box Unit testing (undirected) Source Audit White Box Class Component System Static Analysis, Debugging
  10. 10. The testing landscape System Test Beta/Acceptance Testing Black Box Pen/fuzz Testing Integration Testing GUI Testing TDD Grey Box Unit testing (undirected) Source Audit White Box Class Component System Static Analysis, Debugging
  11. 11. TDD - what it achieves
  12. 12. TDD - what it achieves • Imposes black-box thinking for the developer
  13. 13. TDD - what it achieves • Imposes black-box thinking for the developer • Guides design and implementation
  14. 14. TDD - what it achieves • Imposes black-box thinking for the developer • Guides design and implementation • YAGNI
  15. 15. TDD - what it achieves • Imposes black-box thinking for the developer • Guides design and implementation • YAGNI • Provides a safety net for future development
  16. 16. TDD - what it achieves • Imposes black-box thinking for the developer • Guides design and implementation • YAGNI • Provides a safety net for future development • Assists accurate planning
  17. 17. Find bugs before…
  18. 18. © 2009 Microsoft …your customers do
  19. 19. TDD != [bullet silverColor]
  20. 20. TDD != [bullet silverColor] • Can’t ensure the developer understood requirements
  21. 21. TDD != [bullet silverColor] • Can’t ensure the developer understood requirements • Or that the requirements remained static
  22. 22. TDD != [bullet silverColor] • Can’t ensure the developer understood requirements • Or that the requirements remained static • Doesn’t guarantee successful integration
  23. 23. TDD != [bullet silverColor] • Can’t ensure the developer understood requirements • Or that the requirements remained static • Doesn’t guarantee successful integration • Takes time (mainly to write)
  24. 24. TDD != [bullet silverColor] • Can’t ensure the developer understood requirements • Or that the requirements remained static • Doesn’t guarantee successful integration • Takes time (mainly to write) • Must actually be run to add value
  25. 25. How TDD Works
  26. 26. How TDD Works RED
  27. 27. How TDD Works RED GREEN
  28. 28. How TDD Works RED GREEN REFACTOR
  29. 29. What do I test?
  30. 30. What do I test? • Anything, within reason • Mustn’t take too long to run the tests • Shouldn’t depend on the environment • database, filesystem, network • …not that those tests aren’t important
  31. 31. What do I test? • Anything, within reason • Mustn’t take too long to run the tests • Shouldn’t depend on the environment • database, filesystem, network • …not that those tests aren’t important • Evaluate risk • known-buggy classes • “hard” code
  32. 32. When do I test? • Whenever you make a change • Whenever you want to build
  33. 33. Test Design #import <SenTestingKit/SenTestingKit.h> @interface DateComparisonTests : SenTestCase { One (or more) per class - (void)setUp { gregorianCalendar = [[NSCalendar alloc] initWithCalendarIdentifier: NSGregorianCalendar]; comps = [[NSDateComponents alloc] init]; } Common stuff here - (void)tearDown { [gregorianCalendar release]; gregorianCalendar = nil; [comps release]; comps = nil; } - (void)testDatesOnTheSameDayAreConsideredSame { //... } - (void)testCloseDatesOnSeparateDaysAreNotSame { These all independent short, readable, fast //... } - (void)testSameDayInDifferentYearsAreNotTheSame { //... }
  34. 34. Test Design must be repeatable Source: http://xkcd.com/221/
  35. 35. Testable code
  36. 36. Testable code • Small, focussed classes, that contain…
  37. 37. Testable code • Small, focussed classes, that contain… • Short methods, each with obvious effect
  38. 38. Testable code • Small, focussed classes, that contain… • Short methods, each with obvious effect • Any side-effects are few and easy to predict
  39. 39. Testable code • Small, focussed classes, that contain… • Short methods, each with obvious effect • Any side-effects are few and easy to predict • Helper data passed in, not discovered
  40. 40. Testable code • Small, focussed classes, that contain… • Short methods, each with obvious effect • Any side-effects are few and easy to predict • Helper data passed in, not discovered • Low “cyclomatic complexity”
  41. 41. Testable code • Small, focussed classes, that contain… • Short methods, each with obvious effect • Any side-effects are few and easy to predict • Helper data passed in, not discovered • Low “cyclomatic complexity” i.e. an end to @interface GodClass : UIViewController
  42. 42. OCUnit and Xcode 3
  43. 43. OCUnit and Xcode 4
  44. 44. OCUnit and Xcode 4 Yay! Boo.
  45. 45. The competition…
  46. 46. The competition…
  47. 47. OCUnit and the Device Source: http://developer.apple.com/iphone/library/documentation/Xcode/Conceptual/ iphone_development/135-Unit_Testing_Applications/unit_testing_applications.html
  48. 48. Enter GHUnit http://github.com/gabriel/gh-unit
  49. 49. Enter GHUnit http://github.com/gabriel/gh-unit
  50. 50. Fakes and Mocks - (IBAction)removeTune: (id)sender { [self.tunesArrayController remove: sender]; [self destroyAttachedWindow]; }
  51. 51. Fakes and Mocks Fake sender - (IBAction)removeTune: (id)sender { [self.tunesArrayController remove: sender]; [self destroyAttachedWindow]; }
  52. 52. Fakes and Mocks Fake sender - (IBAction)removeTune: (id)sender { [self.tunesArrayController remove: sender]; [self destroyAttachedWindow]; } Mock array controller
  53. 53. Bibble…Biblob…List of books
  54. 54. Bibble…Biblob…List of books
  55. 55. Bibble…Biblob…List of books
  56. 56. Bibble…Biblob…List of books
  57. 57. Bibble…Biblob…List of books
  58. 58. Bibble…Biblob…List of books
  59. 59. iamleeg
  60. 60. iamleeg

×