Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Applying TDD to Infrastructure Code

Applying TDD to Infrastructure Code

Talk given at engineers4engineers, Waltham, MA

Stephen Nelson-Smith

September 12, 2014
Tweet

More Decks by Stephen Nelson-Smith

Other Decks in Programming

Transcript

  1. Steps to write a unit test •Ensure the object can

    operate in isolation •Create the object •Provide any dependencies •Interact with the object •Verify the object behaved as expiated
  2. Listening to the tests If the test is hard to

    write: The design is probably wrong.
  3. “We’ve seen projects with high-quality, well unit-tested code that turned

    out not to be called from anywhere, or that could not be integrated with the rest of the system and had to be rewritten.” ! Steve Freeman & Nat Pryce, Growing Object-Oriented Software, Guided by Tests ! Doing the wrong thing right
  4. Gojko Adžić’s Useless Crap Diagram Build the right thing Business

    Failure Useless Crap Success Maintenance Nightmare Build the thing right
  5. Gojko Adžić’s Useless Crap Diagram Build the right thing Business

    Failure Useless Crap Success Maintenance Nightmare Build the thing right
  6. Brian Marick’s Testing Quadrant Business-facing Technology-facing Support development Critique Project

    Acceptance Tests Unit Tests Integration Tests Usability Tests Exploratory Tests Load Tests Penetration Tests
  7. Brian Marick’s Testing Quadrant Business-facing Technology-facing Support development Critique Project

    Acceptance Tests Unit Tests Integration Tests Usability Tests Exploratory Tests Load Tests Penetration Tests
  8. +

  9. Thankfully…. kitchen@tk00:~$ chef --version! Chef Development Kit Version: 0.2.1! kitchen@tk00:~$

    kitchen --version! Test Kitchen version 1.2.1! kitchen@tk00:~$ VBoxManage --version! 4.3.16r95972! kitchen@tk00:~$ vagrant --version! Vagrant 1.6.5
  10. $ chef --help! Usage:! chef -h/--help! chef -v/--version! chef command

    [arguments...] [options...]! ! ! Available Commands:! exec Runs the command in context of the embedded ruby! gem Runs the `gem` command in context of the embedded ruby! generate Generate a new app, cookbook, or component! shell-init Initialize your shell to use ChefDK as your primary ruby! verify Test the embedded ChefDK applications Chef CLI
  11. What’s in the box? • Foodcritic • Test-Kitchen (KitchenCI) •

    Chefspec • Berkshelf • Chef CLI • Knife • Chef Client
  12. $ chef --help! Usage:! chef -h/--help! chef -v/--version! chef command

    [arguments...] [options...]! ! ! Available Commands:! exec Runs the command in context of the embedded ruby! gem Runs the `gem` command in context of the embedded ruby! generate Generate a new app, cookbook, or component! shell-init Initialize your shell to use ChefDK as your primary ruby! verify Test the embedded ChefDK applications Chef CLI
  13. Run kitchen test •Obtains Vagrant boxes •Creates instances (ubuntu &

    centos) •Converges node (no runlist) •Skips setup (no tests) •Skips verify (no tests) •Destroys instances •Exits zero
  14. Create our test instances •Run kitchen create •Creates instances (ubuntu

    & centos) •Can keep them around for a while (saves time) •Beware long-lived instances
  15. Run our test •Run kitchen verify •Installs Chef •Runs kitchen

    setup (installs testing tools) •Copies tests to instance •Runs tests •Reports results
  16. Bootstrap a machine knife digital_ocean droplet create \! --server-name tk

    \! --image 1234 --size 62 --location 4 \ -- ssh-keys 4321 --ssh-port 22 \ ! --bootstrap \ ! --identity-file ~/.ssh/lordcope
  17. Write the code to make it pass… (see the power

    of Chef / Berkshelf) In recipes/default.rb: In metadata.rb:
  18. “Code without tests is bad code. It doesn't matter how

    well written it is; it doesn't matter how pretty or object-oriented or well-encapsulated it is. With tests, we can change the behavior of our code quickly and verifiably. Without them, we really don't know if our code is getting better or worse.”! ― Michael C. Feathers, Working Effectively with Legacy Code" Conclusion
  19. ! “Tests that take too long to run end up

    not being run.”! ― Michael C. Feathers, Working Effectively with Legacy Code Speeding up tests