Slide 1

Slide 1 text

A TDD primer with Ruby Or something.

Slide 2

Slide 2 text

The structure of this talk 1. Test-Driven Development theory / methodology 2. Ruby testing tools 3. Demo

Slide 3

Slide 3 text

What is Test Driven Development? a software development process that relies on the repetition of a very short development cycle: first the developer writes a failing automated test case that defines a desired improvement or new function, then produces code to pass that test and finally refactors the new code to acceptable standards

Slide 4

Slide 4 text

What is Test Driven Development? a software development process that relies on the repetition of a very short development cycle: first the developer writes a failing automated test case that defines a desired improvement or new function, then produces code to pass that test and finally refactors the new code to acceptable standards TL; DR

Slide 5

Slide 5 text

What is Test Driven Development? 1. RED a. Write a failing test. 2. GREEN a. Write code to make the failing test pass. 3. REFACTOR a. Confidently clean up, making sure tests stay green. 4. GOTO 1

Slide 6

Slide 6 text

Why test first? 1. Encourages simple designs a. Only write enough code to make tests pass b. Prevents over-design c. Less code == fewer bugs 2. Inspires confidence a. Have the freedom to relentlessly refactor 3. Red -> Green verifies that the test is valid a. Testing after the fact doesn't ensure that the code you wrote made the test pass

Slide 7

Slide 7 text

Ruby testing tools ● Test libraries ○ Test::Unit, RSpec, Minitest::Spec ● Factory libraries ○ FactoryGirl, Machinist, Fabrication ● TDD workflow / efficiency tools ○ Spork ■ Dynamic ruby server that forks before each run to ensure a clean testing state ○ Guard ■ Watches project files, runs corresponding tests when code or tests have changed

Slide 8

Slide 8 text

Minitest::Spec example require 'minitest/spec' require 'minitest/autorun' describe Array do it "can be created with no arguments" do Array.new.must_be_instance_of Array end it "can be created with a specific size" do Array.new(10).size.must_equal 10 end end

Slide 9

Slide 9 text

Minitest::Spec expectations obj.must_be(operator, expected) - for example, 10.must_be :< , 11 obj.must_be_close_to - the equivalent of assert_in_delta obj.must_be_empty - Fails unless obj.empty? obj.must_be_instance_of(klass) - Fails unless obj.class == klass obj.must_be_kind_of(klass) - Fails unless obj is of class klass or klass is one of its superclasses. obj.must_be_nil obj.must_be_same_as - tests for true object equality lambda {}.must_be_silent obj.must_be_within_delta obj.must_be_within_epsilon obj.must_equal(other) - Does a ==/eql? comparison between two objects. obj.must_include(other) obj.must_match(regex) - A regular expression match, e.g. "hello".must_match /w+/ lambda {}.must_output(stdout, [stderr..]) - The block should have certain output on stdout or stderr. Set stdout to nil just to check stderr. lambda {}.must_raise(exception) obj.must_respond_to(message) obj.must_throw(sym)

Slide 10

Slide 10 text

Defining a Factory Girl factory # ../my_project/app/models/applicant.rb class Applicant < ActiveRecord::Base validates_presence_of :name validates_presence_of :date_of_birth end # ../my_project/test/factories/applicants.rb FactoryGirl.define do factory :applicant do name 'John Doe' date_of_birth { 21.years.ago } end end

Slide 11

Slide 11 text

Using a Factory Girl factory describe Applicant do it "will have a valid factory instance" do FactoryGirl.build(:applicant).must_be :valid? end it "can successfully be saved" do applicant = FactoryGirl.create(:applicant) Applicant.first.must_equal applicant end end

Slide 12

Slide 12 text

DO IT LIVE!

Slide 13

Slide 13 text

Resources ● TDD books ○ Growing Object-Oriented Software, Guided by Tests ○ Test Driven Development: By Example (Kent Beck) ○ Rails Test Prescriptions (Noel Rappin) ● Minitest::Spec ○ http://www.rubyinside.com/a-minitestspec-tutorial-elegant-spec- style-testing-that-comes-with-ruby-5354.html ● Factory Girl ○ https://github. com/thoughtbot/factory_girl/blob/master/GETTING_STARTED.md