A recent article (
[here]) showed you how we build up a series of classes, each with their own piece of test code, into applications.
It's all very well putting a piece of test code in the bottom of our class definition file - and that's a useful thing to do - but it's just a single test, and it doesn't provide for a management system for tests, nor for regression testing where new tests are added to a suite as more code gets added to the class. That's where
cucumber comes in - and we have a whole separate module on that - see
[here].
Using cucumber, we describe a
behaviour in a feature file (using the gherkin language):
Feature: Checking we know station names
Scenario:
When we ask for the full name for "MKM"
Then we are told it is "Melksham"
Scenario:
When we ask for the full name for "PLY"
Then we are told it is "Plymouth"
Scenario:
When we ask for the full name for "OXF"
Then we are told it is "Oxford"
Scenario:
When we ask for the full name for "BNS"
Then we are told it is "Birmingham New Street"
We then run that under cucumber, and we're offered snippets of code to help us implement the tests which might look like
When(/^we ask for the full name for "(.*?)"$/) do |arg1|
@station = loadStationFactory[arg1]
end
Then(/^we are told it is "(.*?)"$/) do |arg1|
expect(@station.getFullName).to eq(arg1)
end
and when we run that completed code, all of our scenarios are run and we see a full set of results:
munchkin:lr grahamellis$ cucumber -s bdd_stations
Feature: Checking we know station names
Scenario:
When we ask for the full name for "MKM"
Then we are told it is "Melksham"
Scenario:
When we ask for the full name for "PLY"
Then we are told it is "Plymouth"
Scenario:
When we ask for the full name for "OXF"
Then we are told it is "Oxford"
Scenario:
When we ask for the full name for "BNS"
Then we are told it is "Birmingham New Street"
expected: "Birmingham New Street"
got: "Barnes"
(compared using ==)
(RSpec::Expectations::ExpectationNotMetError)
./bdd_stations/step_definitions/station_steps.rb:10:in `/^we are told it is "(.*?)"$/'
bdd_stations/station.feature:19:in `Then we are told it is "Birmingham New Street"'
Failing Scenarios:
cucumber bdd_stations/station.feature:17
4 scenarios (1 failed, 3 passed)
8 steps (1 failed, 7 passed)
0m0.238s
munchkin:lr grahamellis$
Files for this example:
[here]for the file to be tested
[here] for feature definitions
[here] for step implementation
[here] for the data used by the class
(written 2015-10-23)
Associated topics are indexed as below, or enter http://melksh.am/nnnn for individual articles
R221 - Ruby - Introduction to Cucumber [4380] Behaviour Driven Development / Ruby and Cucumber - (2015-01-02)
[4381] Installing Cucumber (Ruby) - (2015-01-03)
[4382] Second step Cucumber and Gherkin - beyond Hello World - (2015-01-03)
[4383] Improved test in Cucumber with RSpec - (2015-01-03)
[4384] Installing Cucumber on Ubuntu - cannot load such file -- mkmf (LoadError) message - (2015-01-04)
[4386] Guide exercise to help you learn Gherkin, Cucumber and Rspec - (2015-01-06)
[4552] Scenario outlines - tables of values to test - in Gherkin / Cucumber - (2015-10-23)
R108 - Ruby - More Classes and Objects [184] MTBF of coffee machines - (2005-01-20)
[656] Think about your design even if you don't use full UML - (2006-03-24)
[1217] What are factory and singleton classes? - (2007-06-04)
[1587] Some Ruby programming examples from our course - (2008-03-21)
[2292] Object Orientation in Ruby - intermediate examples - (2009-07-16)
[2601] Ruby - is_a? v instance_of? - what is the difference? - (2010-01-27)
[2603] Ruby objects - a primer - (2010-01-29)
[2604] Tips for writing a test program (Ruby / Python / Java) - (2010-01-29)
[2616] Defining a static method - Java, Python and Ruby - (2010-02-01)
[2620] Direct access to object variable (attributes) in Ruby - (2010-02-02)
[2623] Object Oriented Ruby - new examples - (2010-02-03)
[2717] The Multiple Inheritance Conundrum, interfaces and mixins - (2010-04-11)
[2977] What is a factory method and why use one? - Example in Ruby - (2010-09-30)
[2980] Ruby - examples of regular expressions, inheritance and polymorphism - (2010-10-02)
[3142] Private and Public - and things between - (2011-01-22)
[3154] Changing a class later on - Ruby - (2011-02-02)
[3158] Ruby training - some fresh examples for string handling applications - (2011-02-05)
[3260] Ruby - a training example that puts many language elements together to demonstrate the whole - (2011-04-23)
[3760] Why you should use objects even for short data manipulation programs in Ruby - (2012-06-10)
[3781] Private, Protected, Public in Ruby. What about interfaces and abstract classes in Ruby? - (2012-06-23)
[3782] Standard methods available on all objects in Ruby - (2012-06-23)
[4366] Changing what operators do on objects - a comparison across different programming languages - (2014-12-26)
[4504] Where does Ruby load modules from, and how to load from current directory - (2015-06-03)
[4550] Build up classes into applications sharing data types in Ruby - (2015-10-23)
Some other Articles
Preprocessor directives in C and C++ - what they meanPassing information into functions in C - by name, by valueRUby - loading, using, changing, storing JSON format dataTesting your new class - first steps with cucumberClarrissa-Marybelle - too long to really fit?Melksham - two small townships, or one big one?RUH Hopper - experience and thoughts forwardIs the RUH hopper a limited, duplicate service running unnecessarily and at high cost?